]>
Commit | Line | Data |
---|---|---|
58964a49 | 1 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
d02b48c6 RE |
2 | * All rights reserved. |
3 | * | |
4 | * This package is an SSL implementation written | |
5 | * by Eric Young (eay@cryptsoft.com). | |
6 | * The implementation was written so as to conform with Netscapes SSL. | |
0f113f3e | 7 | * |
d02b48c6 RE |
8 | * This library is free for commercial and non-commercial use as long as |
9 | * the following conditions are aheared to. The following conditions | |
10 | * apply to all code found in this distribution, be it the RC4, RSA, | |
11 | * lhash, DES, etc., code; not just the SSL code. The SSL documentation | |
12 | * included with this distribution is covered by the same copyright terms | |
13 | * except that the holder is Tim Hudson (tjh@cryptsoft.com). | |
0f113f3e | 14 | * |
d02b48c6 RE |
15 | * Copyright remains Eric Young's, and as such any Copyright notices in |
16 | * the code are not to be removed. | |
17 | * If this package is used in a product, Eric Young should be given attribution | |
18 | * as the author of the parts of the library used. | |
19 | * This can be in the form of a textual message at program startup or | |
20 | * in documentation (online or textual) provided with the package. | |
0f113f3e | 21 | * |
d02b48c6 RE |
22 | * Redistribution and use in source and binary forms, with or without |
23 | * modification, are permitted provided that the following conditions | |
24 | * are met: | |
25 | * 1. Redistributions of source code must retain the copyright | |
26 | * notice, this list of conditions and the following disclaimer. | |
27 | * 2. Redistributions in binary form must reproduce the above copyright | |
28 | * notice, this list of conditions and the following disclaimer in the | |
29 | * documentation and/or other materials provided with the distribution. | |
30 | * 3. All advertising materials mentioning features or use of this software | |
31 | * must display the following acknowledgement: | |
32 | * "This product includes cryptographic software written by | |
33 | * Eric Young (eay@cryptsoft.com)" | |
34 | * The word 'cryptographic' can be left out if the rouines from the library | |
35 | * being used are not cryptographic related :-). | |
0f113f3e | 36 | * 4. If you include any Windows specific code (or a derivative thereof) from |
d02b48c6 RE |
37 | * the apps directory (application code) you must include an acknowledgement: |
38 | * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" | |
0f113f3e | 39 | * |
d02b48c6 RE |
40 | * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND |
41 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
42 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
43 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE | |
44 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |
45 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |
46 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |
47 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |
48 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |
49 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
50 | * SUCH DAMAGE. | |
0f113f3e | 51 | * |
d02b48c6 RE |
52 | * The licence and distribution terms for any publically available version or |
53 | * derivative of this code cannot be changed. i.e. this code cannot simply be | |
54 | * copied and put under another distribution licence | |
55 | * [including the GNU Public Licence.] | |
56 | */ | |
57 | ||
d86b6915 RL |
58 | /* Part of the code in here was originally in conf.c, which is now removed */ |
59 | ||
d02b48c6 | 60 | #include <stdio.h> |
9887c71c | 61 | #include <string.h> |
b39fc560 | 62 | #include "internal/cryptlib.h" |
ec577822 BM |
63 | #include <openssl/stack.h> |
64 | #include <openssl/lhash.h> | |
65 | #include <openssl/conf.h> | |
d86b6915 RL |
66 | #include <openssl/conf_api.h> |
67 | #include "conf_def.h" | |
ec577822 BM |
68 | #include <openssl/buffer.h> |
69 | #include <openssl/err.h> | |
d02b48c6 | 70 | |
d86b6915 RL |
71 | static char *eat_ws(CONF *conf, char *p); |
72 | static char *eat_alpha_numeric(CONF *conf, char *p); | |
73 | static void clear_comments(CONF *conf, char *p); | |
0f113f3e | 74 | static int str_copy(CONF *conf, char *section, char **to, char *from); |
d86b6915 RL |
75 | static char *scan_quote(CONF *conf, char *p); |
76 | static char *scan_dquote(CONF *conf, char *p); | |
0f113f3e | 77 | #define scan_esc(conf,p) (((IS_EOF((conf),(p)[1]))?((p)+1):((p)+2))) |
d86b6915 RL |
78 | |
79 | static CONF *def_create(CONF_METHOD *meth); | |
80 | static int def_init_default(CONF *conf); | |
81 | static int def_init_WIN32(CONF *conf); | |
82 | static int def_destroy(CONF *conf); | |
83 | static int def_destroy_data(CONF *conf); | |
befb3e7a RL |
84 | static int def_load(CONF *conf, const char *name, long *eline); |
85 | static int def_load_bio(CONF *conf, BIO *bp, long *eline); | |
9dd5ae65 BL |
86 | static int def_dump(const CONF *conf, BIO *bp); |
87 | static int def_is_number(const CONF *conf, char c); | |
88 | static int def_to_int(const CONF *conf, char c); | |
d86b6915 | 89 | |
d86b6915 | 90 | static CONF_METHOD default_method = { |
0f113f3e MC |
91 | "OpenSSL default", |
92 | def_create, | |
93 | def_init_default, | |
94 | def_destroy, | |
95 | def_destroy_data, | |
96 | def_load_bio, | |
97 | def_dump, | |
98 | def_is_number, | |
99 | def_to_int, | |
100 | def_load | |
101 | }; | |
d86b6915 RL |
102 | |
103 | static CONF_METHOD WIN32_method = { | |
0f113f3e MC |
104 | "WIN32", |
105 | def_create, | |
106 | def_init_WIN32, | |
107 | def_destroy, | |
108 | def_destroy_data, | |
109 | def_load_bio, | |
110 | def_dump, | |
111 | def_is_number, | |
112 | def_to_int, | |
113 | def_load | |
114 | }; | |
d86b6915 RL |
115 | |
116 | CONF_METHOD *NCONF_default() | |
0f113f3e MC |
117 | { |
118 | return &default_method; | |
119 | } | |
120 | ||
d86b6915 | 121 | CONF_METHOD *NCONF_WIN32() |
0f113f3e MC |
122 | { |
123 | return &WIN32_method; | |
124 | } | |
d02b48c6 | 125 | |
d86b6915 | 126 | static CONF *def_create(CONF_METHOD *meth) |
0f113f3e MC |
127 | { |
128 | CONF *ret; | |
129 | ||
b4faea50 | 130 | ret = OPENSSL_malloc(sizeof(*ret)); |
90945fa3 | 131 | if (ret != NULL) |
0f113f3e MC |
132 | if (meth->init(ret) == 0) { |
133 | OPENSSL_free(ret); | |
134 | ret = NULL; | |
135 | } | |
136 | return ret; | |
137 | } | |
138 | ||
d86b6915 | 139 | static int def_init_default(CONF *conf) |
0f113f3e MC |
140 | { |
141 | if (conf == NULL) | |
142 | return 0; | |
d86b6915 | 143 | |
0f113f3e MC |
144 | conf->meth = &default_method; |
145 | conf->meth_data = (void *)CONF_type_default; | |
146 | conf->data = NULL; | |
d02b48c6 | 147 | |
0f113f3e MC |
148 | return 1; |
149 | } | |
8623f693 | 150 | |
d86b6915 | 151 | static int def_init_WIN32(CONF *conf) |
0f113f3e MC |
152 | { |
153 | if (conf == NULL) | |
154 | return 0; | |
8623f693 | 155 | |
0f113f3e MC |
156 | conf->meth = &WIN32_method; |
157 | conf->meth_data = (void *)CONF_type_win32; | |
158 | conf->data = NULL; | |
d86b6915 | 159 | |
0f113f3e MC |
160 | return 1; |
161 | } | |
d86b6915 RL |
162 | |
163 | static int def_destroy(CONF *conf) | |
0f113f3e MC |
164 | { |
165 | if (def_destroy_data(conf)) { | |
166 | OPENSSL_free(conf); | |
167 | return 1; | |
168 | } | |
169 | return 0; | |
170 | } | |
8623f693 | 171 | |
d86b6915 | 172 | static int def_destroy_data(CONF *conf) |
0f113f3e MC |
173 | { |
174 | if (conf == NULL) | |
175 | return 0; | |
176 | _CONF_free_data(conf); | |
177 | return 1; | |
178 | } | |
8623f693 | 179 | |
befb3e7a | 180 | static int def_load(CONF *conf, const char *name, long *line) |
0f113f3e MC |
181 | { |
182 | int ret; | |
183 | BIO *in = NULL; | |
befb3e7a | 184 | |
bc36ee62 | 185 | #ifdef OPENSSL_SYS_VMS |
0f113f3e | 186 | in = BIO_new_file(name, "r"); |
befb3e7a | 187 | #else |
0f113f3e | 188 | in = BIO_new_file(name, "rb"); |
befb3e7a | 189 | #endif |
0f113f3e MC |
190 | if (in == NULL) { |
191 | if (ERR_GET_REASON(ERR_peek_last_error()) == BIO_R_NO_SUCH_FILE) | |
192 | CONFerr(CONF_F_DEF_LOAD, CONF_R_NO_SUCH_FILE); | |
193 | else | |
194 | CONFerr(CONF_F_DEF_LOAD, ERR_R_SYS_LIB); | |
195 | return 0; | |
196 | } | |
befb3e7a | 197 | |
0f113f3e MC |
198 | ret = def_load_bio(conf, in, line); |
199 | BIO_free(in); | |
befb3e7a | 200 | |
0f113f3e MC |
201 | return ret; |
202 | } | |
befb3e7a RL |
203 | |
204 | static int def_load_bio(CONF *conf, BIO *in, long *line) | |
0f113f3e | 205 | { |
6a89a25c | 206 | /* The macro BUFSIZE conflicts with a system macro in VxWorks */ |
0f113f3e MC |
207 | #define CONFBUFSIZE 512 |
208 | int bufnum = 0, i, ii; | |
209 | BUF_MEM *buff = NULL; | |
210 | char *s, *p, *end; | |
211 | int again; | |
212 | long eline = 0; | |
213 | char btmp[DECIMAL_SIZE(eline) + 1]; | |
214 | CONF_VALUE *v = NULL, *tv; | |
215 | CONF_VALUE *sv = NULL; | |
216 | char *section = NULL, *buf; | |
217 | char *start, *psection, *pname; | |
218 | void *h = (void *)(conf->data); | |
219 | ||
220 | if ((buff = BUF_MEM_new()) == NULL) { | |
221 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_BUF_LIB); | |
222 | goto err; | |
223 | } | |
224 | ||
7644a9ae | 225 | section = OPENSSL_strdup("default"); |
0f113f3e MC |
226 | if (section == NULL) { |
227 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE); | |
228 | goto err; | |
229 | } | |
0f113f3e MC |
230 | |
231 | if (_CONF_new_data(conf) == 0) { | |
232 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE); | |
233 | goto err; | |
234 | } | |
235 | ||
236 | sv = _CONF_new_section(conf, section); | |
237 | if (sv == NULL) { | |
238 | CONFerr(CONF_F_DEF_LOAD_BIO, CONF_R_UNABLE_TO_CREATE_NEW_SECTION); | |
239 | goto err; | |
240 | } | |
241 | ||
242 | bufnum = 0; | |
243 | again = 0; | |
244 | for (;;) { | |
245 | if (!BUF_MEM_grow(buff, bufnum + CONFBUFSIZE)) { | |
246 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_BUF_LIB); | |
247 | goto err; | |
248 | } | |
249 | p = &(buff->data[bufnum]); | |
250 | *p = '\0'; | |
251 | BIO_gets(in, p, CONFBUFSIZE - 1); | |
252 | p[CONFBUFSIZE - 1] = '\0'; | |
253 | ii = i = strlen(p); | |
254 | if (i == 0 && !again) | |
255 | break; | |
256 | again = 0; | |
257 | while (i > 0) { | |
258 | if ((p[i - 1] != '\r') && (p[i - 1] != '\n')) | |
259 | break; | |
260 | else | |
261 | i--; | |
262 | } | |
263 | /* | |
264 | * we removed some trailing stuff so there is a new line on the end. | |
265 | */ | |
266 | if (ii && i == ii) | |
267 | again = 1; /* long line */ | |
268 | else { | |
269 | p[i] = '\0'; | |
270 | eline++; /* another input line */ | |
271 | } | |
272 | ||
273 | /* we now have a line with trailing \r\n removed */ | |
274 | ||
275 | /* i is the number of bytes */ | |
276 | bufnum += i; | |
277 | ||
278 | v = NULL; | |
279 | /* check for line continuation */ | |
280 | if (bufnum >= 1) { | |
281 | /* | |
282 | * If we have bytes and the last char '\\' and second last char | |
283 | * is not '\\' | |
284 | */ | |
285 | p = &(buff->data[bufnum - 1]); | |
286 | if (IS_ESC(conf, p[0]) && ((bufnum <= 1) || !IS_ESC(conf, p[-1]))) { | |
287 | bufnum--; | |
288 | again = 1; | |
289 | } | |
290 | } | |
291 | if (again) | |
292 | continue; | |
293 | bufnum = 0; | |
294 | buf = buff->data; | |
295 | ||
296 | clear_comments(conf, buf); | |
297 | s = eat_ws(conf, buf); | |
298 | if (IS_EOF(conf, *s)) | |
299 | continue; /* blank line */ | |
300 | if (*s == '[') { | |
301 | char *ss; | |
302 | ||
303 | s++; | |
304 | start = eat_ws(conf, s); | |
305 | ss = start; | |
306 | again: | |
307 | end = eat_alpha_numeric(conf, ss); | |
308 | p = eat_ws(conf, end); | |
309 | if (*p != ']') { | |
310 | if (*p != '\0' && ss != p) { | |
311 | ss = p; | |
312 | goto again; | |
313 | } | |
314 | CONFerr(CONF_F_DEF_LOAD_BIO, | |
315 | CONF_R_MISSING_CLOSE_SQUARE_BRACKET); | |
316 | goto err; | |
317 | } | |
318 | *end = '\0'; | |
319 | if (!str_copy(conf, NULL, §ion, start)) | |
320 | goto err; | |
321 | if ((sv = _CONF_get_section(conf, section)) == NULL) | |
322 | sv = _CONF_new_section(conf, section); | |
323 | if (sv == NULL) { | |
324 | CONFerr(CONF_F_DEF_LOAD_BIO, | |
325 | CONF_R_UNABLE_TO_CREATE_NEW_SECTION); | |
326 | goto err; | |
327 | } | |
328 | continue; | |
329 | } else { | |
330 | pname = s; | |
331 | psection = NULL; | |
332 | end = eat_alpha_numeric(conf, s); | |
333 | if ((end[0] == ':') && (end[1] == ':')) { | |
334 | *end = '\0'; | |
335 | end += 2; | |
336 | psection = pname; | |
337 | pname = end; | |
338 | end = eat_alpha_numeric(conf, end); | |
339 | } | |
340 | p = eat_ws(conf, end); | |
341 | if (*p != '=') { | |
342 | CONFerr(CONF_F_DEF_LOAD_BIO, CONF_R_MISSING_EQUAL_SIGN); | |
343 | goto err; | |
344 | } | |
345 | *end = '\0'; | |
346 | p++; | |
347 | start = eat_ws(conf, p); | |
348 | while (!IS_EOF(conf, *p)) | |
349 | p++; | |
350 | p--; | |
351 | while ((p != start) && (IS_WS(conf, *p))) | |
352 | p--; | |
353 | p++; | |
354 | *p = '\0'; | |
355 | ||
75ebbd9a | 356 | if ((v = OPENSSL_malloc(sizeof(*v))) == NULL) { |
0f113f3e MC |
357 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE); |
358 | goto err; | |
359 | } | |
360 | if (psection == NULL) | |
361 | psection = section; | |
b196e7d9 | 362 | v->name = OPENSSL_malloc(strlen(pname) + 1); |
0f113f3e MC |
363 | v->value = NULL; |
364 | if (v->name == NULL) { | |
365 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE); | |
366 | goto err; | |
367 | } | |
7644a9ae | 368 | OPENSSL_strlcpy(v->name, pname, strlen(pname) + 1); |
0f113f3e MC |
369 | if (!str_copy(conf, psection, &(v->value), start)) |
370 | goto err; | |
371 | ||
372 | if (strcmp(psection, section) != 0) { | |
373 | if ((tv = _CONF_get_section(conf, psection)) | |
374 | == NULL) | |
375 | tv = _CONF_new_section(conf, psection); | |
376 | if (tv == NULL) { | |
377 | CONFerr(CONF_F_DEF_LOAD_BIO, | |
378 | CONF_R_UNABLE_TO_CREATE_NEW_SECTION); | |
379 | goto err; | |
380 | } | |
381 | } else | |
382 | tv = sv; | |
0f113f3e MC |
383 | if (_CONF_add_string(conf, tv, v) == 0) { |
384 | CONFerr(CONF_F_DEF_LOAD_BIO, ERR_R_MALLOC_FAILURE); | |
385 | goto err; | |
386 | } | |
0f113f3e MC |
387 | v = NULL; |
388 | } | |
389 | } | |
25aaa98a | 390 | BUF_MEM_free(buff); |
b548a1f1 | 391 | OPENSSL_free(section); |
0f113f3e MC |
392 | return (1); |
393 | err: | |
25aaa98a | 394 | BUF_MEM_free(buff); |
b548a1f1 | 395 | OPENSSL_free(section); |
0f113f3e MC |
396 | if (line != NULL) |
397 | *line = eline; | |
398 | BIO_snprintf(btmp, sizeof btmp, "%ld", eline); | |
399 | ERR_add_error_data(2, "line ", btmp); | |
25aaa98a | 400 | if (h != conf->data) { |
0f113f3e MC |
401 | CONF_free(conf->data); |
402 | conf->data = NULL; | |
403 | } | |
404 | if (v != NULL) { | |
b548a1f1 RS |
405 | OPENSSL_free(v->name); |
406 | OPENSSL_free(v->value); | |
407 | OPENSSL_free(v); | |
0f113f3e MC |
408 | } |
409 | return (0); | |
410 | } | |
8623f693 | 411 | |
d86b6915 | 412 | static void clear_comments(CONF *conf, char *p) |
0f113f3e MC |
413 | { |
414 | for (;;) { | |
415 | if (IS_FCOMMENT(conf, *p)) { | |
416 | *p = '\0'; | |
417 | return; | |
418 | } | |
419 | if (!IS_WS(conf, *p)) { | |
420 | break; | |
421 | } | |
422 | p++; | |
423 | } | |
424 | ||
425 | for (;;) { | |
426 | if (IS_COMMENT(conf, *p)) { | |
427 | *p = '\0'; | |
428 | return; | |
429 | } | |
430 | if (IS_DQUOTE(conf, *p)) { | |
431 | p = scan_dquote(conf, p); | |
432 | continue; | |
433 | } | |
434 | if (IS_QUOTE(conf, *p)) { | |
435 | p = scan_quote(conf, p); | |
436 | continue; | |
437 | } | |
438 | if (IS_ESC(conf, *p)) { | |
439 | p = scan_esc(conf, p); | |
440 | continue; | |
441 | } | |
442 | if (IS_EOF(conf, *p)) | |
443 | return; | |
444 | else | |
445 | p++; | |
446 | } | |
447 | } | |
d02b48c6 | 448 | |
d86b6915 | 449 | static int str_copy(CONF *conf, char *section, char **pto, char *from) |
0f113f3e MC |
450 | { |
451 | int q, r, rr = 0, to = 0, len = 0; | |
452 | char *s, *e, *rp, *p, *rrp, *np, *cp, v; | |
453 | BUF_MEM *buf; | |
454 | ||
455 | if ((buf = BUF_MEM_new()) == NULL) | |
456 | return (0); | |
457 | ||
458 | len = strlen(from) + 1; | |
459 | if (!BUF_MEM_grow(buf, len)) | |
460 | goto err; | |
461 | ||
462 | for (;;) { | |
463 | if (IS_QUOTE(conf, *from)) { | |
464 | q = *from; | |
465 | from++; | |
466 | while (!IS_EOF(conf, *from) && (*from != q)) { | |
467 | if (IS_ESC(conf, *from)) { | |
468 | from++; | |
469 | if (IS_EOF(conf, *from)) | |
470 | break; | |
471 | } | |
472 | buf->data[to++] = *(from++); | |
473 | } | |
474 | if (*from == q) | |
475 | from++; | |
476 | } else if (IS_DQUOTE(conf, *from)) { | |
477 | q = *from; | |
478 | from++; | |
479 | while (!IS_EOF(conf, *from)) { | |
480 | if (*from == q) { | |
481 | if (*(from + 1) == q) { | |
482 | from++; | |
483 | } else { | |
484 | break; | |
485 | } | |
486 | } | |
487 | buf->data[to++] = *(from++); | |
488 | } | |
489 | if (*from == q) | |
490 | from++; | |
491 | } else if (IS_ESC(conf, *from)) { | |
492 | from++; | |
493 | v = *(from++); | |
494 | if (IS_EOF(conf, v)) | |
495 | break; | |
496 | else if (v == 'r') | |
497 | v = '\r'; | |
498 | else if (v == 'n') | |
499 | v = '\n'; | |
500 | else if (v == 'b') | |
501 | v = '\b'; | |
502 | else if (v == 't') | |
503 | v = '\t'; | |
504 | buf->data[to++] = v; | |
505 | } else if (IS_EOF(conf, *from)) | |
506 | break; | |
507 | else if (*from == '$') { | |
508 | /* try to expand it */ | |
509 | rrp = NULL; | |
510 | s = &(from[1]); | |
511 | if (*s == '{') | |
512 | q = '}'; | |
513 | else if (*s == '(') | |
514 | q = ')'; | |
515 | else | |
516 | q = 0; | |
517 | ||
518 | if (q) | |
519 | s++; | |
520 | cp = section; | |
521 | e = np = s; | |
522 | while (IS_ALPHA_NUMERIC(conf, *e)) | |
523 | e++; | |
524 | if ((e[0] == ':') && (e[1] == ':')) { | |
525 | cp = np; | |
526 | rrp = e; | |
527 | rr = *e; | |
528 | *rrp = '\0'; | |
529 | e += 2; | |
530 | np = e; | |
531 | while (IS_ALPHA_NUMERIC(conf, *e)) | |
532 | e++; | |
533 | } | |
534 | r = *e; | |
535 | *e = '\0'; | |
536 | rp = e; | |
537 | if (q) { | |
538 | if (r != q) { | |
539 | CONFerr(CONF_F_STR_COPY, CONF_R_NO_CLOSE_BRACE); | |
540 | goto err; | |
541 | } | |
542 | e++; | |
543 | } | |
50e735f9 MC |
544 | /*- |
545 | * So at this point we have | |
546 | * np which is the start of the name string which is | |
547 | * '\0' terminated. | |
548 | * cp which is the start of the section string which is | |
549 | * '\0' terminated. | |
550 | * e is the 'next point after'. | |
551 | * r and rr are the chars replaced by the '\0' | |
552 | * rp and rrp is where 'r' and 'rr' came from. | |
553 | */ | |
0f113f3e MC |
554 | p = _CONF_get_string(conf, cp, np); |
555 | if (rrp != NULL) | |
556 | *rrp = rr; | |
557 | *rp = r; | |
558 | if (p == NULL) { | |
559 | CONFerr(CONF_F_STR_COPY, CONF_R_VARIABLE_HAS_NO_VALUE); | |
560 | goto err; | |
561 | } | |
b0333e69 GP |
562 | if (!BUF_MEM_grow_clean(buf, |
563 | (strlen(p) + buf->length - (e - from)))) { | |
564 | CONFerr(CONF_F_STR_COPY, ERR_R_MALLOC_FAILURE); | |
565 | goto err; | |
566 | } | |
0f113f3e MC |
567 | while (*p) |
568 | buf->data[to++] = *(p++); | |
569 | ||
570 | /* | |
571 | * Since we change the pointer 'from', we also have to change the | |
572 | * perceived length of the string it points at. /RL | |
573 | */ | |
574 | len -= e - from; | |
575 | from = e; | |
576 | ||
577 | /* | |
578 | * In case there were no braces or parenthesis around the | |
579 | * variable reference, we have to put back the character that was | |
580 | * replaced with a '\0'. /RL | |
581 | */ | |
582 | *rp = r; | |
583 | } else | |
584 | buf->data[to++] = *(from++); | |
585 | } | |
586 | buf->data[to] = '\0'; | |
b548a1f1 | 587 | OPENSSL_free(*pto); |
0f113f3e MC |
588 | *pto = buf->data; |
589 | OPENSSL_free(buf); | |
590 | return (1); | |
591 | err: | |
25aaa98a | 592 | BUF_MEM_free(buf); |
0f113f3e MC |
593 | return (0); |
594 | } | |
d02b48c6 | 595 | |
d86b6915 | 596 | static char *eat_ws(CONF *conf, char *p) |
0f113f3e MC |
597 | { |
598 | while (IS_WS(conf, *p) && (!IS_EOF(conf, *p))) | |
599 | p++; | |
600 | return (p); | |
601 | } | |
d02b48c6 | 602 | |
d86b6915 | 603 | static char *eat_alpha_numeric(CONF *conf, char *p) |
0f113f3e MC |
604 | { |
605 | for (;;) { | |
606 | if (IS_ESC(conf, *p)) { | |
607 | p = scan_esc(conf, p); | |
608 | continue; | |
609 | } | |
610 | if (!IS_ALPHA_NUMERIC_PUNCT(conf, *p)) | |
611 | return (p); | |
612 | p++; | |
613 | } | |
614 | } | |
d02b48c6 | 615 | |
d86b6915 | 616 | static char *scan_quote(CONF *conf, char *p) |
0f113f3e MC |
617 | { |
618 | int q = *p; | |
619 | ||
620 | p++; | |
621 | while (!(IS_EOF(conf, *p)) && (*p != q)) { | |
622 | if (IS_ESC(conf, *p)) { | |
623 | p++; | |
624 | if (IS_EOF(conf, *p)) | |
625 | return (p); | |
626 | } | |
627 | p++; | |
628 | } | |
629 | if (*p == q) | |
630 | p++; | |
631 | return (p); | |
632 | } | |
d86b6915 RL |
633 | |
634 | static char *scan_dquote(CONF *conf, char *p) | |
0f113f3e MC |
635 | { |
636 | int q = *p; | |
637 | ||
638 | p++; | |
639 | while (!(IS_EOF(conf, *p))) { | |
640 | if (*p == q) { | |
641 | if (*(p + 1) == q) { | |
642 | p++; | |
643 | } else { | |
644 | break; | |
645 | } | |
646 | } | |
647 | p++; | |
648 | } | |
649 | if (*p == q) | |
650 | p++; | |
651 | return (p); | |
652 | } | |
d02b48c6 | 653 | |
2a056de8 | 654 | static void dump_value_doall_arg(const CONF_VALUE *a, BIO *out) |
0f113f3e MC |
655 | { |
656 | if (a->name) | |
657 | BIO_printf(out, "[%s] %s=%s\n", a->section, a->name, a->value); | |
658 | else | |
659 | BIO_printf(out, "[[%s]]\n", a->section); | |
660 | } | |
d86b6915 | 661 | |
2a056de8 | 662 | IMPLEMENT_LHASH_DOALL_ARG_CONST(CONF_VALUE, BIO); |
3c914840 | 663 | |
9dd5ae65 | 664 | static int def_dump(const CONF *conf, BIO *out) |
0f113f3e | 665 | { |
2a056de8 | 666 | lh_CONF_VALUE_doall_BIO(conf->data, dump_value_doall_arg, out); |
0f113f3e MC |
667 | return 1; |
668 | } | |
d02b48c6 | 669 | |
9dd5ae65 | 670 | static int def_is_number(const CONF *conf, char c) |
0f113f3e MC |
671 | { |
672 | return IS_NUMBER(conf, c); | |
673 | } | |
d02b48c6 | 674 | |
9dd5ae65 | 675 | static int def_to_int(const CONF *conf, char c) |
0f113f3e MC |
676 | { |
677 | return c - '0'; | |
678 | } |