diff options
-rw-r--r-- | server/mpm/winnt/mpm_winnt.c | 7 | ||||
-rw-r--r-- | server/mpm/winnt/mpm_winnt.h | 2 | ||||
-rw-r--r-- | server/mpm/winnt/service.c | 59 |
3 files changed, 50 insertions, 18 deletions
diff --git a/server/mpm/winnt/mpm_winnt.c b/server/mpm/winnt/mpm_winnt.c index 0f54e2c46b..cf8f8af365 100644 --- a/server/mpm/winnt/mpm_winnt.c +++ b/server/mpm/winnt/mpm_winnt.c @@ -2213,6 +2213,7 @@ static int winnt_post_config(apr_pool_t *pconf_, apr_pool_t *plog, apr_pool_t *p /* Handle the following SCM aspects in this phase: * * -k install + * -k config * -k start * -k restart * -k runservice [Win95, only once - after we parsed the config] @@ -2225,7 +2226,11 @@ static int winnt_post_config(apr_pool_t *pconf_, apr_pool_t *plog, apr_pool_t *p */ if (!strcasecmp(signal_arg, "install")) { - rv = mpm_service_install(ptemp, inst_argc, inst_argv); + rv = mpm_service_install(ptemp, inst_argc, inst_argv, 0); + exit (rv); + } + if (!strcasecmp(signal_arg, "config")) { + rv = mpm_service_install(ptemp, inst_argc, inst_argv, 1); exit (rv); } diff --git a/server/mpm/winnt/mpm_winnt.h b/server/mpm/winnt/mpm_winnt.h index 9fc45abc01..26397db7ad 100644 --- a/server/mpm/winnt/mpm_winnt.h +++ b/server/mpm/winnt/mpm_winnt.h @@ -99,7 +99,7 @@ apr_status_t mpm_merge_service_args(apr_pool_t *p, apr_array_header_t *args, apr_status_t mpm_service_to_start(const char **display_name, apr_pool_t *p); apr_status_t mpm_service_started(void); apr_status_t mpm_service_install(apr_pool_t *ptemp, int argc, - char const* const* argv); + char const* const* argv, int reconfig); apr_status_t mpm_service_uninstall(void); apr_status_t mpm_service_start(apr_pool_t *ptemp, int argc, diff --git a/server/mpm/winnt/service.c b/server/mpm/winnt/service.c index 0e6ca2947a..0981d6ad05 100644 --- a/server/mpm/winnt/service.c +++ b/server/mpm/winnt/service.c @@ -775,14 +775,15 @@ void mpm_service_stopping(void) apr_status_t mpm_service_install(apr_pool_t *ptemp, int argc, - const char * const * argv) + const char * const * argv, int reconfig) { char key_name[MAX_PATH]; char exe_path[MAX_PATH]; char *launch_cmd; apr_status_t(rv); - fprintf(stderr,"Installing the %s service\n", mpm_display_name); + fprintf(stderr,reconfig ? "Reconfiguring the %s service\n" + : "Installing the %s service\n", mpm_display_name); if (GetModuleFileName(NULL, exe_path, sizeof(exe_path)) == 0) { @@ -809,12 +810,37 @@ apr_status_t mpm_service_install(apr_pool_t *ptemp, int argc, launch_cmd = apr_psprintf(ptemp, "\"%s\" -k runservice", exe_path); - /* RPCSS is the Remote Procedure Call (RPC) Locator required for DCOM - * communication pipes. I am far from convinced we should add this to - * the default service dependencies, but be warned that future apache - * modules or ISAPI dll's may depend on it. - */ - schService = CreateService(schSCManager, // SCManager database + if (reconfig) { + schService = OpenService(schSCManager, mpm_service_name, + SERVICE_ALL_ACCESS); + if (!schService) { + ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_ERR, + apr_get_os_error(), NULL, + "OpenService failed"); + } + else if (!ChangeServiceConfig(schService, + SERVICE_WIN32_OWN_PROCESS, + SERVICE_AUTO_START, + SERVICE_ERROR_NORMAL, + launch_cmd, NULL, NULL, + "Tcpip\0Afd\0", NULL, NULL, + mpm_display_name)) { + ap_log_error(APLOG_MARK, APLOG_ERR|APLOG_ERR, + apr_get_os_error(), NULL, + "ChangeServiceConfig failed"); + /* !schService aborts configuration below */ + CloseServiceHandle(schService); + schService = NULL; + } + } + else { + /* RPCSS is the Remote Procedure Call (RPC) Locator required + * for DCOM communication pipes. I am far from convinced we + * should add this to the default service dependencies, but + * be warned that future apache modules or ISAPI dll's may + * depend on it. + */ + schService = CreateService(schSCManager, // SCManager database mpm_service_name, // name of service mpm_display_name, // name to display SERVICE_ALL_ACCESS, // access required @@ -828,15 +854,16 @@ apr_status_t mpm_service_install(apr_pool_t *ptemp, int argc, NULL, // use SYSTEM account NULL); // no password - if (!schService) - { - rv = apr_get_os_error(); - ap_log_error(APLOG_MARK, APLOG_ERR | APLOG_STARTUP, rv, NULL, - "Failed to create WinNT Service Profile"); - CloseServiceHandle(schSCManager); - return (rv); + if (!schService) + { + rv = apr_get_os_error(); + ap_log_error(APLOG_MARK, APLOG_ERR | APLOG_STARTUP, rv, NULL, + "Failed to create WinNT Service Profile"); + CloseServiceHandle(schSCManager); + return (rv); + } } - + CloseServiceHandle(schService); CloseServiceHandle(schSCManager); } |