X-Git-Url: https://git.openssl.org/gitweb/?p=openssl.git;a=blobdiff_plain;f=crypto%2Fconf%2Fconf_mod.c;h=df1642a0a56216f3dff4bdd04ed6a96126af1f8b;hp=f1950ea16dcde656aaa0ecd92a6c18a69420bd7f;hb=0bcb17a7776b7f740e855932890edfb7acfd7124;hpb=dd2589494f7142aeda2f282a5b6bf1e9a2dd2110 diff --git a/crypto/conf/conf_mod.c b/crypto/conf/conf_mod.c index f1950ea16d..df1642a0a5 100644 --- a/crypto/conf/conf_mod.c +++ b/crypto/conf/conf_mod.c @@ -1,5 +1,5 @@ /* conf_mod.c */ -/* Written by Stephen Henson (shenson@bigfoot.com) for the OpenSSL +/* Written by Stephen Henson (steve@openssl.org) for the OpenSSL * project 2001. */ /* ==================================================================== @@ -57,6 +57,7 @@ */ #include +#include #include #include "cryptlib.h" #include @@ -108,28 +109,35 @@ static STACK_OF(CONF_IMODULE) *initialized_modules = NULL; static void module_free(CONF_MODULE *md); static void module_finish(CONF_IMODULE *imod); -static int module_run(CONF *cnf, char *name, char *value, unsigned long flags); +static int module_run(const CONF *cnf, char *name, char *value, + unsigned long flags); static CONF_MODULE *module_add(DSO *dso, const char *name, conf_init_func *ifunc, conf_finish_func *ffunc); static CONF_MODULE *module_find(char *name); -static int module_init(CONF_MODULE *pmod, char *name, char *value, CONF *cnf); -static CONF_MODULE *module_load_dso(CONF *cnf, char *name, char *value, unsigned long flags); +static int module_init(CONF_MODULE *pmod, char *name, char *value, + const CONF *cnf); +static CONF_MODULE *module_load_dso(const CONF *cnf, char *name, char *value, + unsigned long flags); /* Main function: load modules from a CONF structure */ -int CONF_modules_load(CONF *cnf, char *appname, unsigned long flags) +int CONF_modules_load(const CONF *cnf, const char *appname, + unsigned long flags) { STACK_OF(CONF_VALUE) *values; CONF_VALUE *vl; - char *vsection; + char *vsection = NULL; int ret, i; - if (!cnf || !appname) + if (!cnf) return 1; + if (appname) + vsection = NCONF_get_string(cnf, NULL, appname); - vsection = NCONF_get_string(cnf, NULL, appname); + if (!appname || (!vsection && (flags & CONF_MFLAGS_DEFAULT_SECTION))) + vsection = NCONF_get_string(cnf, NULL, "openssl_conf"); if (!vsection) { @@ -155,26 +163,48 @@ int CONF_modules_load(CONF *cnf, char *appname, unsigned long flags) } -int CONF_modules_load_file(char *filename, char *appname, unsigned long flags) +int CONF_modules_load_file(const char *filename, const char *appname, + unsigned long flags) { + char *file = NULL; CONF *conf = NULL; int ret = 0; conf = NCONF_new(NULL); if (!conf) goto err; - if (NCONF_load(conf, filename, NULL) <= 0) + if (filename == NULL) + { + file = CONF_get1_default_config_file(); + if (!file) + goto err; + } + else + file = (char *)filename; + + if (NCONF_load(conf, file, NULL) <= 0) + { + if ((flags & CONF_MFLAGS_IGNORE_MISSING_FILE) && + (ERR_GET_REASON(ERR_peek_last_error()) == CONF_R_NO_SUCH_FILE)) + { + ERR_clear_error(); + ret = 1; + } goto err; + } ret = CONF_modules_load(conf, appname, flags); err: + if (filename == NULL) + OPENSSL_free(file); NCONF_free(conf); return ret; } -static int module_run(CONF *cnf, char *name, char *value, unsigned long flags) +static int module_run(const CONF *cnf, char *name, char *value, + unsigned long flags) { CONF_MODULE *md; int ret; @@ -182,7 +212,7 @@ static int module_run(CONF *cnf, char *name, char *value, unsigned long flags) md = module_find(name); /* Module not found: try to load DSO */ - if (!md) + if (!md && !(flags & CONF_MFLAGS_NO_DSO)) md = module_load_dso(cnf, name, value, flags); if (!md) @@ -201,9 +231,9 @@ static int module_run(CONF *cnf, char *name, char *value, unsigned long flags) { if (!(flags & CONF_MFLAGS_SILENT)) { - char rcode[10]; - CONFerr(CONF_F_CONF_MODULES_LOAD, CONF_R_MODULE_INITIALIZATION_ERROR); - sprintf(rcode, "%-8d", ret); + char rcode[DECIMAL_SIZE(ret)+1]; + CONFerr(CONF_F_MODULE_RUN, CONF_R_MODULE_INITIALIZATION_ERROR); + BIO_snprintf(rcode, sizeof rcode, "%-8d", ret); ERR_add_error_data(6, "module=", name, ", value=", value, ", retcode=", rcode); } } @@ -212,7 +242,8 @@ static int module_run(CONF *cnf, char *name, char *value, unsigned long flags) } /* Load a module from a DSO */ -static CONF_MODULE *module_load_dso(CONF *cnf, char *name, char *value, unsigned long flags) +static CONF_MODULE *module_load_dso(const CONF *cnf, char *name, char *value, + unsigned long flags) { DSO *dso = NULL; conf_init_func *ifunc; @@ -224,7 +255,7 @@ static CONF_MODULE *module_load_dso(CONF *cnf, char *name, char *value, unsigned path = NCONF_get_string(cnf, value, "path"); if (!path) { - ERR_get_error(); + ERR_clear_error(); path = name; } dso = DSO_load(NULL, path, NULL, 0); @@ -240,11 +271,6 @@ static CONF_MODULE *module_load_dso(CONF *cnf, char *name, char *value, unsigned goto err; } ffunc = (conf_finish_func *)DSO_bind_func(dso, DSO_mod_finish_name); - if (!ffunc) - { - errcode = CONF_R_MISSING_FINISH_FUNCTION; - goto err; - } /* All OK, add module */ md = module_add(dso, name, ifunc, ffunc); @@ -263,7 +289,7 @@ static CONF_MODULE *module_load_dso(CONF *cnf, char *name, char *value, unsigned /* add module to list */ static CONF_MODULE *module_add(DSO *dso, const char *name, - conf_init_func *ifunc, conf_finish_func *ffunc) + conf_init_func *ifunc, conf_finish_func *ffunc) { CONF_MODULE *tmod = NULL; if (supported_modules == NULL) @@ -318,7 +344,8 @@ static CONF_MODULE *module_find(char *name) } /* initialize a module */ -static int module_init(CONF_MODULE *pmod, char *name, char *value, CONF *cnf) +static int module_init(CONF_MODULE *pmod, char *name, char *value, + const CONF *cnf) { int ret = 1; int init_called = 0; @@ -396,6 +423,7 @@ void CONF_modules_unload(int all) { int i; CONF_MODULE *md; + CONF_modules_finish(); /* unload modules in reverse order */ for (i = sk_CONF_MODULE_num(supported_modules) - 1; i >= 0; i--) { @@ -404,7 +432,7 @@ void CONF_modules_unload(int all) if (((md->links > 0) || !md->dso) && !all) continue; /* Since we're working in reverse this is OK */ - sk_CONF_MODULE_delete(supported_modules, i); + (void)sk_CONF_MODULE_delete(supported_modules, i); module_free(md); } if (sk_CONF_MODULE_num(supported_modules) == 0) @@ -441,7 +469,8 @@ void CONF_modules_finish(void) static void module_finish(CONF_IMODULE *imod) { - imod->pmod->finish(imod); + if (imod->pmod->finish) + imod->pmod->finish(imod); imod->pmod->links--; OPENSSL_free(imod->name); OPENSSL_free(imod->value); @@ -467,17 +496,17 @@ void CONF_modules_free(void) /* Utility functions */ -char *CONF_imodule_get_name(CONF_IMODULE *md) +const char *CONF_imodule_get_name(const CONF_IMODULE *md) { return md->name; } -char *CONF_imodule_get_value(CONF_IMODULE *md) +const char *CONF_imodule_get_value(const CONF_IMODULE *md) { return md->value; } -void *CONF_imodule_get_usr_data(CONF_IMODULE *md) +void *CONF_imodule_get_usr_data(const CONF_IMODULE *md) { return md->usr_data; } @@ -487,12 +516,12 @@ void CONF_imodule_set_usr_data(CONF_IMODULE *md, void *usr_data) md->usr_data = usr_data; } -CONF_MODULE *CONF_imodule_get_module(CONF_IMODULE *md) +CONF_MODULE *CONF_imodule_get_module(const CONF_IMODULE *md) { return md->pmod; } -unsigned long CONF_imodule_get_flags(CONF_IMODULE *md) +unsigned long CONF_imodule_get_flags(const CONF_IMODULE *md) { return md->flags; } @@ -512,3 +541,83 @@ void CONF_module_set_usr_data(CONF_MODULE *pmod, void *usr_data) pmod->usr_data = usr_data; } +/* Return default config file name */ + +char *CONF_get1_default_config_file(void) + { + char *file; + int len; + + file = getenv("OPENSSL_CONF"); + if (file) + return BUF_strdup(file); + + len = strlen(X509_get_default_cert_area()); +#ifndef OPENSSL_SYS_VMS + len++; +#endif + len += strlen(OPENSSL_CONF); + + file = OPENSSL_malloc(len + 1); + + if (!file) + return NULL; + BUF_strlcpy(file,X509_get_default_cert_area(),len + 1); +#ifndef OPENSSL_SYS_VMS + BUF_strlcat(file,"/",len + 1); +#endif + BUF_strlcat(file,OPENSSL_CONF,len + 1); + + return file; + } + +/* This function takes a list separated by 'sep' and calls the + * callback function giving the start and length of each member + * optionally stripping leading and trailing whitespace. This can + * be used to parse comma separated lists for example. + */ + +int CONF_parse_list(const char *list_, int sep, int nospc, + int (*list_cb)(const char *elem, int len, void *usr), void *arg) + { + int ret; + const char *lstart, *tmpend, *p; + + if(list_ == NULL) + { + CONFerr(CONF_F_CONF_PARSE_LIST, CONF_R_LIST_CANNOT_BE_NULL); + return 0; + } + + lstart = list_; + for(;;) + { + if (nospc) + { + while(*lstart && isspace((unsigned char)*lstart)) + lstart++; + } + p = strchr(lstart, sep); + if (p == lstart || !*lstart) + ret = list_cb(NULL, 0, arg); + else + { + if (p) + tmpend = p - 1; + else + tmpend = lstart + strlen(lstart) - 1; + if (nospc) + { + while(isspace((unsigned char)*tmpend)) + tmpend--; + } + ret = list_cb(lstart, tmpend - lstart + 1, arg); + } + if (ret <= 0) + return ret; + if (p == NULL) + return 1; + lstart = p + 1; + } + } +