summaryrefslogtreecommitdiff
path: root/crypto/apr_crypto.c
diff options
context:
space:
mode:
Diffstat (limited to 'crypto/apr_crypto.c')
-rw-r--r--crypto/apr_crypto.c84
1 files changed, 51 insertions, 33 deletions
diff --git a/crypto/apr_crypto.c b/crypto/apr_crypto.c
index 07cc672d9..e7c11b734 100644
--- a/crypto/apr_crypto.c
+++ b/crypto/apr_crypto.c
@@ -37,8 +37,6 @@ static apr_hash_t *drivers = NULL;
#define ERROR_SIZE 1024
-#define CLEANUP_CAST (apr_status_t (*)(void*))
-
APR_TYPEDEF_STRUCT(apr_crypto_t,
apr_pool_t *pool;
apr_crypto_driver_t *provider;
@@ -87,26 +85,29 @@ static apr_status_t apr_crypto_term(void *ptr)
APR_DECLARE(apr_status_t) apr_crypto_init(apr_pool_t *pool)
{
apr_status_t rv;
- apr_pool_t *parent;
+ apr_pool_t *rootp;
int flags = 0;
if (drivers != NULL) {
return APR_SUCCESS;
}
- /* Top level pool scope, need process-scope lifetime */
- for (parent = apr_pool_parent_get(pool);
- parent && parent != pool;
- parent = apr_pool_parent_get(pool))
- pool = parent;
+ /* Top level pool scope, for drivers' process-scope lifetime */
+ rootp = pool;
+ for (;;) {
+ apr_pool_t *p = apr_pool_parent_get(rootp);
+ if (!p || p == rootp) {
+ break;
+ }
+ rootp = p;
+ }
#if APR_HAVE_MODULAR_DSO
/* deprecate in 2.0 - permit implicit initialization */
- apu_dso_init(pool);
+ apu_dso_init(rootp);
#endif
- drivers = apr_hash_make(pool);
-
- apr_pool_cleanup_register(pool, NULL, apr_crypto_term,
- apr_pool_cleanup_null);
+ drivers = apr_hash_make(rootp);
+ apr_pool_cleanup_register(rootp, NULL, apr_crypto_term,
+ apr_pool_cleanup_null);
/* apr_crypto_prng_init() may already have been called with
* non-default parameters, so ignore APR_EREINIT.
@@ -203,6 +204,7 @@ APR_DECLARE(apr_status_t) apr_crypto_get_driver(
char symname[34];
apr_dso_handle_t *dso;
apr_dso_handle_sym_t symbol;
+ apr_pool_t *rootp;
#endif
apr_status_t rv;
@@ -227,7 +229,7 @@ APR_DECLARE(apr_status_t) apr_crypto_get_driver(
#if APR_HAVE_MODULAR_DSO
/* The driver DSO must have exactly the same lifetime as the
* drivers hash table; ignore the passed-in pool */
- pool = apr_hash_pool_get(drivers);
+ rootp = apr_hash_pool_get(drivers);
#if defined(NETWARE)
apr_snprintf(modname, sizeof(modname), "crypto%s.nlm", name);
@@ -239,21 +241,19 @@ APR_DECLARE(apr_status_t) apr_crypto_get_driver(
"apr_crypto_%s-" APR_STRINGIFY(APR_MAJOR_VERSION) ".so", name);
#endif
apr_snprintf(symname, sizeof(symname), "apr_crypto_%s_driver", name);
- rv = apu_dso_load(&dso, &symbol, modname, symname, pool);
+ rv = apu_dso_load(&dso, &symbol, modname, symname, rootp);
if (rv == APR_SUCCESS || rv == APR_EINIT) { /* previously loaded?!? */
apr_crypto_driver_t *d = symbol;
rv = APR_SUCCESS;
if (d->init) {
- rv = d->init(pool, params, result);
+ rv = d->init(rootp, params, result);
if (rv == APR_EREINIT) {
rv = APR_SUCCESS;
}
}
if (rv == APR_SUCCESS) {
- *driver = symbol;
- name = apr_pstrdup(pool, name);
- apr_hash_set(drivers, name, APR_HASH_KEY_STRING, *driver);
- rv = APR_SUCCESS;
+ apr_hash_set(drivers, d->name, APR_HASH_KEY_STRING, d);
+ *driver = d;
}
}
apu_dso_mutex_unlock();
@@ -274,32 +274,38 @@ APR_DECLARE(apr_status_t) apr_crypto_get_driver(
/* Load statically-linked drivers: */
#if APU_HAVE_OPENSSL
- if (name[0] == 'o' && !strcmp(name, "openssl")) {
+ if (!strcmp(name, "openssl")) {
DRIVER_LOAD("openssl", apr_crypto_openssl_driver, pool, params, rv, result);
}
+ else
#endif
#if APU_HAVE_NSS
- if (name[0] == 'n' && !strcmp(name, "nss")) {
+ if (!strcmp(name, "nss")) {
DRIVER_LOAD("nss", apr_crypto_nss_driver, pool, params, rv, result);
}
+ else
#endif
#if APU_HAVE_COMMONCRYPTO
- if (name[0] == 'c' && !strcmp(name, "commoncrypto")) {
+ if (!strcmp(name, "commoncrypto")) {
DRIVER_LOAD("commoncrypto", apr_crypto_commoncrypto_driver, pool, params, rv, result);
}
+ else
#endif
#if APU_HAVE_MSCAPI
- if (name[0] == 'm' && !strcmp(name, "mscapi")) {
+ if (!strcmp(name, "mscapi")) {
DRIVER_LOAD("mscapi", apr_crypto_mscapi_driver, pool, params, rv, result);
}
+ else
#endif
#if APU_HAVE_MSCNG
- if (name[0] == 'm' && !strcmp(name, "mscng")) {
+ if (!strcmp(name, "mscng")) {
DRIVER_LOAD("mscng", apr_crypto_mscng_driver, pool, params, rv, result);
}
+ else
#endif
+ ;
-#endif
+#endif /* !APR_HAVE_MODULAR_DSO */
return rv;
}
@@ -407,7 +413,7 @@ APR_DECLARE(apr_status_t) apr_crypto_lib_init(const char *name,
apr_pool_t *pool)
{
apr_status_t rv;
- apr_pool_t *rootp, *p;
+ apr_pool_t *rootp;
struct crypto_lib *lib;
if (!name) {
@@ -419,7 +425,11 @@ APR_DECLARE(apr_status_t) apr_crypto_lib_init(const char *name,
}
rootp = pool;
- while ((p = apr_pool_parent_get(rootp))) {
+ for (;;) {
+ apr_pool_t *p = apr_pool_parent_get(rootp);
+ if (!p || p == rootp) {
+ break;
+ }
rootp = p;
}
@@ -495,8 +505,10 @@ APR_DECLARE(apr_status_t) apr_crypto_lib_init(const char *name,
if (rv == APR_SUCCESS) {
lib->pool = pool;
apr_hash_set(active_libs, lib->name, APR_HASH_KEY_STRING, lib);
- apr_pool_cleanup_register(lib->pool, lib, crypto_lib_cleanup,
- apr_pool_cleanup_null);
+ if (apr_pool_parent_get(pool)) {
+ apr_pool_cleanup_register(pool, lib, crypto_lib_cleanup,
+ apr_pool_cleanup_null);
+ }
}
else {
spare_lib_push(lib);
@@ -513,6 +525,9 @@ static apr_status_t crypto_lib_term(const char *name)
if (!lib) {
return APR_EINIT;
}
+ if (!apr_pool_parent_get(lib->pool)) {
+ return APR_EBUSY;
+ }
rv = APR_ENOTIMPL;
#if APU_HAVE_OPENSSL
@@ -560,12 +575,15 @@ APR_DECLARE(apr_status_t) apr_crypto_lib_term(const char *name)
}
if (!name) {
+ apr_status_t rv = APR_SUCCESS;
apr_hash_index_t *hi = apr_hash_first(NULL, active_libs);
for (; hi; hi = apr_hash_next(hi)) {
- name = apr_hash_this_key(hi);
- crypto_lib_term(name);
+ apr_status_t rt = crypto_lib_term(apr_hash_this_key(hi));
+ if (rt != APR_SUCCESS && (rv == APR_SUCCESS || rv == APR_EBUSY)) {
+ rv = rt;
+ }
}
- return APR_SUCCESS;
+ return rv;
}
return crypto_lib_term(name);