#define AP_MPMQ_HAS_SERF 16 /* MPM can drive serf internally */
/**
- * Query a property of the current MPM.
+ * Query a property of the current MPM.
* @param query_code One of APM_MPMQ_*
* @param result A location to place the result of the query
- * @return APR_SUCCESS or APR_ENOTIMPL
+ * @return APR_EGENERAL if an mpm-query hook has not been registered;
+ * APR_SUCCESS or APR_ENOTIMPL otherwise
+ * @remark The MPM doesn't register the implementing hook until the
+ * register_hooks hook is called, so modules cannot use ap_mpm_query()
+ * until after that point.
* @fn int ap_mpm_query(int query_code, int *result)
*/
AP_DECLARE(apr_status_t) ap_mpm_query(int query_code, int *result);
/* pass control to the MPM */
AP_DECLARE_HOOK(int, mpm, (apr_pool_t *pconf, apr_pool_t *plog, server_rec *s))
-/* implement the mpm query function */
-AP_DECLARE_HOOK(apr_status_t, mpm_query, (int query_code, int *result))
+/* implement the ap_mpm_query() function
+ * The MPM should return OK+APR_ENOTIMPL for any unimplemented query codes;
+ * modules which intercede for specific query codes should DECLINE for others.
+ */
+AP_DECLARE_HOOK(int, mpm_query, (int query_code, int *result, apr_status_t *rv))
/* child specified by index has been killed */
AP_DECLARE_HOOK(apr_status_t, mpm_note_child_killed, (int childnum))
AP_DECLARE_HOOK(apr_status_t, mpm_register_timed_callback,
(apr_time_t t, ap_mpm_callback_fn_t *cbfn, void *baton))
-/* get MPM name */
+/* get MPM name (e.g., "prefork" or "event") */
AP_DECLARE_HOOK(const char *,mpm_get_name,(void))
#ifdef __cplusplus
}
}
-static apr_status_t event_query(int query_code, int *result)
+static int event_query(int query_code, int *result, apr_status_t *rv)
{
+ *rv = APR_SUCCESS;
switch (query_code) {
case AP_MPMQ_MAX_DAEMON_USED:
*result = max_daemons_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_THREADED:
*result = AP_MPMQ_STATIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_FORKED:
*result = AP_MPMQ_DYNAMIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_ASYNC:
*result = 1;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HAS_SERF:
*result = 1;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_DAEMONS:
*result = server_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_THREADS:
*result = thread_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_THREADS:
*result = threads_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_THREADS:
*result = min_spare_threads;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_THREADS:
*result = max_spare_threads;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_REQUESTS_DAEMON:
*result = ap_max_requests_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_DAEMONS:
*result = ap_daemons_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MPM_STATE:
*result = mpm_state;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_GENERATION:
*result = my_generation;
- return APR_SUCCESS;
+ break;
+ default:
+ *rv = APR_ENOTIMPL;
+ break;
}
- return APR_ENOTIMPL;
+ return OK;
}
static apr_status_t event_note_child_killed(int childnum)
#define SAFE_ACCEPT(stmt) do {stmt;} while(0)
#endif
-static apr_status_t prefork_query(int query_code, int *result)
+static int prefork_query(int query_code, int *result, apr_status_t *rv)
{
+ *rv = APR_SUCCESS;
switch(query_code){
case AP_MPMQ_MAX_DAEMON_USED:
*result = ap_daemons_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_THREADED:
*result = AP_MPMQ_NOT_SUPPORTED;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_FORKED:
*result = AP_MPMQ_DYNAMIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_DAEMONS:
*result = server_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_THREADS:
*result = HARD_THREAD_LIMIT;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_THREADS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_DAEMONS:
*result = ap_daemons_min_free;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_THREADS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_DAEMONS:
*result = ap_daemons_max_free;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_THREADS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_REQUESTS_DAEMON:
*result = ap_max_requests_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_DAEMONS:
*result = server_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MPM_STATE:
*result = mpm_state;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_GENERATION:
*result = my_generation;
- return APR_SUCCESS;
+ break;
+ default:
+ *rv = APR_ENOTIMPL;
+ break;
}
- return APR_ENOTIMPL;
+ return OK;
}
static apr_status_t prefork_note_child_killed(int childnum)
return simple_main_loop(sc);
}
-static apr_status_t simple_query(int query_code, int *result)
+static int simple_query(int query_code, int *result, apr_status_t *rv)
{
simple_core_t *sc = simple_core_get();
+ *rv = APR_SUCCESS;
switch (query_code) {
case AP_MPMQ_IS_THREADED:
*result = AP_MPMQ_STATIC;
- return APR_SUCCESS;
break;
case AP_MPMQ_IS_FORKED:
*result = AP_MPMQ_DYNAMIC;
- return APR_SUCCESS;
break;
case AP_MPMQ_IS_ASYNC:
*result = 1;
- return APR_SUCCESS;
break;
case AP_MPMQ_MAX_DAEMON_USED:
*result = sc->procmgr.proc_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_HARD_LIMIT_DAEMONS:
*result = sc->procmgr.proc_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_HARD_LIMIT_THREADS:
*result = sc->procmgr.thread_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MAX_THREADS:
*result = sc->procmgr.thread_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MAX_SPARE_DAEMONS:
*result = sc->procmgr.proc_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MIN_SPARE_DAEMONS:
*result = sc->procmgr.proc_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MIN_SPARE_THREADS:
case AP_MPMQ_MAX_SPARE_THREADS:
*result = sc->procmgr.thread_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MAX_REQUESTS_DAEMON:
*result = sc->procmgr.max_requests_per_child;
- return APR_SUCCESS;
break;
case AP_MPMQ_MAX_DAEMONS:
*result = sc->procmgr.proc_count;
- return APR_SUCCESS;
break;
case AP_MPMQ_MPM_STATE:
*result = sc->mpm_state;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_GENERATION:
*result = 0;
- return APR_SUCCESS;
+ break;
default:
+ *rv = APR_ENOTIMPL;
break;
}
-
- return APR_ENOTIMPL;
+ return OK;
}
static const char *
* service after we preflight the config.
*/
-static apr_status_t winnt_query(int query_code, int *result)
+static int winnt_query(int query_code, int *result, apr_status_t *rv)
{
- switch(query_code){
+ *rv = APR_SUCCESS;
+ switch (query_code) {
case AP_MPMQ_MAX_DAEMON_USED:
*result = MAXIMUM_WAIT_OBJECTS;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_THREADED:
*result = AP_MPMQ_STATIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_FORKED:
*result = AP_MPMQ_NOT_SUPPORTED;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_DAEMONS:
*result = HARD_SERVER_LIMIT;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_THREADS:
*result = thread_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_THREADS:
*result = ap_threads_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_THREADS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_THREADS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_REQUESTS_DAEMON:
*result = ap_max_requests_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MPM_STATE:
*result = winnt_mpm_state;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_GENERATION:
*result = my_generation;
- return APR_SUCCESS;
+ break;
+ default:
+ *rv = APR_ENOTIMPL;
+ break;
}
- return APR_ENOTIMPL;
+ return OK;
}
static const char *winnt_get_name(void)
}
}
-static apr_status_t worker_query(int query_code, int *result)
+static int worker_query(int query_code, int *result, apr_status_t *rv)
{
- switch(query_code){
+ *rv = APR_SUCCESS;
+ switch (query_code) {
case AP_MPMQ_MAX_DAEMON_USED:
*result = max_daemons_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_THREADED:
*result = AP_MPMQ_STATIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_IS_FORKED:
*result = AP_MPMQ_DYNAMIC;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_DAEMONS:
*result = server_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_HARD_LIMIT_THREADS:
*result = thread_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_THREADS:
*result = threads_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MIN_SPARE_THREADS:
*result = min_spare_threads;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_DAEMONS:
*result = 0;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_SPARE_THREADS:
*result = max_spare_threads;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_REQUESTS_DAEMON:
*result = ap_max_requests_per_child;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MAX_DAEMONS:
*result = ap_daemons_limit;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_MPM_STATE:
*result = mpm_state;
- return APR_SUCCESS;
+ break;
case AP_MPMQ_GENERATION:
*result = my_generation;
- return APR_SUCCESS;
+ break;
+ default:
+ *rv = APR_ENOTIMPL;
+ break;
}
- return APR_ENOTIMPL;
+ return OK;
}
static apr_status_t worker_note_child_killed(int childnum)
AP_IMPLEMENT_HOOK_RUN_FIRST(int, mpm,
(apr_pool_t *pconf, apr_pool_t *plog, server_rec *s),
(pconf, plog, s), DECLINED)
-AP_IMPLEMENT_HOOK_RUN_FIRST(apr_status_t, mpm_query,
- (int query_code, int *result),
- (query_code, result), APR_ENOTIMPL)
+AP_IMPLEMENT_HOOK_RUN_FIRST(int, mpm_query,
+ (int query_code, int *result, apr_status_t *_rv),
+ (query_code, result, _rv), DECLINED)
AP_IMPLEMENT_HOOK_RUN_FIRST(apr_status_t, mpm_note_child_killed,
(int childnum),
(childnum), APR_ENOTIMPL)
AP_DECLARE(apr_status_t) ap_mpm_query(int query_code, int *result)
{
- return ap_run_mpm_query(query_code, result);
+ apr_status_t rv;
+
+ if (ap_run_mpm_query(query_code, result, &rv) == DECLINED) {
+ rv = APR_EGENERAL;
+ }
+
+ return rv;
}
AP_DECLARE(apr_status_t) ap_mpm_note_child_killed(int childnum)