You are viewing a plain text version of this content. The canonical link for it is here.
Posted to apache-bugdb@apache.org by Vladislav Malyshkin <ma...@mail1.nai.net> on 2000/04/08 03:30:01 UTC

Re: mod_jserv/5755: mod_jserv and httpd -HUP restarting problem

The following reply was made to PR mod_jserv/5755; it has been noted by GNATS.

From: Vladislav Malyshkin <ma...@mail1.nai.net>
To: Neil_Mckee@inmon.com, apbugs@apache.org, ed@cloudfactory.org
Cc:  
Subject: Re: mod_jserv/5755: mod_jserv and httpd -HUP restarting problem
Date: Fri, 07 Apr 2000 21:23:32 -0400

 >
 > We were seeing the same problem - where multiple SIGHUPs
 > cause mod_jserv to lose track.  I tried changing
 > /etc/logrotate.d/apache to use "kill -HUP `cat /var/run/httpd.pid`"
 > instead of "killall -HUP httpd" but that only seems
 > to work if only one log is being rotated.
 >
 
 It also fails to rotate if you send several
 kill -HUP `cat /var/run/httpd.pid`
 (when you send next -HUP while the server is processing previos -HUP)
 This is precisely what happenes when you rotate sevaral apache logs.
 For each log roateted logrotate send a -HUP signal.
 And while apache processes -HUP sent after access_log was rotated
 it receives -HUP caused by error_log rotation.
 This kills the watchdog of JVM and you get a runaway JVM.
 
 This is the patch I use to fix this problem.
 It fixes this runaway problem.
 Also, even if you have a runaway JVM this
 modification  of watchdog will send an EXIT command to it,
 so it will not be a problem even in this case.
 
 Vladislav
 
 The patch is:
 
 --- ApacheJServ-1.1/src/c/jserv_wrapper_unix.c.orig     Mon Feb 14 16:16:11 2000
 +++ ApacheJServ-1.1/src/c/jserv_wrapper_unix.c  Tue Mar  7 13:54:28 2000
 @@ -84,6 +84,10 @@
  /* Signal handler for SIGTERM (standalone wrapper), and for Apache 1.2, for
   * when the parent Apache process dies.   JServ should kill the JVM. */
  void wrapper_shutdown(int x) {
 +    signal(SIGTERM, wrapper_shutdown);
 +    signal(SIGHUP, wrapper_shutdown);
 +    signal(SIGALRM, wrapper_shutdown);
 +
      jserv_error(JSERV_LOG_INFO, wrapper_data->config,
                  "Wrapper: Shutting down JServ (PID=%d) (sig %d)",getpid(), x);
      /* Cleanup this thing */
 @@ -98,10 +102,12 @@
  /* this is also used from the loop to kill JVM                               */
  void kill_hung_jvm(int signum) {
    int counter = 0;
 -
 +  const int jvm_pid_local=jvm_pid;
 +
    /* Is jvm is really started? If not - do nothing */
 -  if( jvm_pid == 0)
 +  if( jvm_pid_local == 0)
      return;
 +  jvm_pid=0;
 
    if( signum == 0) {
      jserv_error(JSERV_LOG_INFO, wrapper_data->config,
 @@ -112,18 +118,17 @@
    }
    /* IF JVM is not responding to connections, we can't do   *
     * anything but kill it.                                  */
 -  kill(jvm_pid, SIGTERM);
 +  kill(jvm_pid_local, SIGTERM);
 
    /* give the VM as long as five seconds to die gracefully */
    while (counter++ < 5) {
 -    if (waitpid(jvm_pid, NULL, WNOHANG) > 0)
 +    if (waitpid(jvm_pid_local, NULL, WNOHANG) > 0)
        break;
      sleep(1);
    }
 -  if( waitpid(jvm_pid,NULL,WNOHANG)==0 ) {
 -    kill(jvm_pid, SIGKILL);
 +  if( waitpid(jvm_pid_local,NULL,WNOHANG)==0 ) {
 +    kill(jvm_pid_local, SIGKILL);
    }
 -  jvm_pid=0;
  }
 
 
 @@ -193,12 +198,13 @@
      if (proc!=0) return proc;
 
      /* Sleep two seconds waiting for first init to finish and to kill this
 -     * process  - TODO remove this and find a nicer soulution to doublestart */
 -    sleep(3);
 -
      /* If we get a TERM signal, shut down the JVM nicely, then exit.
       */
      signal(SIGTERM, wrapper_shutdown);
 +    signal(SIGHUP, wrapper_shutdown);
 +
 +    /* process  - TODO remove this and find a nicer soulution to doublestart */
 +    sleep(3);
 
      x = 5;
      while (binparams != NULL) {
 @@ -340,10 +346,11 @@
          /* Check every second */
          while (1) {
           sighandler_t old_handler;
 +         int ping_result;
 
  #ifndef JSERV_STANDALONE
              /* did parent httpd die? */
 -            if(getppid() == 1) {
 +            if(getppid() <=1 ) {
                  jserv_error(JSERV_LOG_INFO,wrapper_data->config,
                              "wrapper: Apache exited, cleaning up (PID=%d)",
                              getpid());
 @@ -373,19 +380,32 @@
                            in many places.
                          */
                         alarm(wrapper_data->config->vmtimeout);
 -
 -                       /* check if we can communicate to JVM */
 -                       if( jvm_pid != 0 && jserv_protocol_function(wrapper_data->config->protocol,wrapper_data->config,
 -                                                   JSERV_PING,NULL) == JSERV_FUNC_COMMERROR) {
 -
 -                         /* Note that it's harmless that this function is called twice
 -                            in case of timeout
 -                         */
 -                         kill_hung_jvm(0);
 -
 -                       }
 
 
 +                       ping_result=jserv_protocol_function(
 +                                wrapper_data->config->protocol,wrapper_data->config,
 +                               JSERV_PING,NULL);
 +
 +                       if(ping_result==JSERV_FUNC_COMMERROR)
 +                         {
 +                           if(jvm_pid != 0)
 +                             {
 +                               /* Note that it's harmless that this function is called twice
 +                                  in case of timeout
 +                               */
 +                               kill_hung_jvm(0);
 +                             }
 +                         }
 +                       else if(jvm_pid == 0)
 +                         {
 +
 +                           signal( SIGALRM, kill_hung_jvm);
 +                           /* Send shutdown function to a runaway JVM. */
 +                           jserv_protocol_function(
 +                                    wrapper_data->config->protocol,wrapper_data->config,
 +                                    JSERV_SHUTDOWN,NULL);
 +                         }
 +
                         /* Remove the signal, no matter if it was used or not */
                         alarm(0);
 
 @@ -477,30 +497,33 @@
  /* ========================================================================= */
  /* This does the actual cleanup */
  int wrapper_shutdown_core(wrapper_config *cfg) {
 -    if (jvm_pid != 0) {
 +
 +  const int jvm_pid_local=jvm_pid;
 +    if (jvm_pid_local != 0) {
          int counter = 0;
 +        jvm_pid=0;
          jserv_error(JSERV_LOG_INFO,wrapper_data->config,
                      "wrapper: Terminating JServ (PID=%d, VM PID=%d)",
 -                    getpid(), jvm_pid);
 +                    getpid(), jvm_pid_local);
          /* Send shutdown function */
          jserv_protocol_function(cfg->config->protocol,cfg->config,
                                  JSERV_SHUTDOWN,NULL);
          /* Wait for child to go down */
 -        while (waitpid(jvm_pid,NULL,WNOHANG)==0) {
 +        while (waitpid(jvm_pid_local,NULL,WNOHANG)==0) {
              /* give it a little while to shut down gracefully. Then kill it. */
              if (++counter > cfg->config->vmtimeout) {
                  jserv_error(JSERV_LOG_EMERG, wrapper_data->config,
                              "wrapper: JServ (%d) didn't die nicely, killing it",
 -                            jvm_pid);
 -                kill(jvm_pid, SIGTERM); /* give the process a chance to die */
 +                            jvm_pid_local);
 +                kill(jvm_pid_local, SIGTERM); /* give the process a chance to die */
                  counter = 0;
                  while (counter++ < 3) {
 -                    if (waitpid(jvm_pid, NULL, WNOHANG) > 0)
 +                    if (waitpid(jvm_pid_local, NULL, WNOHANG) > 0)
                          return 0;
                      sleep(1);
                  }
 -                if( waitpid(jvm_pid,NULL,WNOHANG)==0 ) {
 -                    kill(jvm_pid, SIGKILL);
 +                if( waitpid(jvm_pid_local,NULL,WNOHANG)==0 ) {
 +                    kill(jvm_pid_local, SIGKILL);
                  }
              }
              sleep(1);
 
 
 
 >
 >