]>
Commit | Line | Data |
---|---|---|
18f8bd28 CP |
1 | /* |
2 | nterface library functions | |
3 | Copyright (C) 2003-2004 Chris Porter. | |
4 | */ | |
5 | ||
6 | #include <stdio.h> | |
7 | #include <stdlib.h> | |
8 | #include <errno.h> | |
9 | #include <string.h> | |
10 | #include <limits.h> | |
11 | #include <sys/time.h> | |
12 | #include <stdarg.h> | |
13 | ||
14 | #include "../core/config.h" | |
15 | #include "../lib/irc_string.h" | |
16 | #include "../lib/sha1.h" | |
17 | #include "../lib/helix.h" | |
18 | ||
19 | #include "library.h" | |
20 | ||
21 | unsigned char hexlookup[256] = { | |
22 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
23 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
24 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
25 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
26 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x01, | |
27 | 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0xff, 0xff, | |
28 | 0xff, 0xff, 0xff, 0xff, 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, | |
29 | 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
30 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
31 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0a, 0x0b, 0x0c, | |
32 | 0x0d, 0x0e, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
33 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
34 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
35 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
36 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
37 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
38 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
39 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
40 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
41 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
42 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
43 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
44 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
45 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
46 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, | |
47 | 0xff, 0xff, 0xff, 0xff, 0xff, 0xff | |
48 | }; | |
49 | ||
50 | FILE *challenge_random_fd = NULL; | |
51 | ||
52 | unsigned char entropybuffer[CHALLENGE_ENTROPYLEN * CHALLENGE_ENTROPYBUF]; | |
53 | int entropy_remaining = 0; | |
54 | ||
55 | int getcopyconfigitemint(char *section, char *key, int def, int *value) { | |
56 | char buf[50]; | |
57 | sstring *ini; | |
58 | ||
59 | snprintf(buf, sizeof(buf), "%d", def); | |
60 | ini = getcopyconfigitem(section, key, buf, 6); | |
61 | ||
62 | if(!ini) | |
63 | return 0; | |
64 | ||
65 | if(!protectedatoi(ini->content, value)) | |
66 | return 0; | |
67 | ||
68 | return 1; | |
69 | } | |
70 | ||
71 | int getcopyconfigitemintpositive(char *section, char *key, int def) { | |
72 | int value; | |
73 | if(!getcopyconfigitemint(section, key, def, &value)) | |
74 | return -1; | |
75 | ||
76 | if(value < 0) | |
77 | return -1; | |
78 | ||
79 | return value; | |
80 | } | |
81 | ||
82 | int positive_atoi(char *data) { | |
83 | int value; | |
84 | if(!protectedatoi(data, &value)) | |
85 | return -1; | |
86 | ||
87 | if(value < 0) | |
88 | return -1; | |
89 | ||
90 | return value; | |
91 | } | |
92 | ||
93 | char *challenge_response(char *challenge, char *password) { | |
94 | unsigned char buf[20]; | |
95 | static char output[sizeof(buf) * 2 + 1]; | |
96 | SHA1_CTX context; | |
97 | ||
98 | SHA1Init(&context); | |
99 | SHA1Update(&context, (unsigned char *)password, strlen(password)); | |
100 | SHA1Update(&context, (unsigned char *)" ", 1); | |
101 | SHA1Update(&context, (unsigned char *)challenge, strlen(challenge)); | |
102 | SHA1Final(buf, &context); | |
103 | ||
104 | TwentyByteHex(output, buf); | |
105 | ||
106 | return output; | |
107 | } | |
108 | ||
109 | /* my entropy function from Q */ | |
110 | int get_challenge_entropy(unsigned char *data) { | |
111 | if (!challenge_random_fd) { | |
112 | challenge_random_fd = fopen(CHALLENGE_RANDOM_LOCATION, "rb"); | |
113 | if(!challenge_random_fd) | |
114 | return 0; | |
115 | } | |
116 | ||
117 | if(!entropy_remaining) { | |
118 | if(fread(entropybuffer, 1, sizeof(entropybuffer), challenge_random_fd) != sizeof(entropybuffer)) | |
119 | return 0; | |
120 | entropy_remaining = CHALLENGE_ENTROPYBUF; | |
121 | } | |
122 | ||
123 | memcpy(data, entropybuffer + (CHALLENGE_ENTROPYBUF - entropy_remaining) * CHALLENGE_ENTROPYLEN, CHALLENGE_ENTROPYLEN); | |
124 | entropy_remaining--; | |
125 | ||
126 | return 1; | |
127 | } | |
128 | ||
129 | int generate_nonce(unsigned char *nonce, int nterfacer) { | |
130 | unsigned char entropy[CHALLENGE_ENTROPYLEN]; | |
131 | struct timeval tvv; | |
132 | if(!get_challenge_entropy(entropy)) | |
133 | return 0; | |
134 | ||
135 | gettimeofday(&tvv, NULL); | |
136 | ||
137 | memcpy(nonce, &tvv, sizeof(struct timeval)); | |
138 | memcpy(nonce + sizeof(struct timeval) - 2, entropy, NONCE_LEN - sizeof(struct timeval) + 2); | |
139 | ||
140 | if(nterfacer) { | |
15c8d833 | 141 | nonce[7]&=128; |
18f8bd28 | 142 | } else { |
15c8d833 | 143 | nonce[7]|=127; |
18f8bd28 CP |
144 | } |
145 | ||
146 | return 1; | |
147 | } | |
148 | ||
149 | char *get_random_hex(void) { | |
150 | static char output[CHALLENGE_ENTROPYLEN * 2 + 1]; | |
151 | unsigned char stored[CHALLENGE_ENTROPYLEN]; | |
152 | if(get_challenge_entropy(stored)) { | |
153 | TwentyByteHex(output, stored); | |
154 | } else { | |
155 | return NULL; | |
156 | } | |
157 | return output; | |
158 | } | |
159 | ||
160 | char *int_to_hex(unsigned char *input, char *buf, int len) { | |
161 | int i; | |
162 | for(i=0;i<len;i++) | |
163 | sprintf(buf + i * 2, "%.2x", input[i]); | |
164 | *(buf + len * 2) = '\0'; | |
165 | return buf; | |
166 | } | |
167 | ||
168 | int hex_to_int(char *input, unsigned char *buf, int buflen) { | |
169 | int i; | |
170 | for(i=0;i<buflen;i++) { | |
171 | if((0xff == hexlookup[(int)input[i * 2]]) || (0xff == hexlookup[(int)input[i * 2 + 1]])) { | |
172 | return 0; | |
173 | } else { | |
174 | buf[i] = (hexlookup[(int)input[i * 2]] << 4) | hexlookup[(int)input[i * 2 + 1]]; | |
175 | } | |
176 | } | |
177 | return 1; | |
178 | } | |
179 | ||
180 | char *request_error(int errn) { | |
181 | static char err[100]; | |
182 | ||
183 | err[0] = '\0'; | |
184 | switch (errn) { | |
185 | case RE_MEM_ERROR: | |
186 | snc(err, "Memory error"); | |
187 | break; | |
188 | case RE_SERVICE_NOT_FOUND: | |
189 | snc(err, "Service not found on this nterfaced instance"); | |
190 | break; | |
191 | case RE_REQUEST_REJECTED: | |
192 | snc(err, "Transport handler rejected request"); | |
193 | break; | |
194 | case RE_CONNECTION_CLOSED: | |
195 | snc(err, "Transport handler closed connection"); | |
196 | break; | |
197 | case RE_TRANSPORT_NOT_FOUND: | |
198 | snc(err, "Transport module not yet loaded for this service"); | |
199 | break; | |
200 | case RE_COMMAND_NOT_FOUND: | |
201 | snc(err, "Command not found on this service"); | |
202 | break; | |
203 | case RE_WRONG_ARG_COUNT: | |
204 | snc(err, "Wrong number of arguments for this command"); | |
205 | break; | |
206 | case RE_TOO_MANY_ARGS: | |
207 | snc(err, "Too many arguments supplied"); | |
208 | break; | |
209 | case RE_SERVICER_NOT_FOUND: | |
210 | snc(err, "Service not found on this nterfacer instance"); | |
211 | break; | |
212 | default: | |
213 | snc(err, "Unable to find error message"); | |
214 | } | |
215 | err[sizeof(err) - 1] = '\0'; | |
216 | ||
217 | return err; | |
218 | } |