Coverage Report

Created: 2022-11-30 06:20

/src/openssl/crypto/conf/conf_lib.c
Line
Count
Source (jump to first uncovered line)
1
/* conf_lib.c */
2
/*
3
 * Written by Richard Levitte (richard@levitte.org) for the OpenSSL project
4
 * 2000.
5
 */
6
/* ====================================================================
7
 * Copyright (c) 2000 The OpenSSL Project.  All rights reserved.
8
 *
9
 * Redistribution and use in source and binary forms, with or without
10
 * modification, are permitted provided that the following conditions
11
 * are met:
12
 *
13
 * 1. Redistributions of source code must retain the above copyright
14
 *    notice, this list of conditions and the following disclaimer.
15
 *
16
 * 2. Redistributions in binary form must reproduce the above copyright
17
 *    notice, this list of conditions and the following disclaimer in
18
 *    the documentation and/or other materials provided with the
19
 *    distribution.
20
 *
21
 * 3. All advertising materials mentioning features or use of this
22
 *    software must display the following acknowledgment:
23
 *    "This product includes software developed by the OpenSSL Project
24
 *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
25
 *
26
 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
27
 *    endorse or promote products derived from this software without
28
 *    prior written permission. For written permission, please contact
29
 *    licensing@OpenSSL.org.
30
 *
31
 * 5. Products derived from this software may not be called "OpenSSL"
32
 *    nor may "OpenSSL" appear in their names without prior written
33
 *    permission of the OpenSSL Project.
34
 *
35
 * 6. Redistributions of any form whatsoever must retain the following
36
 *    acknowledgment:
37
 *    "This product includes software developed by the OpenSSL Project
38
 *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
39
 *
40
 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
41
 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
43
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
44
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
45
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
46
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
47
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
49
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
50
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
51
 * OF THE POSSIBILITY OF SUCH DAMAGE.
52
 * ====================================================================
53
 *
54
 * This product includes cryptographic software written by Eric Young
55
 * (eay@cryptsoft.com).  This product includes software written by Tim
56
 * Hudson (tjh@cryptsoft.com).
57
 *
58
 */
59
60
#include <stdio.h>
61
#include <openssl/crypto.h>
62
#include <openssl/err.h>
63
#include <openssl/conf.h>
64
#include <openssl/conf_api.h>
65
#include <openssl/lhash.h>
66
67
const char CONF_version[] = "CONF" OPENSSL_VERSION_PTEXT;
68
69
static CONF_METHOD *default_CONF_method = NULL;
70
71
/* Init a 'CONF' structure from an old LHASH */
72
73
void CONF_set_nconf(CONF *conf, LHASH_OF(CONF_VALUE) *hash)
74
0
{
75
0
    if (default_CONF_method == NULL)
76
0
        default_CONF_method = NCONF_default();
77
78
0
    default_CONF_method->init(conf);
79
0
    conf->data = hash;
80
0
}
81
82
/*
83
 * The following section contains the "CONF classic" functions, rewritten in
84
 * terms of the new CONF interface.
85
 */
86
87
int CONF_set_default_method(CONF_METHOD *meth)
88
0
{
89
0
    default_CONF_method = meth;
90
0
    return 1;
91
0
}
92
93
LHASH_OF(CONF_VALUE) *CONF_load(LHASH_OF(CONF_VALUE) *conf, const char *file,
94
                                long *eline)
95
0
{
96
0
    LHASH_OF(CONF_VALUE) *ltmp;
97
0
    BIO *in = NULL;
98
99
#ifdef OPENSSL_SYS_VMS
100
    in = BIO_new_file(file, "r");
101
#else
102
0
    in = BIO_new_file(file, "rb");
103
0
#endif
104
0
    if (in == NULL) {
105
0
        CONFerr(CONF_F_CONF_LOAD, ERR_R_SYS_LIB);
106
0
        return NULL;
107
0
    }
108
109
0
    ltmp = CONF_load_bio(conf, in, eline);
110
0
    BIO_free(in);
111
112
0
    return ltmp;
113
0
}
114
115
#ifndef OPENSSL_NO_FP_API
116
LHASH_OF(CONF_VALUE) *CONF_load_fp(LHASH_OF(CONF_VALUE) *conf, FILE *fp,
117
                                   long *eline)
118
0
{
119
0
    BIO *btmp;
120
0
    LHASH_OF(CONF_VALUE) *ltmp;
121
0
    if (!(btmp = BIO_new_fp(fp, BIO_NOCLOSE))) {
122
0
        CONFerr(CONF_F_CONF_LOAD_FP, ERR_R_BUF_LIB);
123
0
        return NULL;
124
0
    }
125
0
    ltmp = CONF_load_bio(conf, btmp, eline);
126
0
    BIO_free(btmp);
127
0
    return ltmp;
128
0
}
129
#endif
130
131
LHASH_OF(CONF_VALUE) *CONF_load_bio(LHASH_OF(CONF_VALUE) *conf, BIO *bp,
132
                                    long *eline)
133
0
{
134
0
    CONF ctmp;
135
0
    int ret;
136
137
0
    CONF_set_nconf(&ctmp, conf);
138
139
0
    ret = NCONF_load_bio(&ctmp, bp, eline);
140
0
    if (ret)
141
0
        return ctmp.data;
142
0
    return NULL;
143
0
}
144
145
STACK_OF(CONF_VALUE) *CONF_get_section(LHASH_OF(CONF_VALUE) *conf,
146
                                       const char *section)
147
0
{
148
0
    if (conf == NULL) {
149
0
        return NULL;
150
0
    } else {
151
0
        CONF ctmp;
152
0
        CONF_set_nconf(&ctmp, conf);
153
0
        return NCONF_get_section(&ctmp, section);
154
0
    }
155
0
}
156
157
char *CONF_get_string(LHASH_OF(CONF_VALUE) *conf, const char *group,
158
                      const char *name)
159
0
{
160
0
    if (conf == NULL) {
161
0
        return NCONF_get_string(NULL, group, name);
162
0
    } else {
163
0
        CONF ctmp;
164
0
        CONF_set_nconf(&ctmp, conf);
165
0
        return NCONF_get_string(&ctmp, group, name);
166
0
    }
167
0
}
168
169
long CONF_get_number(LHASH_OF(CONF_VALUE) *conf, const char *group,
170
                     const char *name)
171
0
{
172
0
    int status;
173
0
    long result = 0;
174
175
0
    if (conf == NULL) {
176
0
        status = NCONF_get_number_e(NULL, group, name, &result);
177
0
    } else {
178
0
        CONF ctmp;
179
0
        CONF_set_nconf(&ctmp, conf);
180
0
        status = NCONF_get_number_e(&ctmp, group, name, &result);
181
0
    }
182
183
0
    if (status == 0) {
184
        /* This function does not believe in errors... */
185
0
        ERR_clear_error();
186
0
    }
187
0
    return result;
188
0
}
189
190
void CONF_free(LHASH_OF(CONF_VALUE) *conf)
191
0
{
192
0
    CONF ctmp;
193
0
    CONF_set_nconf(&ctmp, conf);
194
0
    NCONF_free_data(&ctmp);
195
0
}
196
197
#ifndef OPENSSL_NO_FP_API
198
int CONF_dump_fp(LHASH_OF(CONF_VALUE) *conf, FILE *out)
199
0
{
200
0
    BIO *btmp;
201
0
    int ret;
202
203
0
    if (!(btmp = BIO_new_fp(out, BIO_NOCLOSE))) {
204
0
        CONFerr(CONF_F_CONF_DUMP_FP, ERR_R_BUF_LIB);
205
0
        return 0;
206
0
    }
207
0
    ret = CONF_dump_bio(conf, btmp);
208
0
    BIO_free(btmp);
209
0
    return ret;
210
0
}
211
#endif
212
213
int CONF_dump_bio(LHASH_OF(CONF_VALUE) *conf, BIO *out)
214
0
{
215
0
    CONF ctmp;
216
0
    CONF_set_nconf(&ctmp, conf);
217
0
    return NCONF_dump_bio(&ctmp, out);
218
0
}
219
220
/*
221
 * The following section contains the "New CONF" functions.  They are
222
 * completely centralised around a new CONF structure that may contain
223
 * basically anything, but at least a method pointer and a table of data.
224
 * These functions are also written in terms of the bridge functions used by
225
 * the "CONF classic" functions, for consistency.
226
 */
227
228
CONF *NCONF_new(CONF_METHOD *meth)
229
19
{
230
19
    CONF *ret;
231
232
19
    if (meth == NULL)
233
19
        meth = NCONF_default();
234
235
19
    ret = meth->create(meth);
236
19
    if (ret == NULL) {
237
0
        CONFerr(CONF_F_NCONF_NEW, ERR_R_MALLOC_FAILURE);
238
0
        return (NULL);
239
0
    }
240
241
19
    return ret;
242
19
}
243
244
void NCONF_free(CONF *conf)
245
19
{
246
19
    if (conf == NULL)
247
0
        return;
248
19
    conf->meth->destroy(conf);
249
19
}
250
251
void NCONF_free_data(CONF *conf)
252
0
{
253
0
    if (conf == NULL)
254
0
        return;
255
0
    conf->meth->destroy_data(conf);
256
0
}
257
258
int NCONF_load(CONF *conf, const char *file, long *eline)
259
19
{
260
19
    if (conf == NULL) {
261
0
        CONFerr(CONF_F_NCONF_LOAD, CONF_R_NO_CONF);
262
0
        return 0;
263
0
    }
264
265
19
    return conf->meth->load(conf, file, eline);
266
19
}
267
268
#ifndef OPENSSL_NO_FP_API
269
int NCONF_load_fp(CONF *conf, FILE *fp, long *eline)
270
0
{
271
0
    BIO *btmp;
272
0
    int ret;
273
0
    if (!(btmp = BIO_new_fp(fp, BIO_NOCLOSE))) {
274
0
        CONFerr(CONF_F_NCONF_LOAD_FP, ERR_R_BUF_LIB);
275
0
        return 0;
276
0
    }
277
0
    ret = NCONF_load_bio(conf, btmp, eline);
278
0
    BIO_free(btmp);
279
0
    return ret;
280
0
}
281
#endif
282
283
int NCONF_load_bio(CONF *conf, BIO *bp, long *eline)
284
0
{
285
0
    if (conf == NULL) {
286
0
        CONFerr(CONF_F_NCONF_LOAD_BIO, CONF_R_NO_CONF);
287
0
        return 0;
288
0
    }
289
290
0
    return conf->meth->load_bio(conf, bp, eline);
291
0
}
292
293
STACK_OF(CONF_VALUE) *NCONF_get_section(const CONF *conf, const char *section)
294
0
{
295
0
    if (conf == NULL) {
296
0
        CONFerr(CONF_F_NCONF_GET_SECTION, CONF_R_NO_CONF);
297
0
        return NULL;
298
0
    }
299
300
0
    if (section == NULL) {
301
0
        CONFerr(CONF_F_NCONF_GET_SECTION, CONF_R_NO_SECTION);
302
0
        return NULL;
303
0
    }
304
305
0
    return _CONF_get_section_values(conf, section);
306
0
}
307
308
char *NCONF_get_string(const CONF *conf, const char *group, const char *name)
309
0
{
310
0
    char *s = _CONF_get_string(conf, group, name);
311
312
    /*
313
     * Since we may get a value from an environment variable even if conf is
314
     * NULL, let's check the value first
315
     */
316
0
    if (s)
317
0
        return s;
318
319
0
    if (conf == NULL) {
320
0
        CONFerr(CONF_F_NCONF_GET_STRING,
321
0
                CONF_R_NO_CONF_OR_ENVIRONMENT_VARIABLE);
322
0
        return NULL;
323
0
    }
324
0
    CONFerr(CONF_F_NCONF_GET_STRING, CONF_R_NO_VALUE);
325
0
    ERR_add_error_data(4, "group=", group, " name=", name);
326
0
    return NULL;
327
0
}
328
329
int NCONF_get_number_e(const CONF *conf, const char *group, const char *name,
330
                       long *result)
331
0
{
332
0
    char *str;
333
334
0
    if (result == NULL) {
335
0
        CONFerr(CONF_F_NCONF_GET_NUMBER_E, ERR_R_PASSED_NULL_PARAMETER);
336
0
        return 0;
337
0
    }
338
339
0
    str = NCONF_get_string(conf, group, name);
340
341
0
    if (str == NULL)
342
0
        return 0;
343
344
0
    for (*result = 0; conf->meth->is_number(conf, *str);) {
345
0
        *result = (*result) * 10 + conf->meth->to_int(conf, *str);
346
0
        str++;
347
0
    }
348
349
0
    return 1;
350
0
}
351
352
#ifndef OPENSSL_NO_FP_API
353
int NCONF_dump_fp(const CONF *conf, FILE *out)
354
0
{
355
0
    BIO *btmp;
356
0
    int ret;
357
0
    if (!(btmp = BIO_new_fp(out, BIO_NOCLOSE))) {
358
0
        CONFerr(CONF_F_NCONF_DUMP_FP, ERR_R_BUF_LIB);
359
0
        return 0;
360
0
    }
361
0
    ret = NCONF_dump_bio(conf, btmp);
362
0
    BIO_free(btmp);
363
0
    return ret;
364
0
}
365
#endif
366
367
int NCONF_dump_bio(const CONF *conf, BIO *out)
368
0
{
369
0
    if (conf == NULL) {
370
0
        CONFerr(CONF_F_NCONF_DUMP_BIO, CONF_R_NO_CONF);
371
0
        return 0;
372
0
    }
373
374
0
    return conf->meth->dump(conf, out);
375
0
}
376
377
/* This function should be avoided */
378
#if 0
379
long NCONF_get_number(CONF *conf, char *group, char *name)
380
{
381
    int status;
382
    long ret = 0;
383
384
    status = NCONF_get_number_e(conf, group, name, &ret);
385
    if (status == 0) {
386
        /* This function does not believe in errors... */
387
        ERR_get_error();
388
    }
389
    return ret;
390
}
391
#endif