On Thursday 20 July 2006 23:33, Anton Golubev wrote:

> This configuration (almost taken from documentation) also crashes the
> server:

Not for me it doesn't.  But putting your <Directory> inside a <VirtualHost>
gets the crash.

So the basic issue is that we're using the server_rec when we may not
have it.  In fact, a <Directory> might be valid within more than one
virtualhost, each having a different backend, so we really need to
expunge the server_rec from ap_dbd_prepare.

I've hacked a quick patch against trunk, that saves the definitions
to a global hash and retrieves them at child_init, when the server_rec
is known to be valid.  Will commit if it looks right after reflection:-)

-- 
Nick Kew
Index: mod_dbd.c
===================================================================
--- mod_dbd.c	(revision 424306)
+++ mod_dbd.c	(working copy)
@@ -67,6 +67,8 @@
                cmd_min, cmd_keep, cmd_max, cmd_exp
 } cmd_parts;
 
+static apr_hash_t *dbd_prepared_defns;
+
 /* a default DBDriver value that'll generate meaningful error messages */
 static const char *const no_dbdriver = "[DBDriver unset]";
 
@@ -144,12 +146,13 @@
 DBD_DECLARE_NONSTD(void) ap_dbd_prepare(server_rec *s, const char *query,
                                         const char *label)
 {
-    svr_cfg *svr = ap_get_module_config(s->module_config, &dbd_module);
     dbd_prepared *prepared = apr_pcalloc(s->process->pool, sizeof(dbd_prepared));
     prepared->label = label;
     prepared->query = query;
-    prepared->next = svr->prepared;
-    svr->prepared = prepared;
+    prepared->next = apr_hash_get(dbd_prepared_defns, s->server_hostname,
+                                  APR_HASH_KEY_STRING);
+    apr_hash_set(dbd_prepared_defns, s->server_hostname, APR_HASH_KEY_STRING,
+                 prepared);
 }
 static const char *dbd_prepare(cmd_parms *cmd, void *cfg, const char *query,
                                const char *label)
@@ -351,11 +354,15 @@
 
     return rv;
 }
+#endif
 static apr_status_t dbd_setup_init(apr_pool_t *pool, server_rec *s)
 {
     svr_cfg *svr = ap_get_module_config(s->module_config, &dbd_module);
     apr_status_t rv;
 
+    svr->prepared = apr_hash_get(dbd_prepared_defns, s->server_hostname,
+                                 APR_HASH_KEY_STRING);
+#if APR_HAS_THREADS
     if (!svr->persist) {
         return APR_SUCCESS;
     }
@@ -374,7 +381,11 @@
                       "DBD: Failed to create thread mutex");
     }
     return rv;
+#else
+    return APR_SUCCESS;
+#endif
 }
+#if APR_HAS_THREADS
 static apr_status_t dbd_setup_lock(apr_pool_t *pool, server_rec *s)
 {
     svr_cfg *svr = ap_get_module_config(s->module_config, &dbd_module);
@@ -604,15 +615,14 @@
 
 static void dbd_hooks(apr_pool_t *pool)
 {
-#if APR_HAS_THREADS
     ap_hook_child_init((void*)dbd_setup_init, NULL, NULL, APR_HOOK_MIDDLE);
-#endif
     APR_REGISTER_OPTIONAL_FN(ap_dbd_open);
     APR_REGISTER_OPTIONAL_FN(ap_dbd_close);
     APR_REGISTER_OPTIONAL_FN(ap_dbd_acquire);
     APR_REGISTER_OPTIONAL_FN(ap_dbd_cacquire);
     APR_REGISTER_OPTIONAL_FN(ap_dbd_prepare);
     apr_dbd_init(pool);
+    dbd_prepared_defns = apr_hash_make(pool);
 }
 
 module AP_MODULE_DECLARE_DATA dbd_module = {

Reply via email to