View | Details | Raw Unified | Return to bug 39329
Collapse All | Expand All

(-)modules/database/mod_dbd.c.orig (-11 / +30 lines)
Lines 433-438 Link Here
433
    svr_cfg *svr = ap_get_module_config(s->module_config, &dbd_module);
432
    svr_cfg *svr = ap_get_module_config(s->module_config, &dbd_module);
434
    apr_status_t rv = APR_SUCCESS;
433
    apr_status_t rv = APR_SUCCESS;
435
    const char *errmsg;
434
    const char *errmsg;
435
    int tries;
436
436
437
    if (!svr->persist) {
437
    if (!svr->persist) {
438
        /* Return a once-only connection */
438
        /* Return a once-only connection */
Lines 445-458 Link Here
445
            return NULL;
445
            return NULL;
446
        }
446
        }
447
    }
447
    }
448
    rv = apr_reslist_acquire(svr->dbpool, &rec);
448
    /* PR#39329: implement retries here
449
    if (rv != APR_SUCCESS) {
449
     * How many times to retry?  Well, svr->nkeep is an absolute max
450
        ap_log_perror(APLOG_MARK, APLOG_ERR, rv, pool,
450
     * for the number of connections that could've gone stale while
451
                      "Failed to acquire DBD connection from pool!");
451
     * the backend remains up.  I guess it could go above that in
452
        return NULL;
452
     * some edge case (the database gets restarted?)
453
    }
453
     * We need 1 try for nkeep = 0 or 1.  Hence the dodgy loop logic.
454
    rv = apr_dbd_check_conn(arec->driver, pool, arec->handle);
454
     *
455
    if ((rv != APR_SUCCESS) && (rv != APR_ENOTIMPL)) {
455
     * This effect of nkeep needs documenting in TFM.
456
     */
457
458
    tries = svr->nkeep;
459
    do {
460
        rv = apr_reslist_acquire(svr->dbpool, &rec);
461
        if (rv != APR_SUCCESS) {
462
            ap_log_perror(APLOG_MARK, APLOG_ERR, rv, pool,
463
                          "Failed to acquire DBD connection from pool!");
464
            break;
465
        }
466
        rv = apr_dbd_check_conn(arec->driver, pool, arec->handle);
467
        /* mysql wants a second mysql_ping to reopen the connection */
468
        if (rv == APR_EGENERAL) {
469
            rv = apr_dbd_check_conn(arec->driver, pool, arec->handle);
470
        }
471
        if ((rv == APR_SUCCESS) || (rv == APR_ENOTIMPL)) {
472
            break;
473
        }
456
        errmsg = apr_dbd_error(arec->driver, arec->handle, rv);
474
        errmsg = apr_dbd_error(arec->driver, arec->handle, rv);
457
        if (!errmsg) {
475
        if (!errmsg) {
458
            errmsg = "(unknown)";
476
            errmsg = "(unknown)";
Lines 460-468 Link Here
460
        ap_log_perror(APLOG_MARK, APLOG_ERR, rv, pool,
478
        ap_log_perror(APLOG_MARK, APLOG_ERR, rv, pool,
461
                      "DBD[%s] Error: %s", svr->name, errmsg );
479
                      "DBD[%s] Error: %s", svr->name, errmsg );
462
        apr_reslist_invalidate(svr->dbpool, rec);
480
        apr_reslist_invalidate(svr->dbpool, rec);
463
        return NULL;
481
    } while (--tries > 0);
464
    }
482
465
    return arec;
483
    return ((rv == APR_SUCCESS) || (rv == APR_ENOTIMPL)) ? arec : NULL;
466
}
484
}
467
#else
485
#else
468
DBD_DECLARE_NONSTD(ap_dbd_t*) ap_dbd_open(apr_pool_t *pool, server_rec *s)
486
DBD_DECLARE_NONSTD(ap_dbd_t*) ap_dbd_open(apr_pool_t *pool, server_rec *s)

Return to bug 39329