1e1051a39Sopenharmony_ci/* 2e1051a39Sopenharmony_ci * Copyright 2012-2020 The OpenSSL Project Authors. All Rights Reserved. 3e1051a39Sopenharmony_ci * 4e1051a39Sopenharmony_ci * Licensed under the Apache License 2.0 (the "License"). You may not use 5e1051a39Sopenharmony_ci * this file except in compliance with the License. You can obtain a copy 6e1051a39Sopenharmony_ci * in the file LICENSE in the source distribution or at 7e1051a39Sopenharmony_ci * https://www.openssl.org/source/license.html 8e1051a39Sopenharmony_ci */ 9e1051a39Sopenharmony_ci 10e1051a39Sopenharmony_ci#include <stdio.h> 11e1051a39Sopenharmony_ci#include <openssl/crypto.h> 12e1051a39Sopenharmony_ci#include "internal/cryptlib.h" 13e1051a39Sopenharmony_ci#include <openssl/conf.h> 14e1051a39Sopenharmony_ci#include <openssl/x509v3.h> 15e1051a39Sopenharmony_ci 16e1051a39Sopenharmony_ci/* Multi string module: add table entries from a given section */ 17e1051a39Sopenharmony_ci 18e1051a39Sopenharmony_cistatic int do_tcreate(const char *value, const char *name); 19e1051a39Sopenharmony_ci 20e1051a39Sopenharmony_cistatic int stbl_module_init(CONF_IMODULE *md, const CONF *cnf) 21e1051a39Sopenharmony_ci{ 22e1051a39Sopenharmony_ci int i; 23e1051a39Sopenharmony_ci const char *stbl_section; 24e1051a39Sopenharmony_ci STACK_OF(CONF_VALUE) *sktmp; 25e1051a39Sopenharmony_ci CONF_VALUE *mval; 26e1051a39Sopenharmony_ci 27e1051a39Sopenharmony_ci stbl_section = CONF_imodule_get_value(md); 28e1051a39Sopenharmony_ci if ((sktmp = NCONF_get_section(cnf, stbl_section)) == NULL) { 29e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_ASN1, ASN1_R_ERROR_LOADING_SECTION); 30e1051a39Sopenharmony_ci return 0; 31e1051a39Sopenharmony_ci } 32e1051a39Sopenharmony_ci for (i = 0; i < sk_CONF_VALUE_num(sktmp); i++) { 33e1051a39Sopenharmony_ci mval = sk_CONF_VALUE_value(sktmp, i); 34e1051a39Sopenharmony_ci if (!do_tcreate(mval->value, mval->name)) { 35e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_ASN1, ASN1_R_INVALID_VALUE); 36e1051a39Sopenharmony_ci return 0; 37e1051a39Sopenharmony_ci } 38e1051a39Sopenharmony_ci } 39e1051a39Sopenharmony_ci return 1; 40e1051a39Sopenharmony_ci} 41e1051a39Sopenharmony_ci 42e1051a39Sopenharmony_cistatic void stbl_module_finish(CONF_IMODULE *md) 43e1051a39Sopenharmony_ci{ 44e1051a39Sopenharmony_ci ASN1_STRING_TABLE_cleanup(); 45e1051a39Sopenharmony_ci} 46e1051a39Sopenharmony_ci 47e1051a39Sopenharmony_civoid ASN1_add_stable_module(void) 48e1051a39Sopenharmony_ci{ 49e1051a39Sopenharmony_ci CONF_module_add("stbl_section", stbl_module_init, stbl_module_finish); 50e1051a39Sopenharmony_ci} 51e1051a39Sopenharmony_ci 52e1051a39Sopenharmony_ci/* 53e1051a39Sopenharmony_ci * Create an table entry based on a name value pair. format is oid_name = 54e1051a39Sopenharmony_ci * n1:v1, n2:v2,... where name is "min", "max", "mask" or "flags". 55e1051a39Sopenharmony_ci */ 56e1051a39Sopenharmony_ci 57e1051a39Sopenharmony_cistatic int do_tcreate(const char *value, const char *name) 58e1051a39Sopenharmony_ci{ 59e1051a39Sopenharmony_ci char *eptr; 60e1051a39Sopenharmony_ci int nid, i, rv = 0; 61e1051a39Sopenharmony_ci long tbl_min = -1, tbl_max = -1; 62e1051a39Sopenharmony_ci unsigned long tbl_mask = 0, tbl_flags = 0; 63e1051a39Sopenharmony_ci STACK_OF(CONF_VALUE) *lst = NULL; 64e1051a39Sopenharmony_ci CONF_VALUE *cnf = NULL; 65e1051a39Sopenharmony_ci nid = OBJ_sn2nid(name); 66e1051a39Sopenharmony_ci if (nid == NID_undef) 67e1051a39Sopenharmony_ci nid = OBJ_ln2nid(name); 68e1051a39Sopenharmony_ci if (nid == NID_undef) 69e1051a39Sopenharmony_ci goto err; 70e1051a39Sopenharmony_ci lst = X509V3_parse_list(value); 71e1051a39Sopenharmony_ci if (!lst) 72e1051a39Sopenharmony_ci goto err; 73e1051a39Sopenharmony_ci for (i = 0; i < sk_CONF_VALUE_num(lst); i++) { 74e1051a39Sopenharmony_ci cnf = sk_CONF_VALUE_value(lst, i); 75e1051a39Sopenharmony_ci if (strcmp(cnf->name, "min") == 0) { 76e1051a39Sopenharmony_ci tbl_min = strtoul(cnf->value, &eptr, 0); 77e1051a39Sopenharmony_ci if (*eptr) 78e1051a39Sopenharmony_ci goto err; 79e1051a39Sopenharmony_ci } else if (strcmp(cnf->name, "max") == 0) { 80e1051a39Sopenharmony_ci tbl_max = strtoul(cnf->value, &eptr, 0); 81e1051a39Sopenharmony_ci if (*eptr) 82e1051a39Sopenharmony_ci goto err; 83e1051a39Sopenharmony_ci } else if (strcmp(cnf->name, "mask") == 0) { 84e1051a39Sopenharmony_ci if (!ASN1_str2mask(cnf->value, &tbl_mask) || !tbl_mask) 85e1051a39Sopenharmony_ci goto err; 86e1051a39Sopenharmony_ci } else if (strcmp(cnf->name, "flags") == 0) { 87e1051a39Sopenharmony_ci if (strcmp(cnf->value, "nomask") == 0) 88e1051a39Sopenharmony_ci tbl_flags = STABLE_NO_MASK; 89e1051a39Sopenharmony_ci else if (strcmp(cnf->value, "none") == 0) 90e1051a39Sopenharmony_ci tbl_flags = STABLE_FLAGS_CLEAR; 91e1051a39Sopenharmony_ci else 92e1051a39Sopenharmony_ci goto err; 93e1051a39Sopenharmony_ci } else 94e1051a39Sopenharmony_ci goto err; 95e1051a39Sopenharmony_ci } 96e1051a39Sopenharmony_ci rv = 1; 97e1051a39Sopenharmony_ci err: 98e1051a39Sopenharmony_ci if (rv == 0) { 99e1051a39Sopenharmony_ci if (cnf) 100e1051a39Sopenharmony_ci ERR_raise_data(ERR_LIB_ASN1, ASN1_R_INVALID_STRING_TABLE_VALUE, 101e1051a39Sopenharmony_ci "field=%s, value=%s", cnf->name, cnf->value); 102e1051a39Sopenharmony_ci else 103e1051a39Sopenharmony_ci ERR_raise_data(ERR_LIB_ASN1, ASN1_R_INVALID_STRING_TABLE_VALUE, 104e1051a39Sopenharmony_ci "name=%s, value=%s", name, value); 105e1051a39Sopenharmony_ci } else { 106e1051a39Sopenharmony_ci rv = ASN1_STRING_TABLE_add(nid, tbl_min, tbl_max, 107e1051a39Sopenharmony_ci tbl_mask, tbl_flags); 108e1051a39Sopenharmony_ci if (!rv) 109e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_ASN1, ERR_R_MALLOC_FAILURE); 110e1051a39Sopenharmony_ci } 111e1051a39Sopenharmony_ci sk_CONF_VALUE_pop_free(lst, X509V3_conf_free); 112e1051a39Sopenharmony_ci return rv; 113e1051a39Sopenharmony_ci} 114