1 |
/* Module for encryption using the Unix crypt() function. |
2 |
* |
3 |
* IRC Services is copyright (c) 1996-2009 Andrew Church. |
4 |
* E-mail: <achurch@achurch.org> |
5 |
* Parts written by Andrew Kempe and others. |
6 |
* This program is free but copyrighted software; see the file GPL.txt for |
7 |
* details. |
8 |
*/ |
9 |
|
10 |
#include "services.h" |
11 |
#include "modules.h" |
12 |
#include "conffile.h" |
13 |
#include "encrypt.h" |
14 |
|
15 |
#if !HAVE_CRYPT |
16 |
# define crypt(pass,salt) NULL |
17 |
#endif |
18 |
|
19 |
/*************************************************************************/ |
20 |
|
21 |
/* Allowable characters in the salt */ |
22 |
const char saltchars[] = |
23 |
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789./"; |
24 |
|
25 |
/*************************************************************************/ |
26 |
/*************************************************************************/ |
27 |
|
28 |
static int unixcrypt_encrypt(const char *src, int len, char *dest, int size) |
29 |
{ |
30 |
char buf[PASSMAX+1], salt[3]; |
31 |
const char *res; |
32 |
|
33 |
if (len > sizeof(buf)-1) |
34 |
len = sizeof(buf)-1; |
35 |
memcpy(buf, src, len); |
36 |
buf[len] = 0; |
37 |
salt[0] = saltchars[random()%64]; |
38 |
salt[1] = saltchars[random()%64]; |
39 |
salt[2] = 0; |
40 |
res = crypt(buf, salt); |
41 |
if (!res) { |
42 |
module_log_perror("encrypt: crypt() failed"); |
43 |
return -1; |
44 |
} |
45 |
if (strlen(res) > size-1) { |
46 |
module_log("encrypt: crypt() returned too long a string! (%d" |
47 |
" characters)", (int)strlen(res)); |
48 |
return strlen(res) + 1; |
49 |
} |
50 |
strscpy(dest, res, size); |
51 |
return 0; |
52 |
} |
53 |
|
54 |
/*************************************************************************/ |
55 |
|
56 |
static int unixcrypt_decrypt(const char *src, char *dest, int size) |
57 |
{ |
58 |
return -2; /* decryption impossible (in reasonable time) */ |
59 |
} |
60 |
|
61 |
/*************************************************************************/ |
62 |
|
63 |
static int unixcrypt_check_password(const char *plaintext, const char *password) |
64 |
{ |
65 |
const char *res; |
66 |
|
67 |
res = crypt(plaintext, password); |
68 |
if (!res) { |
69 |
module_log_perror("check_password: crypt() failed"); |
70 |
return -1; |
71 |
} |
72 |
if (strcmp(res, password) == 0) |
73 |
return 1; |
74 |
return 0; |
75 |
} |
76 |
|
77 |
/*************************************************************************/ |
78 |
/*************************************************************************/ |
79 |
|
80 |
/* Module stuff. */ |
81 |
|
82 |
ConfigDirective module_config[] = { |
83 |
{ NULL } |
84 |
}; |
85 |
|
86 |
static CipherInfo unixcrypt_info = { |
87 |
.name = "unix-crypt", |
88 |
.encrypt = unixcrypt_encrypt, |
89 |
.decrypt = unixcrypt_decrypt, |
90 |
.check_password = unixcrypt_check_password, |
91 |
}; |
92 |
|
93 |
int init_module(void) |
94 |
{ |
95 |
#if !HAVE_CRYPT |
96 |
module_log("Your system does not support the crypt() function!"); |
97 |
return 0; |
98 |
#else |
99 |
if (PASSMAX < 14) { |
100 |
module_log("PASSMAX too small (must be at least 14)"); |
101 |
return 0; |
102 |
} |
103 |
register_cipher(&unixcrypt_info); |
104 |
return 1; |
105 |
#endif |
106 |
} |
107 |
|
108 |
int exit_module(int shutdown_unused) |
109 |
{ |
110 |
unregister_cipher(&unixcrypt_info); |
111 |
return 1; |
112 |
} |
113 |
|
114 |
/*************************************************************************/ |
115 |
|
116 |
/* |
117 |
* Local variables: |
118 |
* c-file-style: "stroustrup" |
119 |
* c-file-offsets: ((case-label . *) (statement-case-intro . *)) |
120 |
* indent-tabs-mode: nil |
121 |
* End: |
122 |
* |
123 |
* vim: expandtab shiftwidth=4: |
124 |
*/ |