xref: /freebsd/crypto/openssl/ssl/ssl_conf.c (revision e71b70530d95c4f34d8bdbd78d1242df1ba4a945)
17bded2dbSJung-uk Kim /*
2*e71b7053SJung-uk Kim  * Copyright 2012-2018 The OpenSSL Project Authors. All Rights Reserved.
37bded2dbSJung-uk Kim  *
4*e71b7053SJung-uk Kim  * Licensed under the OpenSSL license (the "License").  You may not use
5*e71b7053SJung-uk Kim  * this file except in compliance with the License.  You can obtain a copy
6*e71b7053SJung-uk Kim  * in the file LICENSE in the source distribution or at
7*e71b7053SJung-uk Kim  * https://www.openssl.org/source/license.html
87bded2dbSJung-uk Kim  */
97bded2dbSJung-uk Kim 
107bded2dbSJung-uk Kim #include <stdio.h>
117bded2dbSJung-uk Kim #include "ssl_locl.h"
127bded2dbSJung-uk Kim #include <openssl/conf.h>
137bded2dbSJung-uk Kim #include <openssl/objects.h>
147bded2dbSJung-uk Kim #include <openssl/dh.h>
15*e71b7053SJung-uk Kim #include "internal/nelem.h"
167bded2dbSJung-uk Kim 
177bded2dbSJung-uk Kim /*
18*e71b7053SJung-uk Kim  * structure holding name tables. This is used for permitted elements in lists
19*e71b7053SJung-uk Kim  * such as TLSv1.
207bded2dbSJung-uk Kim  */
217bded2dbSJung-uk Kim 
227bded2dbSJung-uk Kim typedef struct {
237bded2dbSJung-uk Kim     const char *name;
247bded2dbSJung-uk Kim     int namelen;
257bded2dbSJung-uk Kim     unsigned int name_flags;
267bded2dbSJung-uk Kim     unsigned long option_value;
277bded2dbSJung-uk Kim } ssl_flag_tbl;
287bded2dbSJung-uk Kim 
29*e71b7053SJung-uk Kim /* Switch table: use for single command line switches like no_tls2 */
30*e71b7053SJung-uk Kim typedef struct {
31*e71b7053SJung-uk Kim     unsigned long option_value;
32*e71b7053SJung-uk Kim     unsigned int name_flags;
33*e71b7053SJung-uk Kim } ssl_switch_tbl;
34*e71b7053SJung-uk Kim 
357bded2dbSJung-uk Kim /* Sense of name is inverted e.g. "TLSv1" will clear SSL_OP_NO_TLSv1 */
367bded2dbSJung-uk Kim #define SSL_TFLAG_INV   0x1
37*e71b7053SJung-uk Kim /* Mask for type of flag referred to */
38*e71b7053SJung-uk Kim #define SSL_TFLAG_TYPE_MASK 0xf00
39*e71b7053SJung-uk Kim /* Flag is for options */
40*e71b7053SJung-uk Kim #define SSL_TFLAG_OPTION    0x000
41*e71b7053SJung-uk Kim /* Flag is for cert_flags */
42*e71b7053SJung-uk Kim #define SSL_TFLAG_CERT      0x100
43*e71b7053SJung-uk Kim /* Flag is for verify mode */
44*e71b7053SJung-uk Kim #define SSL_TFLAG_VFY       0x200
457bded2dbSJung-uk Kim /* Option can only be used for clients */
467bded2dbSJung-uk Kim #define SSL_TFLAG_CLIENT SSL_CONF_FLAG_CLIENT
477bded2dbSJung-uk Kim /* Option can only be used for servers */
487bded2dbSJung-uk Kim #define SSL_TFLAG_SERVER SSL_CONF_FLAG_SERVER
497bded2dbSJung-uk Kim #define SSL_TFLAG_BOTH (SSL_TFLAG_CLIENT|SSL_TFLAG_SERVER)
507bded2dbSJung-uk Kim 
517bded2dbSJung-uk Kim #define SSL_FLAG_TBL(str, flag) \
527bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_BOTH, flag}
537bded2dbSJung-uk Kim #define SSL_FLAG_TBL_SRV(str, flag) \
547bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_SERVER, flag}
557bded2dbSJung-uk Kim #define SSL_FLAG_TBL_CLI(str, flag) \
567bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_CLIENT, flag}
577bded2dbSJung-uk Kim #define SSL_FLAG_TBL_INV(str, flag) \
587bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_INV|SSL_TFLAG_BOTH, flag}
597bded2dbSJung-uk Kim #define SSL_FLAG_TBL_SRV_INV(str, flag) \
607bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_INV|SSL_TFLAG_SERVER, flag}
617bded2dbSJung-uk Kim #define SSL_FLAG_TBL_CERT(str, flag) \
627bded2dbSJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_CERT|SSL_TFLAG_BOTH, flag}
637bded2dbSJung-uk Kim 
64*e71b7053SJung-uk Kim #define SSL_FLAG_VFY_CLI(str, flag) \
65*e71b7053SJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_VFY | SSL_TFLAG_CLIENT, flag}
66*e71b7053SJung-uk Kim #define SSL_FLAG_VFY_SRV(str, flag) \
67*e71b7053SJung-uk Kim         {str, (int)(sizeof(str) - 1), SSL_TFLAG_VFY | SSL_TFLAG_SERVER, flag}
68*e71b7053SJung-uk Kim 
697bded2dbSJung-uk Kim /*
707bded2dbSJung-uk Kim  * Opaque structure containing SSL configuration context.
717bded2dbSJung-uk Kim  */
727bded2dbSJung-uk Kim 
737bded2dbSJung-uk Kim struct ssl_conf_ctx_st {
747bded2dbSJung-uk Kim     /*
757bded2dbSJung-uk Kim      * Various flags indicating (among other things) which options we will
767bded2dbSJung-uk Kim      * recognise.
777bded2dbSJung-uk Kim      */
787bded2dbSJung-uk Kim     unsigned int flags;
797bded2dbSJung-uk Kim     /* Prefix and length of commands */
807bded2dbSJung-uk Kim     char *prefix;
817bded2dbSJung-uk Kim     size_t prefixlen;
827bded2dbSJung-uk Kim     /* SSL_CTX or SSL structure to perform operations on */
837bded2dbSJung-uk Kim     SSL_CTX *ctx;
847bded2dbSJung-uk Kim     SSL *ssl;
857bded2dbSJung-uk Kim     /* Pointer to SSL or SSL_CTX options field or NULL if none */
86*e71b7053SJung-uk Kim     uint32_t *poptions;
87*e71b7053SJung-uk Kim     /* Certificate filenames for each type */
88*e71b7053SJung-uk Kim     char *cert_filename[SSL_PKEY_NUM];
897bded2dbSJung-uk Kim     /* Pointer to SSL or SSL_CTX cert_flags or NULL if none */
90*e71b7053SJung-uk Kim     uint32_t *pcert_flags;
91*e71b7053SJung-uk Kim     /* Pointer to SSL or SSL_CTX verify_mode or NULL if none */
92*e71b7053SJung-uk Kim     uint32_t *pvfy_flags;
93*e71b7053SJung-uk Kim     /* Pointer to SSL or SSL_CTX min_version field or NULL if none */
94*e71b7053SJung-uk Kim     int *min_version;
95*e71b7053SJung-uk Kim     /* Pointer to SSL or SSL_CTX max_version field or NULL if none */
96*e71b7053SJung-uk Kim     int *max_version;
977bded2dbSJung-uk Kim     /* Current flag table being worked on */
987bded2dbSJung-uk Kim     const ssl_flag_tbl *tbl;
997bded2dbSJung-uk Kim     /* Size of table */
1007bded2dbSJung-uk Kim     size_t ntbl;
101*e71b7053SJung-uk Kim     /* Client CA names */
102*e71b7053SJung-uk Kim     STACK_OF(X509_NAME) *canames;
1037bded2dbSJung-uk Kim };
1047bded2dbSJung-uk Kim 
105*e71b7053SJung-uk Kim static void ssl_set_option(SSL_CONF_CTX *cctx, unsigned int name_flags,
106*e71b7053SJung-uk Kim                            unsigned long option_value, int onoff)
107*e71b7053SJung-uk Kim {
108*e71b7053SJung-uk Kim     uint32_t *pflags;
109*e71b7053SJung-uk Kim     if (cctx->poptions == NULL)
110*e71b7053SJung-uk Kim         return;
111*e71b7053SJung-uk Kim     if (name_flags & SSL_TFLAG_INV)
112*e71b7053SJung-uk Kim         onoff ^= 1;
113*e71b7053SJung-uk Kim     switch (name_flags & SSL_TFLAG_TYPE_MASK) {
114*e71b7053SJung-uk Kim 
115*e71b7053SJung-uk Kim     case SSL_TFLAG_CERT:
116*e71b7053SJung-uk Kim         pflags = cctx->pcert_flags;
117*e71b7053SJung-uk Kim         break;
118*e71b7053SJung-uk Kim 
119*e71b7053SJung-uk Kim     case SSL_TFLAG_VFY:
120*e71b7053SJung-uk Kim         pflags = cctx->pvfy_flags;
121*e71b7053SJung-uk Kim         break;
122*e71b7053SJung-uk Kim 
123*e71b7053SJung-uk Kim     case SSL_TFLAG_OPTION:
124*e71b7053SJung-uk Kim         pflags = cctx->poptions;
125*e71b7053SJung-uk Kim         break;
126*e71b7053SJung-uk Kim 
127*e71b7053SJung-uk Kim     default:
128*e71b7053SJung-uk Kim         return;
129*e71b7053SJung-uk Kim 
130*e71b7053SJung-uk Kim     }
131*e71b7053SJung-uk Kim     if (onoff)
132*e71b7053SJung-uk Kim         *pflags |= option_value;
133*e71b7053SJung-uk Kim     else
134*e71b7053SJung-uk Kim         *pflags &= ~option_value;
135*e71b7053SJung-uk Kim }
136*e71b7053SJung-uk Kim 
1377bded2dbSJung-uk Kim static int ssl_match_option(SSL_CONF_CTX *cctx, const ssl_flag_tbl *tbl,
1387bded2dbSJung-uk Kim                             const char *name, int namelen, int onoff)
1397bded2dbSJung-uk Kim {
1407bded2dbSJung-uk Kim     /* If name not relevant for context skip */
1417bded2dbSJung-uk Kim     if (!(cctx->flags & tbl->name_flags & SSL_TFLAG_BOTH))
1427bded2dbSJung-uk Kim         return 0;
1437bded2dbSJung-uk Kim     if (namelen == -1) {
1447bded2dbSJung-uk Kim         if (strcmp(tbl->name, name))
1457bded2dbSJung-uk Kim             return 0;
146*e71b7053SJung-uk Kim     } else if (tbl->namelen != namelen || strncasecmp(tbl->name, name, namelen))
1477bded2dbSJung-uk Kim         return 0;
148*e71b7053SJung-uk Kim     ssl_set_option(cctx, tbl->name_flags, tbl->option_value, onoff);
1497bded2dbSJung-uk Kim     return 1;
1507bded2dbSJung-uk Kim }
1517bded2dbSJung-uk Kim 
1527bded2dbSJung-uk Kim static int ssl_set_option_list(const char *elem, int len, void *usr)
1537bded2dbSJung-uk Kim {
1547bded2dbSJung-uk Kim     SSL_CONF_CTX *cctx = usr;
1557bded2dbSJung-uk Kim     size_t i;
1567bded2dbSJung-uk Kim     const ssl_flag_tbl *tbl;
1577bded2dbSJung-uk Kim     int onoff = 1;
1587bded2dbSJung-uk Kim     /*
1597bded2dbSJung-uk Kim      * len == -1 indicates not being called in list context, just for single
1607bded2dbSJung-uk Kim      * command line switches, so don't allow +, -.
1617bded2dbSJung-uk Kim      */
1627bded2dbSJung-uk Kim     if (elem == NULL)
1637bded2dbSJung-uk Kim         return 0;
1647bded2dbSJung-uk Kim     if (len != -1) {
1657bded2dbSJung-uk Kim         if (*elem == '+') {
1667bded2dbSJung-uk Kim             elem++;
1677bded2dbSJung-uk Kim             len--;
1687bded2dbSJung-uk Kim             onoff = 1;
1697bded2dbSJung-uk Kim         } else if (*elem == '-') {
1707bded2dbSJung-uk Kim             elem++;
1717bded2dbSJung-uk Kim             len--;
1727bded2dbSJung-uk Kim             onoff = 0;
1737bded2dbSJung-uk Kim         }
1747bded2dbSJung-uk Kim     }
1757bded2dbSJung-uk Kim     for (i = 0, tbl = cctx->tbl; i < cctx->ntbl; i++, tbl++) {
1767bded2dbSJung-uk Kim         if (ssl_match_option(cctx, tbl, elem, len, onoff))
1777bded2dbSJung-uk Kim             return 1;
1787bded2dbSJung-uk Kim     }
1797bded2dbSJung-uk Kim     return 0;
1807bded2dbSJung-uk Kim }
1817bded2dbSJung-uk Kim 
1827bded2dbSJung-uk Kim /* Set supported signature algorithms */
1837bded2dbSJung-uk Kim static int cmd_SignatureAlgorithms(SSL_CONF_CTX *cctx, const char *value)
1847bded2dbSJung-uk Kim {
1857bded2dbSJung-uk Kim     int rv;
1867bded2dbSJung-uk Kim     if (cctx->ssl)
1877bded2dbSJung-uk Kim         rv = SSL_set1_sigalgs_list(cctx->ssl, value);
1887bded2dbSJung-uk Kim     /* NB: ctx == NULL performs syntax checking only */
1897bded2dbSJung-uk Kim     else
1907bded2dbSJung-uk Kim         rv = SSL_CTX_set1_sigalgs_list(cctx->ctx, value);
1917bded2dbSJung-uk Kim     return rv > 0;
1927bded2dbSJung-uk Kim }
1937bded2dbSJung-uk Kim 
1947bded2dbSJung-uk Kim /* Set supported client signature algorithms */
195*e71b7053SJung-uk Kim static int cmd_ClientSignatureAlgorithms(SSL_CONF_CTX *cctx, const char *value)
1967bded2dbSJung-uk Kim {
1977bded2dbSJung-uk Kim     int rv;
1987bded2dbSJung-uk Kim     if (cctx->ssl)
1997bded2dbSJung-uk Kim         rv = SSL_set1_client_sigalgs_list(cctx->ssl, value);
2007bded2dbSJung-uk Kim     /* NB: ctx == NULL performs syntax checking only */
2017bded2dbSJung-uk Kim     else
2027bded2dbSJung-uk Kim         rv = SSL_CTX_set1_client_sigalgs_list(cctx->ctx, value);
2037bded2dbSJung-uk Kim     return rv > 0;
2047bded2dbSJung-uk Kim }
2057bded2dbSJung-uk Kim 
206*e71b7053SJung-uk Kim static int cmd_Groups(SSL_CONF_CTX *cctx, const char *value)
2077bded2dbSJung-uk Kim {
2087bded2dbSJung-uk Kim     int rv;
2097bded2dbSJung-uk Kim     if (cctx->ssl)
210*e71b7053SJung-uk Kim         rv = SSL_set1_groups_list(cctx->ssl, value);
2117bded2dbSJung-uk Kim     /* NB: ctx == NULL performs syntax checking only */
2127bded2dbSJung-uk Kim     else
213*e71b7053SJung-uk Kim         rv = SSL_CTX_set1_groups_list(cctx->ctx, value);
2147bded2dbSJung-uk Kim     return rv > 0;
2157bded2dbSJung-uk Kim }
2167bded2dbSJung-uk Kim 
217*e71b7053SJung-uk Kim /* This is the old name for cmd_Groups - retained for backwards compatibility */
218*e71b7053SJung-uk Kim static int cmd_Curves(SSL_CONF_CTX *cctx, const char *value)
219*e71b7053SJung-uk Kim {
220*e71b7053SJung-uk Kim     return cmd_Groups(cctx, value);
221*e71b7053SJung-uk Kim }
222*e71b7053SJung-uk Kim 
223*e71b7053SJung-uk Kim #ifndef OPENSSL_NO_EC
2247bded2dbSJung-uk Kim /* ECDH temporary parameters */
2257bded2dbSJung-uk Kim static int cmd_ECDHParameters(SSL_CONF_CTX *cctx, const char *value)
2267bded2dbSJung-uk Kim {
227*e71b7053SJung-uk Kim     int rv = 1;
2287bded2dbSJung-uk Kim     EC_KEY *ecdh;
2297bded2dbSJung-uk Kim     int nid;
230*e71b7053SJung-uk Kim 
231*e71b7053SJung-uk Kim     /* Ignore values supported by 1.0.2 for the automatic selection */
232*e71b7053SJung-uk Kim     if ((cctx->flags & SSL_CONF_FLAG_FILE)
233*e71b7053SJung-uk Kim             && (strcasecmp(value, "+automatic") == 0
234*e71b7053SJung-uk Kim                 || strcasecmp(value, "automatic") == 0))
235*e71b7053SJung-uk Kim         return 1;
236*e71b7053SJung-uk Kim     if ((cctx->flags & SSL_CONF_FLAG_CMDLINE) &&
237*e71b7053SJung-uk Kim         strcmp(value, "auto") == 0)
238*e71b7053SJung-uk Kim         return 1;
239*e71b7053SJung-uk Kim 
2407bded2dbSJung-uk Kim     nid = EC_curve_nist2nid(value);
2417bded2dbSJung-uk Kim     if (nid == NID_undef)
2427bded2dbSJung-uk Kim         nid = OBJ_sn2nid(value);
2437bded2dbSJung-uk Kim     if (nid == 0)
2447bded2dbSJung-uk Kim         return 0;
2457bded2dbSJung-uk Kim     ecdh = EC_KEY_new_by_curve_name(nid);
2467bded2dbSJung-uk Kim     if (!ecdh)
2477bded2dbSJung-uk Kim         return 0;
2487bded2dbSJung-uk Kim     if (cctx->ctx)
2497bded2dbSJung-uk Kim         rv = SSL_CTX_set_tmp_ecdh(cctx->ctx, ecdh);
2507bded2dbSJung-uk Kim     else if (cctx->ssl)
2517bded2dbSJung-uk Kim         rv = SSL_set_tmp_ecdh(cctx->ssl, ecdh);
2527bded2dbSJung-uk Kim     EC_KEY_free(ecdh);
2537bded2dbSJung-uk Kim 
2547bded2dbSJung-uk Kim     return rv > 0;
2557bded2dbSJung-uk Kim }
2567bded2dbSJung-uk Kim #endif
2577bded2dbSJung-uk Kim static int cmd_CipherString(SSL_CONF_CTX *cctx, const char *value)
2587bded2dbSJung-uk Kim {
2597bded2dbSJung-uk Kim     int rv = 1;
260*e71b7053SJung-uk Kim 
2617bded2dbSJung-uk Kim     if (cctx->ctx)
2627bded2dbSJung-uk Kim         rv = SSL_CTX_set_cipher_list(cctx->ctx, value);
2637bded2dbSJung-uk Kim     if (cctx->ssl)
2647bded2dbSJung-uk Kim         rv = SSL_set_cipher_list(cctx->ssl, value);
2657bded2dbSJung-uk Kim     return rv > 0;
2667bded2dbSJung-uk Kim }
2677bded2dbSJung-uk Kim 
268*e71b7053SJung-uk Kim static int cmd_Ciphersuites(SSL_CONF_CTX *cctx, const char *value)
269*e71b7053SJung-uk Kim {
270*e71b7053SJung-uk Kim     int rv = 1;
271*e71b7053SJung-uk Kim 
272*e71b7053SJung-uk Kim     if (cctx->ctx)
273*e71b7053SJung-uk Kim         rv = SSL_CTX_set_ciphersuites(cctx->ctx, value);
274*e71b7053SJung-uk Kim     if (cctx->ssl)
275*e71b7053SJung-uk Kim         rv = SSL_set_ciphersuites(cctx->ssl, value);
276*e71b7053SJung-uk Kim     return rv > 0;
277*e71b7053SJung-uk Kim }
278*e71b7053SJung-uk Kim 
2797bded2dbSJung-uk Kim static int cmd_Protocol(SSL_CONF_CTX *cctx, const char *value)
2807bded2dbSJung-uk Kim {
2817bded2dbSJung-uk Kim     static const ssl_flag_tbl ssl_protocol_list[] = {
2827bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("ALL", SSL_OP_NO_SSL_MASK),
2837bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("SSLv2", SSL_OP_NO_SSLv2),
2847bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("SSLv3", SSL_OP_NO_SSLv3),
2857bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("TLSv1", SSL_OP_NO_TLSv1),
2867bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("TLSv1.1", SSL_OP_NO_TLSv1_1),
287*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("TLSv1.2", SSL_OP_NO_TLSv1_2),
288*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("TLSv1.3", SSL_OP_NO_TLSv1_3),
289*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("DTLSv1", SSL_OP_NO_DTLSv1),
290*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("DTLSv1.2", SSL_OP_NO_DTLSv1_2)
2917bded2dbSJung-uk Kim     };
2927bded2dbSJung-uk Kim     cctx->tbl = ssl_protocol_list;
293*e71b7053SJung-uk Kim     cctx->ntbl = OSSL_NELEM(ssl_protocol_list);
294*e71b7053SJung-uk Kim     return CONF_parse_list(value, ',', 1, ssl_set_option_list, cctx);
295*e71b7053SJung-uk Kim }
2964c6a0400SJung-uk Kim 
297*e71b7053SJung-uk Kim /*
298*e71b7053SJung-uk Kim  * protocol_from_string - converts a protocol version string to a number
299*e71b7053SJung-uk Kim  *
300*e71b7053SJung-uk Kim  * Returns -1 on failure or the version on success
301*e71b7053SJung-uk Kim  */
302*e71b7053SJung-uk Kim static int protocol_from_string(const char *value)
303*e71b7053SJung-uk Kim {
304*e71b7053SJung-uk Kim     struct protocol_versions {
305*e71b7053SJung-uk Kim         const char *name;
306*e71b7053SJung-uk Kim         int version;
307*e71b7053SJung-uk Kim     };
308*e71b7053SJung-uk Kim     static const struct protocol_versions versions[] = {
309*e71b7053SJung-uk Kim         {"None", 0},
310*e71b7053SJung-uk Kim         {"SSLv3", SSL3_VERSION},
311*e71b7053SJung-uk Kim         {"TLSv1", TLS1_VERSION},
312*e71b7053SJung-uk Kim         {"TLSv1.1", TLS1_1_VERSION},
313*e71b7053SJung-uk Kim         {"TLSv1.2", TLS1_2_VERSION},
314*e71b7053SJung-uk Kim         {"TLSv1.3", TLS1_3_VERSION},
315*e71b7053SJung-uk Kim         {"DTLSv1", DTLS1_VERSION},
316*e71b7053SJung-uk Kim         {"DTLSv1.2", DTLS1_2_VERSION}
317*e71b7053SJung-uk Kim     };
318*e71b7053SJung-uk Kim     size_t i;
319*e71b7053SJung-uk Kim     size_t n = OSSL_NELEM(versions);
320*e71b7053SJung-uk Kim 
321*e71b7053SJung-uk Kim     for (i = 0; i < n; i++)
322*e71b7053SJung-uk Kim         if (strcmp(versions[i].name, value) == 0)
323*e71b7053SJung-uk Kim             return versions[i].version;
324*e71b7053SJung-uk Kim     return -1;
325*e71b7053SJung-uk Kim }
326*e71b7053SJung-uk Kim 
327*e71b7053SJung-uk Kim static int min_max_proto(SSL_CONF_CTX *cctx, const char *value, int *bound)
328*e71b7053SJung-uk Kim {
329*e71b7053SJung-uk Kim     int method_version;
330*e71b7053SJung-uk Kim     int new_version;
331*e71b7053SJung-uk Kim 
332*e71b7053SJung-uk Kim     if (cctx->ctx != NULL)
333*e71b7053SJung-uk Kim         method_version = cctx->ctx->method->version;
334*e71b7053SJung-uk Kim     else if (cctx->ssl != NULL)
335*e71b7053SJung-uk Kim         method_version = cctx->ssl->ctx->method->version;
336*e71b7053SJung-uk Kim     else
337*e71b7053SJung-uk Kim         return 0;
338*e71b7053SJung-uk Kim     if ((new_version = protocol_from_string(value)) < 0)
339*e71b7053SJung-uk Kim         return 0;
340*e71b7053SJung-uk Kim     return ssl_set_version_bound(method_version, new_version, bound);
341*e71b7053SJung-uk Kim }
342*e71b7053SJung-uk Kim 
343*e71b7053SJung-uk Kim /*
344*e71b7053SJung-uk Kim  * cmd_MinProtocol - Set min protocol version
345*e71b7053SJung-uk Kim  * @cctx: config structure to save settings in
346*e71b7053SJung-uk Kim  * @value: The min protocol version in string form
347*e71b7053SJung-uk Kim  *
348*e71b7053SJung-uk Kim  * Returns 1 on success and 0 on failure.
349*e71b7053SJung-uk Kim  */
350*e71b7053SJung-uk Kim static int cmd_MinProtocol(SSL_CONF_CTX *cctx, const char *value)
351*e71b7053SJung-uk Kim {
352*e71b7053SJung-uk Kim     return min_max_proto(cctx, value, cctx->min_version);
353*e71b7053SJung-uk Kim }
354*e71b7053SJung-uk Kim 
355*e71b7053SJung-uk Kim /*
356*e71b7053SJung-uk Kim  * cmd_MaxProtocol - Set max protocol version
357*e71b7053SJung-uk Kim  * @cctx: config structure to save settings in
358*e71b7053SJung-uk Kim  * @value: The max protocol version in string form
359*e71b7053SJung-uk Kim  *
360*e71b7053SJung-uk Kim  * Returns 1 on success and 0 on failure.
361*e71b7053SJung-uk Kim  */
362*e71b7053SJung-uk Kim static int cmd_MaxProtocol(SSL_CONF_CTX *cctx, const char *value)
363*e71b7053SJung-uk Kim {
364*e71b7053SJung-uk Kim     return min_max_proto(cctx, value, cctx->max_version);
3657bded2dbSJung-uk Kim }
3667bded2dbSJung-uk Kim 
3677bded2dbSJung-uk Kim static int cmd_Options(SSL_CONF_CTX *cctx, const char *value)
3687bded2dbSJung-uk Kim {
3697bded2dbSJung-uk Kim     static const ssl_flag_tbl ssl_option_list[] = {
3707bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("SessionTicket", SSL_OP_NO_TICKET),
3717bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("EmptyFragments",
3727bded2dbSJung-uk Kim                          SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS),
3737bded2dbSJung-uk Kim         SSL_FLAG_TBL("Bugs", SSL_OP_ALL),
3747bded2dbSJung-uk Kim         SSL_FLAG_TBL_INV("Compression", SSL_OP_NO_COMPRESSION),
3757bded2dbSJung-uk Kim         SSL_FLAG_TBL_SRV("ServerPreference", SSL_OP_CIPHER_SERVER_PREFERENCE),
3767bded2dbSJung-uk Kim         SSL_FLAG_TBL_SRV("NoResumptionOnRenegotiation",
3777bded2dbSJung-uk Kim                          SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION),
3787bded2dbSJung-uk Kim         SSL_FLAG_TBL_SRV("DHSingle", SSL_OP_SINGLE_DH_USE),
3797bded2dbSJung-uk Kim         SSL_FLAG_TBL_SRV("ECDHSingle", SSL_OP_SINGLE_ECDH_USE),
3807bded2dbSJung-uk Kim         SSL_FLAG_TBL("UnsafeLegacyRenegotiation",
3817bded2dbSJung-uk Kim                      SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION),
382*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("EncryptThenMac", SSL_OP_NO_ENCRYPT_THEN_MAC),
383*e71b7053SJung-uk Kim         SSL_FLAG_TBL("NoRenegotiation", SSL_OP_NO_RENEGOTIATION),
384*e71b7053SJung-uk Kim         SSL_FLAG_TBL("AllowNoDHEKEX", SSL_OP_ALLOW_NO_DHE_KEX),
385*e71b7053SJung-uk Kim         SSL_FLAG_TBL("PrioritizeChaCha", SSL_OP_PRIORITIZE_CHACHA),
386*e71b7053SJung-uk Kim         SSL_FLAG_TBL("MiddleboxCompat", SSL_OP_ENABLE_MIDDLEBOX_COMPAT),
387*e71b7053SJung-uk Kim         SSL_FLAG_TBL_INV("AntiReplay", SSL_OP_NO_ANTI_REPLAY)
3887bded2dbSJung-uk Kim     };
3897bded2dbSJung-uk Kim     if (value == NULL)
3907bded2dbSJung-uk Kim         return -3;
3917bded2dbSJung-uk Kim     cctx->tbl = ssl_option_list;
392*e71b7053SJung-uk Kim     cctx->ntbl = OSSL_NELEM(ssl_option_list);
393*e71b7053SJung-uk Kim     return CONF_parse_list(value, ',', 1, ssl_set_option_list, cctx);
394*e71b7053SJung-uk Kim }
395*e71b7053SJung-uk Kim 
396*e71b7053SJung-uk Kim static int cmd_VerifyMode(SSL_CONF_CTX *cctx, const char *value)
397*e71b7053SJung-uk Kim {
398*e71b7053SJung-uk Kim     static const ssl_flag_tbl ssl_vfy_list[] = {
399*e71b7053SJung-uk Kim         SSL_FLAG_VFY_CLI("Peer", SSL_VERIFY_PEER),
400*e71b7053SJung-uk Kim         SSL_FLAG_VFY_SRV("Request", SSL_VERIFY_PEER),
401*e71b7053SJung-uk Kim         SSL_FLAG_VFY_SRV("Require",
402*e71b7053SJung-uk Kim                          SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT),
403*e71b7053SJung-uk Kim         SSL_FLAG_VFY_SRV("Once", SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE),
404*e71b7053SJung-uk Kim         SSL_FLAG_VFY_SRV("RequestPostHandshake",
405*e71b7053SJung-uk Kim                          SSL_VERIFY_PEER | SSL_VERIFY_POST_HANDSHAKE),
406*e71b7053SJung-uk Kim         SSL_FLAG_VFY_SRV("RequirePostHandshake",
407*e71b7053SJung-uk Kim                          SSL_VERIFY_PEER | SSL_VERIFY_POST_HANDSHAKE |
408*e71b7053SJung-uk Kim                          SSL_VERIFY_FAIL_IF_NO_PEER_CERT),
409*e71b7053SJung-uk Kim     };
410*e71b7053SJung-uk Kim     if (value == NULL)
411*e71b7053SJung-uk Kim         return -3;
412*e71b7053SJung-uk Kim     cctx->tbl = ssl_vfy_list;
413*e71b7053SJung-uk Kim     cctx->ntbl = OSSL_NELEM(ssl_vfy_list);
4147bded2dbSJung-uk Kim     return CONF_parse_list(value, ',', 1, ssl_set_option_list, cctx);
4157bded2dbSJung-uk Kim }
4167bded2dbSJung-uk Kim 
4177bded2dbSJung-uk Kim static int cmd_Certificate(SSL_CONF_CTX *cctx, const char *value)
4187bded2dbSJung-uk Kim {
4197bded2dbSJung-uk Kim     int rv = 1;
420*e71b7053SJung-uk Kim     CERT *c = NULL;
421*e71b7053SJung-uk Kim     if (cctx->ctx) {
4227bded2dbSJung-uk Kim         rv = SSL_CTX_use_certificate_chain_file(cctx->ctx, value);
423*e71b7053SJung-uk Kim         c = cctx->ctx->cert;
424*e71b7053SJung-uk Kim     }
425*e71b7053SJung-uk Kim     if (cctx->ssl) {
426*e71b7053SJung-uk Kim         rv = SSL_use_certificate_chain_file(cctx->ssl, value);
427*e71b7053SJung-uk Kim         c = cctx->ssl->cert;
428*e71b7053SJung-uk Kim     }
429*e71b7053SJung-uk Kim     if (rv > 0 && c && cctx->flags & SSL_CONF_FLAG_REQUIRE_PRIVATE) {
430*e71b7053SJung-uk Kim         char **pfilename = &cctx->cert_filename[c->key - c->pkeys];
431*e71b7053SJung-uk Kim         OPENSSL_free(*pfilename);
432*e71b7053SJung-uk Kim         *pfilename = OPENSSL_strdup(value);
433*e71b7053SJung-uk Kim         if (!*pfilename)
434*e71b7053SJung-uk Kim             rv = 0;
435*e71b7053SJung-uk Kim     }
436*e71b7053SJung-uk Kim 
4377bded2dbSJung-uk Kim     return rv > 0;
4387bded2dbSJung-uk Kim }
4397bded2dbSJung-uk Kim 
4407bded2dbSJung-uk Kim static int cmd_PrivateKey(SSL_CONF_CTX *cctx, const char *value)
4417bded2dbSJung-uk Kim {
4427bded2dbSJung-uk Kim     int rv = 1;
4437bded2dbSJung-uk Kim     if (!(cctx->flags & SSL_CONF_FLAG_CERTIFICATE))
4447bded2dbSJung-uk Kim         return -2;
4457bded2dbSJung-uk Kim     if (cctx->ctx)
4467bded2dbSJung-uk Kim         rv = SSL_CTX_use_PrivateKey_file(cctx->ctx, value, SSL_FILETYPE_PEM);
4477bded2dbSJung-uk Kim     if (cctx->ssl)
4487bded2dbSJung-uk Kim         rv = SSL_use_PrivateKey_file(cctx->ssl, value, SSL_FILETYPE_PEM);
4497bded2dbSJung-uk Kim     return rv > 0;
4507bded2dbSJung-uk Kim }
4517bded2dbSJung-uk Kim 
4527bded2dbSJung-uk Kim static int cmd_ServerInfoFile(SSL_CONF_CTX *cctx, const char *value)
4537bded2dbSJung-uk Kim {
4547bded2dbSJung-uk Kim     int rv = 1;
4557bded2dbSJung-uk Kim     if (cctx->ctx)
4567bded2dbSJung-uk Kim         rv = SSL_CTX_use_serverinfo_file(cctx->ctx, value);
4577bded2dbSJung-uk Kim     return rv > 0;
4587bded2dbSJung-uk Kim }
4597bded2dbSJung-uk Kim 
460*e71b7053SJung-uk Kim static int do_store(SSL_CONF_CTX *cctx,
461*e71b7053SJung-uk Kim                     const char *CAfile, const char *CApath, int verify_store)
462*e71b7053SJung-uk Kim {
463*e71b7053SJung-uk Kim     CERT *cert;
464*e71b7053SJung-uk Kim     X509_STORE **st;
465*e71b7053SJung-uk Kim     if (cctx->ctx)
466*e71b7053SJung-uk Kim         cert = cctx->ctx->cert;
467*e71b7053SJung-uk Kim     else if (cctx->ssl)
468*e71b7053SJung-uk Kim         cert = cctx->ssl->cert;
469*e71b7053SJung-uk Kim     else
470*e71b7053SJung-uk Kim         return 1;
471*e71b7053SJung-uk Kim     st = verify_store ? &cert->verify_store : &cert->chain_store;
472*e71b7053SJung-uk Kim     if (*st == NULL) {
473*e71b7053SJung-uk Kim         *st = X509_STORE_new();
474*e71b7053SJung-uk Kim         if (*st == NULL)
475*e71b7053SJung-uk Kim             return 0;
476*e71b7053SJung-uk Kim     }
477*e71b7053SJung-uk Kim     return X509_STORE_load_locations(*st, CAfile, CApath) > 0;
478*e71b7053SJung-uk Kim }
479*e71b7053SJung-uk Kim 
480*e71b7053SJung-uk Kim static int cmd_ChainCAPath(SSL_CONF_CTX *cctx, const char *value)
481*e71b7053SJung-uk Kim {
482*e71b7053SJung-uk Kim     return do_store(cctx, NULL, value, 0);
483*e71b7053SJung-uk Kim }
484*e71b7053SJung-uk Kim 
485*e71b7053SJung-uk Kim static int cmd_ChainCAFile(SSL_CONF_CTX *cctx, const char *value)
486*e71b7053SJung-uk Kim {
487*e71b7053SJung-uk Kim     return do_store(cctx, value, NULL, 0);
488*e71b7053SJung-uk Kim }
489*e71b7053SJung-uk Kim 
490*e71b7053SJung-uk Kim static int cmd_VerifyCAPath(SSL_CONF_CTX *cctx, const char *value)
491*e71b7053SJung-uk Kim {
492*e71b7053SJung-uk Kim     return do_store(cctx, NULL, value, 1);
493*e71b7053SJung-uk Kim }
494*e71b7053SJung-uk Kim 
495*e71b7053SJung-uk Kim static int cmd_VerifyCAFile(SSL_CONF_CTX *cctx, const char *value)
496*e71b7053SJung-uk Kim {
497*e71b7053SJung-uk Kim     return do_store(cctx, value, NULL, 1);
498*e71b7053SJung-uk Kim }
499*e71b7053SJung-uk Kim 
500*e71b7053SJung-uk Kim static int cmd_RequestCAFile(SSL_CONF_CTX *cctx, const char *value)
501*e71b7053SJung-uk Kim {
502*e71b7053SJung-uk Kim     if (cctx->canames == NULL)
503*e71b7053SJung-uk Kim         cctx->canames = sk_X509_NAME_new_null();
504*e71b7053SJung-uk Kim     if (cctx->canames == NULL)
505*e71b7053SJung-uk Kim         return 0;
506*e71b7053SJung-uk Kim     return SSL_add_file_cert_subjects_to_stack(cctx->canames, value);
507*e71b7053SJung-uk Kim }
508*e71b7053SJung-uk Kim 
509*e71b7053SJung-uk Kim static int cmd_ClientCAFile(SSL_CONF_CTX *cctx, const char *value)
510*e71b7053SJung-uk Kim {
511*e71b7053SJung-uk Kim     return cmd_RequestCAFile(cctx, value);
512*e71b7053SJung-uk Kim }
513*e71b7053SJung-uk Kim 
514*e71b7053SJung-uk Kim static int cmd_RequestCAPath(SSL_CONF_CTX *cctx, const char *value)
515*e71b7053SJung-uk Kim {
516*e71b7053SJung-uk Kim     if (cctx->canames == NULL)
517*e71b7053SJung-uk Kim         cctx->canames = sk_X509_NAME_new_null();
518*e71b7053SJung-uk Kim     if (cctx->canames == NULL)
519*e71b7053SJung-uk Kim         return 0;
520*e71b7053SJung-uk Kim     return SSL_add_dir_cert_subjects_to_stack(cctx->canames, value);
521*e71b7053SJung-uk Kim }
522*e71b7053SJung-uk Kim 
523*e71b7053SJung-uk Kim static int cmd_ClientCAPath(SSL_CONF_CTX *cctx, const char *value)
524*e71b7053SJung-uk Kim {
525*e71b7053SJung-uk Kim     return cmd_RequestCAPath(cctx, value);
526*e71b7053SJung-uk Kim }
527*e71b7053SJung-uk Kim 
5287bded2dbSJung-uk Kim #ifndef OPENSSL_NO_DH
5297bded2dbSJung-uk Kim static int cmd_DHParameters(SSL_CONF_CTX *cctx, const char *value)
5307bded2dbSJung-uk Kim {
5317bded2dbSJung-uk Kim     int rv = 0;
5327bded2dbSJung-uk Kim     DH *dh = NULL;
5337bded2dbSJung-uk Kim     BIO *in = NULL;
5347bded2dbSJung-uk Kim     if (cctx->ctx || cctx->ssl) {
535*e71b7053SJung-uk Kim         in = BIO_new(BIO_s_file());
536*e71b7053SJung-uk Kim         if (in == NULL)
5377bded2dbSJung-uk Kim             goto end;
5387bded2dbSJung-uk Kim         if (BIO_read_filename(in, value) <= 0)
5397bded2dbSJung-uk Kim             goto end;
5407bded2dbSJung-uk Kim         dh = PEM_read_bio_DHparams(in, NULL, NULL, NULL);
541*e71b7053SJung-uk Kim         if (dh == NULL)
5427bded2dbSJung-uk Kim             goto end;
5437bded2dbSJung-uk Kim     } else
5447bded2dbSJung-uk Kim         return 1;
5457bded2dbSJung-uk Kim     if (cctx->ctx)
5467bded2dbSJung-uk Kim         rv = SSL_CTX_set_tmp_dh(cctx->ctx, dh);
5477bded2dbSJung-uk Kim     if (cctx->ssl)
5487bded2dbSJung-uk Kim         rv = SSL_set_tmp_dh(cctx->ssl, dh);
5497bded2dbSJung-uk Kim  end:
5507bded2dbSJung-uk Kim     DH_free(dh);
5517bded2dbSJung-uk Kim     BIO_free(in);
5527bded2dbSJung-uk Kim     return rv > 0;
5537bded2dbSJung-uk Kim }
5547bded2dbSJung-uk Kim #endif
555*e71b7053SJung-uk Kim 
556*e71b7053SJung-uk Kim static int cmd_RecordPadding(SSL_CONF_CTX *cctx, const char *value)
557*e71b7053SJung-uk Kim {
558*e71b7053SJung-uk Kim     int rv = 0;
559*e71b7053SJung-uk Kim     int block_size = atoi(value);
560*e71b7053SJung-uk Kim 
561*e71b7053SJung-uk Kim     /*
562*e71b7053SJung-uk Kim      * All we care about is a non-negative value,
563*e71b7053SJung-uk Kim      * the setters check the range
564*e71b7053SJung-uk Kim      */
565*e71b7053SJung-uk Kim     if (block_size >= 0) {
566*e71b7053SJung-uk Kim         if (cctx->ctx)
567*e71b7053SJung-uk Kim             rv = SSL_CTX_set_block_padding(cctx->ctx, block_size);
568*e71b7053SJung-uk Kim         if (cctx->ssl)
569*e71b7053SJung-uk Kim             rv = SSL_set_block_padding(cctx->ssl, block_size);
570*e71b7053SJung-uk Kim     }
571*e71b7053SJung-uk Kim     return rv;
572*e71b7053SJung-uk Kim }
573*e71b7053SJung-uk Kim 
574*e71b7053SJung-uk Kim 
575*e71b7053SJung-uk Kim static int cmd_NumTickets(SSL_CONF_CTX *cctx, const char *value)
576*e71b7053SJung-uk Kim {
577*e71b7053SJung-uk Kim     int rv = 0;
578*e71b7053SJung-uk Kim     int num_tickets = atoi(value);
579*e71b7053SJung-uk Kim 
580*e71b7053SJung-uk Kim     if (num_tickets >= 0) {
581*e71b7053SJung-uk Kim         if (cctx->ctx)
582*e71b7053SJung-uk Kim             rv = SSL_CTX_set_num_tickets(cctx->ctx, num_tickets);
583*e71b7053SJung-uk Kim         if (cctx->ssl)
584*e71b7053SJung-uk Kim             rv = SSL_set_num_tickets(cctx->ssl, num_tickets);
585*e71b7053SJung-uk Kim     }
586*e71b7053SJung-uk Kim     return rv;
587*e71b7053SJung-uk Kim }
588*e71b7053SJung-uk Kim 
5897bded2dbSJung-uk Kim typedef struct {
5907bded2dbSJung-uk Kim     int (*cmd) (SSL_CONF_CTX *cctx, const char *value);
5917bded2dbSJung-uk Kim     const char *str_file;
5927bded2dbSJung-uk Kim     const char *str_cmdline;
593*e71b7053SJung-uk Kim     unsigned short flags;
594*e71b7053SJung-uk Kim     unsigned short value_type;
5957bded2dbSJung-uk Kim } ssl_conf_cmd_tbl;
5967bded2dbSJung-uk Kim 
5977bded2dbSJung-uk Kim /* Table of supported parameters */
5987bded2dbSJung-uk Kim 
599*e71b7053SJung-uk Kim #define SSL_CONF_CMD(name, cmdopt, flags, type) \
600*e71b7053SJung-uk Kim         {cmd_##name, #name, cmdopt, flags, type}
6017bded2dbSJung-uk Kim 
602*e71b7053SJung-uk Kim #define SSL_CONF_CMD_STRING(name, cmdopt, flags) \
603*e71b7053SJung-uk Kim         SSL_CONF_CMD(name, cmdopt, flags, SSL_CONF_TYPE_STRING)
6047bded2dbSJung-uk Kim 
605*e71b7053SJung-uk Kim #define SSL_CONF_CMD_SWITCH(name, flags) \
606*e71b7053SJung-uk Kim         {0, NULL, name, flags, SSL_CONF_TYPE_NONE}
607*e71b7053SJung-uk Kim 
608*e71b7053SJung-uk Kim /* See apps/apps.h if you change this table. */
6097bded2dbSJung-uk Kim static const ssl_conf_cmd_tbl ssl_conf_cmds[] = {
610*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_ssl3", 0),
611*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_tls1", 0),
612*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_tls1_1", 0),
613*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_tls1_2", 0),
614*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_tls1_3", 0),
615*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("bugs", 0),
616*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_comp", 0),
617*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("comp", 0),
618*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("ecdh_single", SSL_CONF_FLAG_SERVER),
619*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_ticket", 0),
620*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("serverpref", SSL_CONF_FLAG_SERVER),
621*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("legacy_renegotiation", 0),
622*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("legacy_server_connect", SSL_CONF_FLAG_SERVER),
623*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_renegotiation", 0),
624*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_resumption_on_reneg", SSL_CONF_FLAG_SERVER),
625*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_legacy_server_connect", SSL_CONF_FLAG_SERVER),
626*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("allow_no_dhe_kex", 0),
627*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("prioritize_chacha", SSL_CONF_FLAG_SERVER),
628*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("strict", 0),
629*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_middlebox", 0),
630*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("anti_replay", SSL_CONF_FLAG_SERVER),
631*e71b7053SJung-uk Kim     SSL_CONF_CMD_SWITCH("no_anti_replay", SSL_CONF_FLAG_SERVER),
632*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(SignatureAlgorithms, "sigalgs", 0),
633*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(ClientSignatureAlgorithms, "client_sigalgs", 0),
634*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(Curves, "curves", 0),
635*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(Groups, "groups", 0),
636*e71b7053SJung-uk Kim #ifndef OPENSSL_NO_EC
637*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(ECDHParameters, "named_curve", SSL_CONF_FLAG_SERVER),
6387bded2dbSJung-uk Kim #endif
639*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(CipherString, "cipher", 0),
640*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(Ciphersuites, "ciphersuites", 0),
641*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(Protocol, NULL, 0),
642*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(MinProtocol, "min_protocol", 0),
643*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(MaxProtocol, "max_protocol", 0),
644*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(Options, NULL, 0),
645*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(VerifyMode, NULL, 0),
646*e71b7053SJung-uk Kim     SSL_CONF_CMD(Certificate, "cert", SSL_CONF_FLAG_CERTIFICATE,
647*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
648*e71b7053SJung-uk Kim     SSL_CONF_CMD(PrivateKey, "key", SSL_CONF_FLAG_CERTIFICATE,
649*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
650*e71b7053SJung-uk Kim     SSL_CONF_CMD(ServerInfoFile, NULL,
651*e71b7053SJung-uk Kim                  SSL_CONF_FLAG_SERVER | SSL_CONF_FLAG_CERTIFICATE,
652*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
653*e71b7053SJung-uk Kim     SSL_CONF_CMD(ChainCAPath, "chainCApath", SSL_CONF_FLAG_CERTIFICATE,
654*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_DIR),
655*e71b7053SJung-uk Kim     SSL_CONF_CMD(ChainCAFile, "chainCAfile", SSL_CONF_FLAG_CERTIFICATE,
656*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
657*e71b7053SJung-uk Kim     SSL_CONF_CMD(VerifyCAPath, "verifyCApath", SSL_CONF_FLAG_CERTIFICATE,
658*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_DIR),
659*e71b7053SJung-uk Kim     SSL_CONF_CMD(VerifyCAFile, "verifyCAfile", SSL_CONF_FLAG_CERTIFICATE,
660*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
661*e71b7053SJung-uk Kim     SSL_CONF_CMD(RequestCAFile, "requestCAFile", SSL_CONF_FLAG_CERTIFICATE,
662*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
663*e71b7053SJung-uk Kim     SSL_CONF_CMD(ClientCAFile, NULL,
664*e71b7053SJung-uk Kim                  SSL_CONF_FLAG_SERVER | SSL_CONF_FLAG_CERTIFICATE,
665*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
666*e71b7053SJung-uk Kim     SSL_CONF_CMD(RequestCAPath, NULL, SSL_CONF_FLAG_CERTIFICATE,
667*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_DIR),
668*e71b7053SJung-uk Kim     SSL_CONF_CMD(ClientCAPath, NULL,
669*e71b7053SJung-uk Kim                  SSL_CONF_FLAG_SERVER | SSL_CONF_FLAG_CERTIFICATE,
670*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_DIR),
6717bded2dbSJung-uk Kim #ifndef OPENSSL_NO_DH
672*e71b7053SJung-uk Kim     SSL_CONF_CMD(DHParameters, "dhparam",
673*e71b7053SJung-uk Kim                  SSL_CONF_FLAG_SERVER | SSL_CONF_FLAG_CERTIFICATE,
674*e71b7053SJung-uk Kim                  SSL_CONF_TYPE_FILE),
6757bded2dbSJung-uk Kim #endif
676*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(RecordPadding, "record_padding", 0),
677*e71b7053SJung-uk Kim     SSL_CONF_CMD_STRING(NumTickets, "num_tickets", SSL_CONF_FLAG_SERVER),
678*e71b7053SJung-uk Kim };
679*e71b7053SJung-uk Kim 
680*e71b7053SJung-uk Kim /* Supported switches: must match order of switches in ssl_conf_cmds */
681*e71b7053SJung-uk Kim static const ssl_switch_tbl ssl_cmd_switches[] = {
682*e71b7053SJung-uk Kim     {SSL_OP_NO_SSLv3, 0},       /* no_ssl3 */
683*e71b7053SJung-uk Kim     {SSL_OP_NO_TLSv1, 0},       /* no_tls1 */
684*e71b7053SJung-uk Kim     {SSL_OP_NO_TLSv1_1, 0},     /* no_tls1_1 */
685*e71b7053SJung-uk Kim     {SSL_OP_NO_TLSv1_2, 0},     /* no_tls1_2 */
686*e71b7053SJung-uk Kim     {SSL_OP_NO_TLSv1_3, 0},     /* no_tls1_3 */
687*e71b7053SJung-uk Kim     {SSL_OP_ALL, 0},            /* bugs */
688*e71b7053SJung-uk Kim     {SSL_OP_NO_COMPRESSION, 0}, /* no_comp */
689*e71b7053SJung-uk Kim     {SSL_OP_NO_COMPRESSION, SSL_TFLAG_INV}, /* comp */
690*e71b7053SJung-uk Kim     {SSL_OP_SINGLE_ECDH_USE, 0}, /* ecdh_single */
691*e71b7053SJung-uk Kim     {SSL_OP_NO_TICKET, 0},      /* no_ticket */
692*e71b7053SJung-uk Kim     {SSL_OP_CIPHER_SERVER_PREFERENCE, 0}, /* serverpref */
693*e71b7053SJung-uk Kim     /* legacy_renegotiation */
694*e71b7053SJung-uk Kim     {SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION, 0},
695*e71b7053SJung-uk Kim     /* legacy_server_connect */
696*e71b7053SJung-uk Kim     {SSL_OP_LEGACY_SERVER_CONNECT, 0},
697*e71b7053SJung-uk Kim     /* no_renegotiation */
698*e71b7053SJung-uk Kim     {SSL_OP_NO_RENEGOTIATION, 0},
699*e71b7053SJung-uk Kim     /* no_resumption_on_reneg */
700*e71b7053SJung-uk Kim     {SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION, 0},
701*e71b7053SJung-uk Kim     /* no_legacy_server_connect */
702*e71b7053SJung-uk Kim     {SSL_OP_LEGACY_SERVER_CONNECT, SSL_TFLAG_INV},
703*e71b7053SJung-uk Kim     /* allow_no_dhe_kex */
704*e71b7053SJung-uk Kim     {SSL_OP_ALLOW_NO_DHE_KEX, 0},
705*e71b7053SJung-uk Kim     /* chacha reprioritization */
706*e71b7053SJung-uk Kim     {SSL_OP_PRIORITIZE_CHACHA, 0},
707*e71b7053SJung-uk Kim     {SSL_CERT_FLAG_TLS_STRICT, SSL_TFLAG_CERT}, /* strict */
708*e71b7053SJung-uk Kim     /* no_middlebox */
709*e71b7053SJung-uk Kim     {SSL_OP_ENABLE_MIDDLEBOX_COMPAT, SSL_TFLAG_INV},
710*e71b7053SJung-uk Kim     /* anti_replay */
711*e71b7053SJung-uk Kim     {SSL_OP_NO_ANTI_REPLAY, SSL_TFLAG_INV},
712*e71b7053SJung-uk Kim     /* no_anti_replay */
713*e71b7053SJung-uk Kim     {SSL_OP_NO_ANTI_REPLAY, 0},
7147bded2dbSJung-uk Kim };
7157bded2dbSJung-uk Kim 
7167bded2dbSJung-uk Kim static int ssl_conf_cmd_skip_prefix(SSL_CONF_CTX *cctx, const char **pcmd)
7177bded2dbSJung-uk Kim {
7187bded2dbSJung-uk Kim     if (!pcmd || !*pcmd)
7197bded2dbSJung-uk Kim         return 0;
7207bded2dbSJung-uk Kim     /* If a prefix is set, check and skip */
7217bded2dbSJung-uk Kim     if (cctx->prefix) {
7227bded2dbSJung-uk Kim         if (strlen(*pcmd) <= cctx->prefixlen)
7237bded2dbSJung-uk Kim             return 0;
7247bded2dbSJung-uk Kim         if (cctx->flags & SSL_CONF_FLAG_CMDLINE &&
7257bded2dbSJung-uk Kim             strncmp(*pcmd, cctx->prefix, cctx->prefixlen))
7267bded2dbSJung-uk Kim             return 0;
7277bded2dbSJung-uk Kim         if (cctx->flags & SSL_CONF_FLAG_FILE &&
7287bded2dbSJung-uk Kim             strncasecmp(*pcmd, cctx->prefix, cctx->prefixlen))
7297bded2dbSJung-uk Kim             return 0;
7307bded2dbSJung-uk Kim         *pcmd += cctx->prefixlen;
7317bded2dbSJung-uk Kim     } else if (cctx->flags & SSL_CONF_FLAG_CMDLINE) {
7327bded2dbSJung-uk Kim         if (**pcmd != '-' || !(*pcmd)[1])
7337bded2dbSJung-uk Kim             return 0;
7347bded2dbSJung-uk Kim         *pcmd += 1;
7357bded2dbSJung-uk Kim     }
7367bded2dbSJung-uk Kim     return 1;
7377bded2dbSJung-uk Kim }
7387bded2dbSJung-uk Kim 
739*e71b7053SJung-uk Kim /* Determine if a command is allowed according to cctx flags */
740*e71b7053SJung-uk Kim static int ssl_conf_cmd_allowed(SSL_CONF_CTX *cctx, const ssl_conf_cmd_tbl * t)
741*e71b7053SJung-uk Kim {
742*e71b7053SJung-uk Kim     unsigned int tfl = t->flags;
743*e71b7053SJung-uk Kim     unsigned int cfl = cctx->flags;
744*e71b7053SJung-uk Kim     if ((tfl & SSL_CONF_FLAG_SERVER) && !(cfl & SSL_CONF_FLAG_SERVER))
745*e71b7053SJung-uk Kim         return 0;
746*e71b7053SJung-uk Kim     if ((tfl & SSL_CONF_FLAG_CLIENT) && !(cfl & SSL_CONF_FLAG_CLIENT))
747*e71b7053SJung-uk Kim         return 0;
748*e71b7053SJung-uk Kim     if ((tfl & SSL_CONF_FLAG_CERTIFICATE)
749*e71b7053SJung-uk Kim         && !(cfl & SSL_CONF_FLAG_CERTIFICATE))
750*e71b7053SJung-uk Kim         return 0;
751*e71b7053SJung-uk Kim     return 1;
752*e71b7053SJung-uk Kim }
753*e71b7053SJung-uk Kim 
7547bded2dbSJung-uk Kim static const ssl_conf_cmd_tbl *ssl_conf_cmd_lookup(SSL_CONF_CTX *cctx,
7557bded2dbSJung-uk Kim                                                    const char *cmd)
7567bded2dbSJung-uk Kim {
7577bded2dbSJung-uk Kim     const ssl_conf_cmd_tbl *t;
7587bded2dbSJung-uk Kim     size_t i;
7597bded2dbSJung-uk Kim     if (cmd == NULL)
7607bded2dbSJung-uk Kim         return NULL;
7617bded2dbSJung-uk Kim 
7627bded2dbSJung-uk Kim     /* Look for matching parameter name in table */
763*e71b7053SJung-uk Kim     for (i = 0, t = ssl_conf_cmds; i < OSSL_NELEM(ssl_conf_cmds); i++, t++) {
764*e71b7053SJung-uk Kim         if (ssl_conf_cmd_allowed(cctx, t)) {
7657bded2dbSJung-uk Kim             if (cctx->flags & SSL_CONF_FLAG_CMDLINE) {
766*e71b7053SJung-uk Kim                 if (t->str_cmdline && strcmp(t->str_cmdline, cmd) == 0)
7677bded2dbSJung-uk Kim                     return t;
7687bded2dbSJung-uk Kim             }
7697bded2dbSJung-uk Kim             if (cctx->flags & SSL_CONF_FLAG_FILE) {
770*e71b7053SJung-uk Kim                 if (t->str_file && strcasecmp(t->str_file, cmd) == 0)
7717bded2dbSJung-uk Kim                     return t;
7727bded2dbSJung-uk Kim             }
7737bded2dbSJung-uk Kim         }
774*e71b7053SJung-uk Kim     }
7757bded2dbSJung-uk Kim     return NULL;
7767bded2dbSJung-uk Kim }
7777bded2dbSJung-uk Kim 
778*e71b7053SJung-uk Kim static int ctrl_switch_option(SSL_CONF_CTX *cctx, const ssl_conf_cmd_tbl * cmd)
779*e71b7053SJung-uk Kim {
780*e71b7053SJung-uk Kim     /* Find index of command in table */
781*e71b7053SJung-uk Kim     size_t idx = cmd - ssl_conf_cmds;
782*e71b7053SJung-uk Kim     const ssl_switch_tbl *scmd;
783*e71b7053SJung-uk Kim     /* Sanity check index */
784*e71b7053SJung-uk Kim     if (idx >= OSSL_NELEM(ssl_cmd_switches))
785*e71b7053SJung-uk Kim         return 0;
786*e71b7053SJung-uk Kim     /* Obtain switches entry with same index */
787*e71b7053SJung-uk Kim     scmd = ssl_cmd_switches + idx;
788*e71b7053SJung-uk Kim     ssl_set_option(cctx, scmd->name_flags, scmd->option_value, 1);
789*e71b7053SJung-uk Kim     return 1;
790*e71b7053SJung-uk Kim }
791*e71b7053SJung-uk Kim 
7927bded2dbSJung-uk Kim int SSL_CONF_cmd(SSL_CONF_CTX *cctx, const char *cmd, const char *value)
7937bded2dbSJung-uk Kim {
7947bded2dbSJung-uk Kim     const ssl_conf_cmd_tbl *runcmd;
7957bded2dbSJung-uk Kim     if (cmd == NULL) {
7967bded2dbSJung-uk Kim         SSLerr(SSL_F_SSL_CONF_CMD, SSL_R_INVALID_NULL_CMD_NAME);
7977bded2dbSJung-uk Kim         return 0;
7987bded2dbSJung-uk Kim     }
7997bded2dbSJung-uk Kim 
8007bded2dbSJung-uk Kim     if (!ssl_conf_cmd_skip_prefix(cctx, &cmd))
8017bded2dbSJung-uk Kim         return -2;
8027bded2dbSJung-uk Kim 
8037bded2dbSJung-uk Kim     runcmd = ssl_conf_cmd_lookup(cctx, cmd);
8047bded2dbSJung-uk Kim 
8057bded2dbSJung-uk Kim     if (runcmd) {
8067bded2dbSJung-uk Kim         int rv;
807*e71b7053SJung-uk Kim         if (runcmd->value_type == SSL_CONF_TYPE_NONE) {
808*e71b7053SJung-uk Kim             return ctrl_switch_option(cctx, runcmd);
809*e71b7053SJung-uk Kim         }
8107bded2dbSJung-uk Kim         if (value == NULL)
8117bded2dbSJung-uk Kim             return -3;
8127bded2dbSJung-uk Kim         rv = runcmd->cmd(cctx, value);
8137bded2dbSJung-uk Kim         if (rv > 0)
8147bded2dbSJung-uk Kim             return 2;
8157bded2dbSJung-uk Kim         if (rv == -2)
8167bded2dbSJung-uk Kim             return -2;
8177bded2dbSJung-uk Kim         if (cctx->flags & SSL_CONF_FLAG_SHOW_ERRORS) {
8187bded2dbSJung-uk Kim             SSLerr(SSL_F_SSL_CONF_CMD, SSL_R_BAD_VALUE);
8197bded2dbSJung-uk Kim             ERR_add_error_data(4, "cmd=", cmd, ", value=", value);
8207bded2dbSJung-uk Kim         }
8217bded2dbSJung-uk Kim         return 0;
8227bded2dbSJung-uk Kim     }
8237bded2dbSJung-uk Kim 
8247bded2dbSJung-uk Kim     if (cctx->flags & SSL_CONF_FLAG_SHOW_ERRORS) {
8257bded2dbSJung-uk Kim         SSLerr(SSL_F_SSL_CONF_CMD, SSL_R_UNKNOWN_CMD_NAME);
8267bded2dbSJung-uk Kim         ERR_add_error_data(2, "cmd=", cmd);
8277bded2dbSJung-uk Kim     }
8287bded2dbSJung-uk Kim 
8297bded2dbSJung-uk Kim     return -2;
8307bded2dbSJung-uk Kim }
8317bded2dbSJung-uk Kim 
8327bded2dbSJung-uk Kim int SSL_CONF_cmd_argv(SSL_CONF_CTX *cctx, int *pargc, char ***pargv)
8337bded2dbSJung-uk Kim {
8347bded2dbSJung-uk Kim     int rv;
8357bded2dbSJung-uk Kim     const char *arg = NULL, *argn;
8367bded2dbSJung-uk Kim     if (pargc && *pargc == 0)
8377bded2dbSJung-uk Kim         return 0;
8387bded2dbSJung-uk Kim     if (!pargc || *pargc > 0)
8397bded2dbSJung-uk Kim         arg = **pargv;
8407bded2dbSJung-uk Kim     if (arg == NULL)
8417bded2dbSJung-uk Kim         return 0;
8427bded2dbSJung-uk Kim     if (!pargc || *pargc > 1)
8437bded2dbSJung-uk Kim         argn = (*pargv)[1];
8447bded2dbSJung-uk Kim     else
8457bded2dbSJung-uk Kim         argn = NULL;
8467bded2dbSJung-uk Kim     cctx->flags &= ~SSL_CONF_FLAG_FILE;
8477bded2dbSJung-uk Kim     cctx->flags |= SSL_CONF_FLAG_CMDLINE;
8487bded2dbSJung-uk Kim     rv = SSL_CONF_cmd(cctx, arg, argn);
8497bded2dbSJung-uk Kim     if (rv > 0) {
8507bded2dbSJung-uk Kim         /* Success: update pargc, pargv */
8517bded2dbSJung-uk Kim         (*pargv) += rv;
8527bded2dbSJung-uk Kim         if (pargc)
8537bded2dbSJung-uk Kim             (*pargc) -= rv;
8547bded2dbSJung-uk Kim         return rv;
8557bded2dbSJung-uk Kim     }
8567bded2dbSJung-uk Kim     /* Unknown switch: indicate no arguments processed */
8577bded2dbSJung-uk Kim     if (rv == -2)
8587bded2dbSJung-uk Kim         return 0;
8597bded2dbSJung-uk Kim     /* Some error occurred processing command, return fatal error */
8607bded2dbSJung-uk Kim     if (rv == 0)
8617bded2dbSJung-uk Kim         return -1;
8627bded2dbSJung-uk Kim     return rv;
8637bded2dbSJung-uk Kim }
8647bded2dbSJung-uk Kim 
8657bded2dbSJung-uk Kim int SSL_CONF_cmd_value_type(SSL_CONF_CTX *cctx, const char *cmd)
8667bded2dbSJung-uk Kim {
8677bded2dbSJung-uk Kim     if (ssl_conf_cmd_skip_prefix(cctx, &cmd)) {
8687bded2dbSJung-uk Kim         const ssl_conf_cmd_tbl *runcmd;
8697bded2dbSJung-uk Kim         runcmd = ssl_conf_cmd_lookup(cctx, cmd);
8707bded2dbSJung-uk Kim         if (runcmd)
8717bded2dbSJung-uk Kim             return runcmd->value_type;
8727bded2dbSJung-uk Kim     }
8737bded2dbSJung-uk Kim     return SSL_CONF_TYPE_UNKNOWN;
8747bded2dbSJung-uk Kim }
8757bded2dbSJung-uk Kim 
8767bded2dbSJung-uk Kim SSL_CONF_CTX *SSL_CONF_CTX_new(void)
8777bded2dbSJung-uk Kim {
878*e71b7053SJung-uk Kim     SSL_CONF_CTX *ret = OPENSSL_zalloc(sizeof(*ret));
879*e71b7053SJung-uk Kim 
8807bded2dbSJung-uk Kim     return ret;
8817bded2dbSJung-uk Kim }
8827bded2dbSJung-uk Kim 
8837bded2dbSJung-uk Kim int SSL_CONF_CTX_finish(SSL_CONF_CTX *cctx)
8847bded2dbSJung-uk Kim {
885*e71b7053SJung-uk Kim     /* See if any certificates are missing private keys */
886*e71b7053SJung-uk Kim     size_t i;
887*e71b7053SJung-uk Kim     CERT *c = NULL;
888*e71b7053SJung-uk Kim     if (cctx->ctx)
889*e71b7053SJung-uk Kim         c = cctx->ctx->cert;
890*e71b7053SJung-uk Kim     else if (cctx->ssl)
891*e71b7053SJung-uk Kim         c = cctx->ssl->cert;
892*e71b7053SJung-uk Kim     if (c && cctx->flags & SSL_CONF_FLAG_REQUIRE_PRIVATE) {
893*e71b7053SJung-uk Kim         for (i = 0; i < SSL_PKEY_NUM; i++) {
894*e71b7053SJung-uk Kim             const char *p = cctx->cert_filename[i];
895*e71b7053SJung-uk Kim             /*
896*e71b7053SJung-uk Kim              * If missing private key try to load one from certificate file
897*e71b7053SJung-uk Kim              */
898*e71b7053SJung-uk Kim             if (p && !c->pkeys[i].privatekey) {
899*e71b7053SJung-uk Kim                 if (!cmd_PrivateKey(cctx, p))
900*e71b7053SJung-uk Kim                     return 0;
901*e71b7053SJung-uk Kim             }
902*e71b7053SJung-uk Kim         }
903*e71b7053SJung-uk Kim     }
904*e71b7053SJung-uk Kim     if (cctx->canames) {
905*e71b7053SJung-uk Kim         if (cctx->ssl)
906*e71b7053SJung-uk Kim             SSL_set0_CA_list(cctx->ssl, cctx->canames);
907*e71b7053SJung-uk Kim         else if (cctx->ctx)
908*e71b7053SJung-uk Kim             SSL_CTX_set0_CA_list(cctx->ctx, cctx->canames);
909*e71b7053SJung-uk Kim         else
910*e71b7053SJung-uk Kim             sk_X509_NAME_pop_free(cctx->canames, X509_NAME_free);
911*e71b7053SJung-uk Kim         cctx->canames = NULL;
912*e71b7053SJung-uk Kim     }
9137bded2dbSJung-uk Kim     return 1;
9147bded2dbSJung-uk Kim }
9157bded2dbSJung-uk Kim 
9167bded2dbSJung-uk Kim void SSL_CONF_CTX_free(SSL_CONF_CTX *cctx)
9177bded2dbSJung-uk Kim {
9187bded2dbSJung-uk Kim     if (cctx) {
919*e71b7053SJung-uk Kim         size_t i;
920*e71b7053SJung-uk Kim         for (i = 0; i < SSL_PKEY_NUM; i++)
921*e71b7053SJung-uk Kim             OPENSSL_free(cctx->cert_filename[i]);
9227bded2dbSJung-uk Kim         OPENSSL_free(cctx->prefix);
923*e71b7053SJung-uk Kim         sk_X509_NAME_pop_free(cctx->canames, X509_NAME_free);
9247bded2dbSJung-uk Kim         OPENSSL_free(cctx);
9257bded2dbSJung-uk Kim     }
9267bded2dbSJung-uk Kim }
9277bded2dbSJung-uk Kim 
9287bded2dbSJung-uk Kim unsigned int SSL_CONF_CTX_set_flags(SSL_CONF_CTX *cctx, unsigned int flags)
9297bded2dbSJung-uk Kim {
9307bded2dbSJung-uk Kim     cctx->flags |= flags;
9317bded2dbSJung-uk Kim     return cctx->flags;
9327bded2dbSJung-uk Kim }
9337bded2dbSJung-uk Kim 
9347bded2dbSJung-uk Kim unsigned int SSL_CONF_CTX_clear_flags(SSL_CONF_CTX *cctx, unsigned int flags)
9357bded2dbSJung-uk Kim {
9367bded2dbSJung-uk Kim     cctx->flags &= ~flags;
9377bded2dbSJung-uk Kim     return cctx->flags;
9387bded2dbSJung-uk Kim }
9397bded2dbSJung-uk Kim 
9407bded2dbSJung-uk Kim int SSL_CONF_CTX_set1_prefix(SSL_CONF_CTX *cctx, const char *pre)
9417bded2dbSJung-uk Kim {
9427bded2dbSJung-uk Kim     char *tmp = NULL;
9437bded2dbSJung-uk Kim     if (pre) {
944*e71b7053SJung-uk Kim         tmp = OPENSSL_strdup(pre);
9457bded2dbSJung-uk Kim         if (tmp == NULL)
9467bded2dbSJung-uk Kim             return 0;
9477bded2dbSJung-uk Kim     }
9487bded2dbSJung-uk Kim     OPENSSL_free(cctx->prefix);
9497bded2dbSJung-uk Kim     cctx->prefix = tmp;
9507bded2dbSJung-uk Kim     if (tmp)
9517bded2dbSJung-uk Kim         cctx->prefixlen = strlen(tmp);
9527bded2dbSJung-uk Kim     else
9537bded2dbSJung-uk Kim         cctx->prefixlen = 0;
9547bded2dbSJung-uk Kim     return 1;
9557bded2dbSJung-uk Kim }
9567bded2dbSJung-uk Kim 
9577bded2dbSJung-uk Kim void SSL_CONF_CTX_set_ssl(SSL_CONF_CTX *cctx, SSL *ssl)
9587bded2dbSJung-uk Kim {
9597bded2dbSJung-uk Kim     cctx->ssl = ssl;
9607bded2dbSJung-uk Kim     cctx->ctx = NULL;
9617bded2dbSJung-uk Kim     if (ssl) {
9627bded2dbSJung-uk Kim         cctx->poptions = &ssl->options;
963*e71b7053SJung-uk Kim         cctx->min_version = &ssl->min_proto_version;
964*e71b7053SJung-uk Kim         cctx->max_version = &ssl->max_proto_version;
9657bded2dbSJung-uk Kim         cctx->pcert_flags = &ssl->cert->cert_flags;
966*e71b7053SJung-uk Kim         cctx->pvfy_flags = &ssl->verify_mode;
9677bded2dbSJung-uk Kim     } else {
9687bded2dbSJung-uk Kim         cctx->poptions = NULL;
969*e71b7053SJung-uk Kim         cctx->min_version = NULL;
970*e71b7053SJung-uk Kim         cctx->max_version = NULL;
9717bded2dbSJung-uk Kim         cctx->pcert_flags = NULL;
972*e71b7053SJung-uk Kim         cctx->pvfy_flags = NULL;
9737bded2dbSJung-uk Kim     }
9747bded2dbSJung-uk Kim }
9757bded2dbSJung-uk Kim 
9767bded2dbSJung-uk Kim void SSL_CONF_CTX_set_ssl_ctx(SSL_CONF_CTX *cctx, SSL_CTX *ctx)
9777bded2dbSJung-uk Kim {
9787bded2dbSJung-uk Kim     cctx->ctx = ctx;
9797bded2dbSJung-uk Kim     cctx->ssl = NULL;
9807bded2dbSJung-uk Kim     if (ctx) {
9817bded2dbSJung-uk Kim         cctx->poptions = &ctx->options;
982*e71b7053SJung-uk Kim         cctx->min_version = &ctx->min_proto_version;
983*e71b7053SJung-uk Kim         cctx->max_version = &ctx->max_proto_version;
9847bded2dbSJung-uk Kim         cctx->pcert_flags = &ctx->cert->cert_flags;
985*e71b7053SJung-uk Kim         cctx->pvfy_flags = &ctx->verify_mode;
9867bded2dbSJung-uk Kim     } else {
9877bded2dbSJung-uk Kim         cctx->poptions = NULL;
988*e71b7053SJung-uk Kim         cctx->min_version = NULL;
989*e71b7053SJung-uk Kim         cctx->max_version = NULL;
9907bded2dbSJung-uk Kim         cctx->pcert_flags = NULL;
991*e71b7053SJung-uk Kim         cctx->pvfy_flags = NULL;
9927bded2dbSJung-uk Kim     }
9937bded2dbSJung-uk Kim }
994