This is an automated email from the ASF dual-hosted git repository. mxmanghi pushed a commit to branch quattuor in repository https://gitbox.apache.org/repos/asf/tcl-rivet.git
commit f3d0fd05a87ff697a8399ed842e1662be837de3c Author: Massimo Manghi <mxman...@apache.org> AuthorDate: Sun Feb 4 23:39:29 2024 +0100 now calling Rivet_RunChildScripts to execute also rivet_child_exit_script --- ChangeLog | 13 ++++++ src/mod_rivet_ng/rivetCore.c | 6 +-- src/mod_rivet_ng/rivet_lazy_mpm.c | 31 ++++++++++---- src/mod_rivet_ng/rivet_prefork_mpm.c | 6 +++ src/mod_rivet_ng/rivet_worker_mpm.c | 72 +++++++++++++++----------------- src/mod_rivet_ng/worker_prefork_common.c | 70 +++++++++++++++++++++++++++++++ tests/README | 4 +- 7 files changed, 149 insertions(+), 53 deletions(-) diff --git a/ChangeLog b/ChangeLog index 58c17f1..dca3b0a 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,16 @@ +<<<<<<< HEAD +======= +2024-02-04 Massimo Manghi <mxman...@apache.org> + * src/mod_rivet_ng/rivet_prefork_mpm.c: + * src/mod_rivet_ng/rivet_worker_mpm.c: + * src/mod_rivet_ng/worker_prefork_common.c: now calling the + new function Rivet_RunChildScripts to execute + both rivet_child_init_script and rivet_child_exit_script + +2024-01-05 Massimo Manghi <mxman...@apache.org> + * VERSION: bumped version number as 3.2.4 + +>>>>>>> 1bdb883 (now calling Rivet_RunChildScripts to execute also rivet_child_exit_script) 2023-11-12 Massimo Manghi <mxman...@apache.org> * .appveyor.yml: Attemping to fix Visual Studio generator version diff --git a/src/mod_rivet_ng/rivetCore.c b/src/mod_rivet_ng/rivetCore.c index 82fba23..f64779e 100644 --- a/src/mod_rivet_ng/rivetCore.c +++ b/src/mod_rivet_ng/rivetCore.c @@ -1761,8 +1761,8 @@ TCL_CMD_HEADER( Rivet_InspectCmd ) * * log_error priority message * - * priority can be one of "emerg", "alert", "crit", "err", - * "warning", "notice", "info", "debug" + * priority can be one of "emerg","alert","crit","err", + * "warning","notice","info","debug" * * Results: * A message is logged to the Apache error log. @@ -1777,7 +1777,7 @@ TCL_CMD_HEADER(Rivet_LogErrorCmd) server_rec *serverRec; int loglevelindex; - int apLogLevel = 0; + int apLogLevel = 0; static CONST86 char *logLevel[] = { "emerg", diff --git a/src/mod_rivet_ng/rivet_lazy_mpm.c b/src/mod_rivet_ng/rivet_lazy_mpm.c index 651a70a..fb9d47e 100644 --- a/src/mod_rivet_ng/rivet_lazy_mpm.c +++ b/src/mod_rivet_ng/rivet_lazy_mpm.c @@ -131,26 +131,41 @@ static void Lazy_RunConfScript (rivet_thread_private* private,lazy_tcl_worker* w case child_global: function = w->conf->rivet_global_init_script; break; case child_init: function = w->conf->rivet_child_init_script; - break; + break; case child_exit: function = w->conf->rivet_child_exit_script; } if (function) { + rivet_interp_globals* globals = NULL; tcl_conf_script = Tcl_NewStringObj(function,-1); Tcl_IncrRefCount(tcl_conf_script); + /* before we run a script we have to store the pointer to the + * running configuration in the thread private data. The design has + * to improve and running a script must have everything sanely + * prepared TODO + */ + + globals = Tcl_GetAssocData(interp,"rivet",NULL); + + /* + * The current server record is stored to enable ::rivet::apache_log_error and + * other commands to log error messages in the virtual host's designated log file + */ + + globals->server = w->server; + if (Tcl_EvalObjEx(interp,tcl_conf_script, 0) != TCL_OK) { char* errmsg = "rivet_lazy_mpm.so: Error in configuration script: %s"; server_rec* root_server = module_globals->server; - ap_log_error(APLOG_MARK, APLOG_ERR, APR_EGENERAL,root_server, - errmsg, function); - ap_log_error(APLOG_MARK, APLOG_ERR, APR_EGENERAL,root_server, - "errorCode: %s", Tcl_GetVar(interp, "errorCode", 0)); - ap_log_error(APLOG_MARK, APLOG_ERR, APR_EGENERAL,root_server, - "errorInfo: %s", Tcl_GetVar(interp, "errorInfo", 0)); + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,root_server,errmsg,function); + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,root_server, + "errorCode: %s",Tcl_GetVar(interp,"errorCode",0)); + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,root_server, + "errorInfo: %s",Tcl_GetVar(interp,"errorInfo",0)); } Tcl_DecrRefCount(tcl_conf_script); @@ -209,7 +224,7 @@ static void* APR_THREAD_FUNC request_processor (apr_thread_t *thd, void *data) Rivet_PerInterpInit(private->ext->interp,private,w->server,private->pool); - /* The child initialization is fired. Beware of the terminologic + /* The child initialization is fired. Beware the terminological * trap: we inherited from fork capable systems the term 'child' * meaning 'child process'. In this case the child init actually * is a worker thread initialization, because in a threaded module diff --git a/src/mod_rivet_ng/rivet_prefork_mpm.c b/src/mod_rivet_ng/rivet_prefork_mpm.c index c65257d..cfc260b 100644 --- a/src/mod_rivet_ng/rivet_prefork_mpm.c +++ b/src/mod_rivet_ng/rivet_prefork_mpm.c @@ -36,6 +36,9 @@ extern DLLIMPORT mod_rivet_globals* module_globals; extern DLLIMPORT apr_threadkey_t* rivet_thread_key; module rivet_module; +rivet_thread_private* Rivet_VirtualHostsInterps (rivet_thread_private* private); +void Rivet_RunChildScripts (rivet_thread_private* private,bool init); + extern TclWebRequest* TclWeb_NewRequestObject (apr_pool_t *p); /* @@ -299,6 +302,9 @@ rivet_thread_interp* MPM_MasterInterp(server_rec* server) int PreforkBridge_ExitHandler(rivet_thread_private* private) { + + Rivet_RunChildScripts(private,false); + Tcl_Exit(private->exit_status); /* actually we'll never get here but we return diff --git a/src/mod_rivet_ng/rivet_worker_mpm.c b/src/mod_rivet_ng/rivet_worker_mpm.c index 887ef67..4b377a0 100644 --- a/src/mod_rivet_ng/rivet_worker_mpm.c +++ b/src/mod_rivet_ng/rivet_worker_mpm.c @@ -57,6 +57,9 @@ apr_threadkey_t* handler_thread_key; int round(double d) { return (int)(d + 0.5); } #endif /* RIVET_NO_HAVE_ROUND */ +rivet_thread_private* Rivet_VirtualHostsInterps (rivet_thread_private* private); +void Rivet_RunChildScripts (rivet_thread_private* private,bool init); + typedef struct mpm_bridge_status { apr_thread_t* supervisor; int server_shutdown; @@ -260,8 +263,8 @@ static void Worker_CreateInterps (rivet_thread_private* private,rivet_thread_int } -/*-- request_processor - * +/* + * -- request_processor */ static void* APR_THREAD_FUNC request_processor (apr_thread_t *thd, void *data) @@ -377,6 +380,8 @@ static void* APR_THREAD_FUNC request_processor (apr_thread_t *thd, void *data) } while (private->ext->keep_going); thread_obj->status = child_exit; + Rivet_RunChildScripts(private,false); + apr_thread_mutex_unlock(thread_obj->mutex); ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, module_globals->server, "processor thread orderly exit"); @@ -445,38 +450,11 @@ static void start_thread_pool (int nthreads) } } -/* -- supervisor_chores - * - */ - -#if 0 -static void supervisor_housekeeping (void) -{ - int nruns = module_globals->num_load_samples; - double devtn; - double count; - - if (nruns == 60) - { - nruns = 0; - module_globals->average_working_threads = 0; - } - - ++nruns; - count = (int) apr_atomic_read32(module_globals->running_threads_count); - - devtn = ((double)count - module_globals->average_working_threads); - module_globals->average_working_threads += devtn / (double)nruns; - module_globals->num_load_samples = nruns; -} -#endif - - /* -- threaded_bridge_supervisor * - * This function runs within a single thread and to the - * start and stop of Tcl worker thread pool. It could be extended also - * provide some basic monitoring data. + * This function runs within a single thread abd manages the + * Tcl worker thread pool. It could be extended also + * to provide some basic monitoring data. * * As we don't delete Tcl interpreters anymore because it can lead * to seg faults or delays the supervisor threads doesn't restart @@ -793,7 +771,8 @@ apr_status_t Worker_Bridge_Finalize (void* data) rv = apr_thread_join (&thread_status,module_globals->mpm->supervisor); if (rv != APR_SUCCESS) { - ap_log_error(APLOG_MARK,APLOG_ERR,rv,s,MODNAME": Error joining supervisor thread"); + ap_log_error(APLOG_MARK,APLOG_ERR,rv,s, + MODNAME": Error joining worker bridge supervisor thread"); } return OK; @@ -823,15 +802,11 @@ int Worker_Bridge_ExitHandler(rivet_thread_private* private) private->ext->keep_going = 0; - //module_globals->mpm->exit_command = 1; - //module_globals->mpm->exit_command_status = private->exit_status; - if (!module_globals->single_thread_exit) { module_globals->mpm->skip_thread_on_exit = 1; - /* We now tell the supervisor to terminate the Tcl worker thread pool to exit - * and is sequence the whole process to shutdown by calling exit() */ + /* We now tell the supervisor to terminate the Tcl worker thread pool */ Worker_Bridge_Finalize (private->r->server); @@ -846,7 +821,26 @@ int Worker_Bridge_ExitHandler(rivet_thread_private* private) return TCL_OK; } -rivet_thread_interp* Worker_Bridge_Interp (rivet_thread_private* private, +/* + * -- WorkerBridge_Interp + * + * Either returns the rivet_thread_interp object that's going + * to run the script or stores in the bridge data the interpreter + * associated to a specific rivet_server_conf record + * + * Arguments: - rivet_thread_private* private: thread private data + * - rivet_server_conf* conf: virtual host configuration + * - rivet_thread_interp* interp: If not NULL stores the interpreter + * in the bridge data. + * Returned value: rivet_thread_interp* + * In any case the function returns + * the rivet_thread_interp + * object associated with the virtual host + * configuration + * + */ + +rivet_thread_interp* Worker_Bridge_Interp (rivet_thread_private* private, rivet_server_conf* conf, rivet_thread_interp* interp) { diff --git a/src/mod_rivet_ng/worker_prefork_common.c b/src/mod_rivet_ng/worker_prefork_common.c index ec92c33..c466695 100644 --- a/src/mod_rivet_ng/worker_prefork_common.c +++ b/src/mod_rivet_ng/worker_prefork_common.c @@ -67,6 +67,71 @@ Rivet_DuplicateVHostInterp(apr_pool_t* pool, rivet_thread_interp* source_obj) return interp_obj; } +/* -- Rivet_RunChildExitScripts + * + * + */ + +void Rivet_RunChildScripts (rivet_thread_private* private,bool init) +{ + server_rec* vhost_server; + server_rec* root_server; + rivet_server_conf* root_server_conf; + void* parentfunction; /* this is topmost initialization script */ + void* function; + + root_server = module_globals->server; + root_server_conf = RIVET_SERVER_CONF (root_server->module_config); + + parentfunction = (init ? root_server_conf->rivet_child_init_script : root_server_conf->rivet_child_exit_script); + for (vhost_server = root_server; vhost_server != NULL; vhost_server = vhost_server->next) + { + rivet_thread_interp* rivet_interp; + rivet_server_conf* myrsc; + rivet_interp_globals* globals = NULL; + + myrsc = RIVET_SERVER_CONF(vhost_server->module_config); + rivet_interp = RIVET_PEEK_INTERP(private,myrsc); + function = (init ? myrsc->rivet_child_init_script : myrsc->rivet_child_exit_script); + if (function && + (vhost_server == root_server || module_globals->separate_virtual_interps || function != parentfunction)) + { + char* errmsg = MODNAME ": Error in Child init script: %s"; + Tcl_Obj* tcl_script_obj = Tcl_NewStringObj(function,-1); + + Tcl_IncrRefCount(tcl_script_obj); + Tcl_Preserve (rivet_interp->interp); + + /* before we run a script we have to store the pointer to the + * running configuration in the thread private data. The design has + * to improve and running a script must have everything sanely + * prepared TODO + */ + + globals = Tcl_GetAssocData(rivet_interp->interp, "rivet", NULL); + + /* + * The current server record is stored to enable ::rivet::apache_log_error and + * other commands to log error messages in the virtual host's designated log file + */ + + globals->server = vhost_server; + private->running_conf = myrsc; + + if (Tcl_EvalObjEx(rivet_interp->interp,tcl_script_obj,0) != TCL_OK) { + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,vhost_server,errmsg, function); + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,vhost_server, + "errorCode: %s", Tcl_GetVar(rivet_interp->interp,"errorCode",0)); + ap_log_error(APLOG_MARK,APLOG_ERR,APR_EGENERAL,vhost_server, + "errorInfo: %s", Tcl_GetVar(rivet_interp->interp,"errorInfo",0)); + } + Tcl_Release (rivet_interp->interp); + Tcl_DecrRefCount(tcl_script_obj); + + } + } +} + /* -- Rivet_VirtualHostsInterps * * The server_rec chain is walked through and server configurations are read to @@ -105,6 +170,8 @@ rivet_thread_private* Rivet_SetupInterps (rivet_thread_private* private) parentfunction = root_server_conf->rivet_child_init_script; + /* then we proceed assigning/creating the interpreters for each virtual host */ + for (vhost_server = root_server; vhost_server != NULL; vhost_server = vhost_server->next) { rivet_server_conf* rsc; @@ -195,6 +262,9 @@ rivet_thread_private* Rivet_SetupInterps (rivet_thread_private* private) Tcl_DecrRefCount(tcl_child_init); } } + + /* the child init scripts get evaluated */ + Rivet_RunChildScripts(private,true); return private; } diff --git a/tests/README b/tests/README index a0d1fc0..0fffd86 100644 --- a/tests/README +++ b/tests/README @@ -1,8 +1,6 @@ Test Suite for Rivet ==================== -$Id$ - These tests are intended to automate the testing of core Rivet features. They are not complete at this point, and work on them would be welcome. @@ -21,7 +19,7 @@ be compiled into Apache for this to work. For example: -./runtest.tcl /usr/sbin/apache +./runtest.tcl /usr/sbin/apache -mpm prefork Where to put tests/which files are which: ---------------------------------------- --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@tcl.apache.org For additional commands, e-mail: commits-h...@tcl.apache.org