From 1dee575fa9754b3fc114d0a06c53c82fcb297886 Mon Sep 17 00:00:00 2001 From: Yann Ylavic Date: Fri, 8 Sep 2017 14:51:44 +0000 Subject: [PATCH] Merge r1799435, r1799437, r1805206, r1805322 from trunk: Allow WatchdogInterval to be sub 1 second Allow finer control over hcheck intervals... minimum is whatever the watchdog slice is. Fix remaining lint from ms capability for hchecks. userland change = we now are OK w/ ms Submitted by: jim Reviewed by: jim, covener, ylavic git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/branches/2.4.x@1807772 13f79535-47bb-0310-9956-ffa450edef68 --- CHANGES | 4 ++++ STATUS | 8 ------- modules/core/mod_watchdog.c | 20 ++++++++++------- modules/proxy/mod_proxy_balancer.c | 15 ++++++++----- modules/proxy/mod_proxy_hcheck.c | 36 +++++++++++++++++------------- 5 files changed, 46 insertions(+), 37 deletions(-) diff --git a/CHANGES b/CHANGES index f6e3a1d1c2..6fa4c307e9 100644 --- a/CHANGES +++ b/CHANGES @@ -1,6 +1,10 @@ -*- coding: utf-8 -*- Changes with Apache 2.4.28 + *) mod_watchdog/mod_proxy_hcheck: Time intervals can now be spefified + down to the millisecond. Supports 'mi' (minute), 'ms' (millisecond), + 's' (second) and 'hr' (hour!) time suffixes. [Jim Jagielski] + *) mod_http2: Fix for stalling when more than 32KB are written to a suspended stream. [Stefan Eissing] diff --git a/STATUS b/STATUS index be642d3486..c74589e708 100644 --- a/STATUS +++ b/STATUS @@ -119,14 +119,6 @@ PATCHES ACCEPTED TO BACKPORT FROM TRUNK: 2.4.x patch: svn merge -c 1801594 ^/httpd/httpd/trunk . +1: jfclere, jim, covener - *) mod_watchdog/mod_proxy_hcheck: Now accept ms interval settings - trunk patch: http://svn.apache.org/r1799435 - http://svn.apache.org/r1799437 - http://svn.apache.org/r1805206 (partial) - http://svn.apache.org/r1805322 - 2.4.x patch: http://home.apache.org/~jim/patches/httpd-2.4-hcheck-ms.patch - +1: jim, covener, ylavic - *) mod_proxy: Name the scheme in the error message when the mod_proxy_foo submodule is missing. trunk patch: http://svn.apache.org/r1745039 diff --git a/modules/core/mod_watchdog.c b/modules/core/mod_watchdog.c index 9f10c0d718..b6deaba306 100644 --- a/modules/core/mod_watchdog.c +++ b/modules/core/mod_watchdog.c @@ -66,7 +66,6 @@ struct wd_server_conf_t static wd_server_conf_t *wd_server_conf = NULL; static apr_interval_time_t wd_interval = AP_WD_TM_INTERVAL; -static int wd_interval_set = 0; static int mpm_is_forked = AP_MPMQ_NOT_SUPPORTED; static const char *wd_proc_mutex_type = "watchdog-callback"; @@ -450,6 +449,9 @@ static int wd_post_config_hook(apr_pool_t *pconf, apr_pool_t *plog, apr_pool_create(&wd_server_conf->pool, ppconf); apr_pool_userdata_set(wd_server_conf, pk, apr_pool_cleanup_null, ppconf); } + ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, APLOGNO(010033) + "Watchdog: Running with WatchdogInterval %" + APR_TIME_T_FMT "ms", apr_time_as_msec(wd_interval)); wd_server_conf->s = s; if ((wl = ap_list_provider_names(pconf, AP_WATCHDOG_PGROUP, AP_WATCHDOG_PVERSION))) { @@ -597,18 +599,20 @@ static void wd_child_init_hook(apr_pool_t *p, server_rec *s) static const char *wd_cmd_watchdog_int(cmd_parms *cmd, void *dummy, const char *arg) { - int i; + apr_status_t rv; const char *errs = ap_check_cmd_context(cmd, GLOBAL_ONLY); if (errs != NULL) return errs; - if (wd_interval_set) - return "Duplicate WatchdogInterval directives are not allowed"; - if ((i = atoi(arg)) < 1) - return "Invalid WatchdogInterval value"; + rv = ap_timeout_parameter_parse(arg, &wd_interval, "s"); + + if (rv != APR_SUCCESS) + return "Unparse-able WatchdogInterval setting"; + if (wd_interval < AP_WD_TM_SLICE) { + return apr_psprintf(cmd->pool, "Invalid WatchdogInterval: minimal value %" + APR_TIME_T_FMT "ms", apr_time_as_msec(AP_WD_TM_SLICE)); + } - wd_interval = apr_time_from_sec(i); - wd_interval_set = 1; return NULL; } diff --git a/modules/proxy/mod_proxy_balancer.c b/modules/proxy/mod_proxy_balancer.c index ec9f103adb..61ff5e4721 100644 --- a/modules/proxy/mod_proxy_balancer.c +++ b/modules/proxy/mod_proxy_balancer.c @@ -22,6 +22,7 @@ #include "apr_version.h" #include "ap_hooks.h" #include "apr_date.h" +#include "mod_watchdog.h" static const char *balancer_mutex_type = "proxy-balancer-shm"; ap_slotmem_provider_t *storage = NULL; @@ -1140,9 +1141,11 @@ static int balancer_handler(request_rec *r) } } if ((val = apr_table_get(params, "w_hi"))) { - int ival = atoi(val); - if (ival >= HCHECK_WATHCHDOG_INTERVAL) { - wsel->s->interval = apr_time_from_sec(ival); + apr_interval_time_t hci; + if (ap_timeout_parameter_parse(val, &hci, "ms") == APR_SUCCESS) { + if (hci >= AP_WD_TM_SLICE) { + wsel->s->interval = hci; + } } } if ((val = apr_table_get(params, "w_hp"))) { @@ -1612,7 +1615,7 @@ static int balancer_handler(request_rec *r) ap_rputs(apr_strfsize(worker->s->read, fbuf), r); if (set_worker_hc_param_f) { ap_rprintf(r, "%s", ap_proxy_show_hcmethod(worker->s->method)); - ap_rprintf(r, "%d", (int)apr_time_sec(worker->s->interval)); + ap_rprintf(r, "%" APR_TIME_T_FMT "ms", apr_time_as_msec(worker->s->interval)); ap_rprintf(r, "%d (%d)", worker->s->passes,worker->s->pcount); ap_rprintf(r, "%d (%d)", worker->s->fails, worker->s->fcount); ap_rprintf(r, "%s", worker->s->hcuri); @@ -1681,8 +1684,8 @@ static int balancer_handler(request_rec *r) ap_rputs("Expr\n\n", r); - ap_rprintf(r, "Interval (secs)\n", (int)apr_time_sec(wsel->s->interval)); + ap_rprintf(r, "Interval (ms)\n", apr_time_as_msec(wsel->s->interval)); ap_rprintf(r, "Passes trigger\n", wsel->s->passes); ap_rprintf(r, "Fails trigger)templates->elts; for (ival = 0; ival < ctx->templates->nelts; ival++, template++) { - if (!strcasecmp(template->name, val)) { + if (!ap_cstr_casecmp(template->name, val)) { if (worker) { worker->s->method = template->method; worker->s->interval = template->interval; @@ -137,7 +139,7 @@ static const char *set_worker_hc_param(apr_pool_t *p, else if (!strcasecmp(key, "hcmethod")) { proxy_hcmethods_t *method = proxy_hcmethods; for (; method->name; method++) { - if (!strcasecmp(val, method->name)) { + if (!ap_cstr_casecmp(val, method->name)) { if (!method->implemented) { return apr_psprintf(p, "Health check method %s not (yet) implemented", val); @@ -153,14 +155,18 @@ static const char *set_worker_hc_param(apr_pool_t *p, return "Unknown method"; } else if (!strcasecmp(key, "hcinterval")) { - ival = atoi(val); - if (ival < HCHECK_WATHCHDOG_INTERVAL) - return apr_psprintf(p, "Interval must be a positive value greater than %d seconds", - HCHECK_WATHCHDOG_INTERVAL); + apr_interval_time_t hci; + apr_status_t rv; + rv = ap_timeout_parameter_parse(val, &hci, "s"); + if (rv != APR_SUCCESS) + return "Unparse-able hcinterval setting"; + if (hci < AP_WD_TM_SLICE) + return apr_psprintf(p, "Interval must be a positive value greater than %" + APR_TIME_T_FMT "ms", apr_time_as_msec(AP_WD_TM_SLICE)); if (worker) { - worker->s->interval = apr_time_from_sec(ival); + worker->s->interval = hci; } else { - temp->interval = apr_time_from_sec(ival); + temp->interval = hci; } } else if (!strcasecmp(key, "hcpasses")) { @@ -555,10 +561,10 @@ static apr_status_t backend_cleanup(const char *proxy_function, proxy_conn_rec * backend->close = 1; ap_proxy_release_connection(proxy_function, backend, s); ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, s, APLOGNO(03251) - "Health check %s Status (%d) for %s.", - ap_proxy_show_hcmethod(backend->worker->s->method), - status, - backend->worker->s->name); + "Health check %s Status (%d) for %s.", + ap_proxy_show_hcmethod(backend->worker->s->method), + status, + backend->worker->s->name); } if (status != OK) { return APR_EGENERAL; @@ -1020,7 +1026,7 @@ static int hc_post_config(apr_pool_t *p, apr_pool_t *plog, continue; } rv = hc_watchdog_register_callback(watchdog, - apr_time_from_sec(HCHECK_WATHCHDOG_INTERVAL), + AP_WD_TM_SLICE, ctx, hc_watchdog_callback); if (rv) { @@ -1137,7 +1143,7 @@ static const char *hc_expr_var_fn(ap_expr_eval_ctx_t *ctx, const void *data) { char *var = (char *)data; - if (var && *var && ctx->r && strcasecmp(var, "BODY") == 0) { + if (var && *var && ctx->r && ap_cstr_casecmp(var, "BODY") == 0) { return hc_get_body(ctx->r); } return NULL; @@ -1148,7 +1154,7 @@ static const char *hc_expr_func_fn(ap_expr_eval_ctx_t *ctx, const void *data, { char *var = (char *)arg; - if (var && *var && ctx->r && strcasecmp(var, "BODY") == 0) { + if (var && *var && ctx->r && ap_cstr_casecmp(var, "BODY") == 0) { return hc_get_body(ctx->r); } return NULL; -- 2.40.0