You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by bu...@apache.org on 2005/11/09 23:37:39 UTC

DO NOT REPLY [Bug 37430] New: - Syslog support for jsvc

DO NOT REPLY TO THIS EMAIL, BUT PLEASE POST YOUR BUG�
RELATED COMMENTS THROUGH THE WEB INTERFACE AVAILABLE AT
<http://issues.apache.org/bugzilla/show_bug.cgi?id=37430>.
ANY REPLY MADE TO THIS MESSAGE WILL NOT BE COLLECTED AND�
INSERTED IN THE BUG DATABASE.

http://issues.apache.org/bugzilla/show_bug.cgi?id=37430

           Summary: Syslog support for jsvc
           Product: Tomcat 5
           Version: 5.5.12
          Platform: PC
        OS/Version: Linux
            Status: NEW
          Severity: enhancement
          Priority: P4
         Component: Native:Packaging
        AssignedTo: tomcat-dev@jakarta.apache.org
        ReportedBy: mike@pictage.com


Currently, the only way to rotate the logs produced via jsvc
is to restart the tomcat server. I've coded up support for
using syslog through the local0.* channels. It probably needs
a little work, but hopefully it can be incorporated into a
future release.

--- jsvc-unix.c 2005-05-17 06:13:39.000000000 -0700
+++ /tmp/jsvc-unix.c    2005-11-08 14:18:18.000000000 -0800
@@ -25,6 +25,8 @@
 #include <stdio.h>
 #include <pwd.h>
 #include <grp.h>
+#include <syslog.h>
+#include <errno.h>
 #ifdef OS_LINUX
 #include <sys/prctl.h>
 #include <sys/syscall.h>
@@ -35,6 +37,7 @@
 extern char **environ;

 pid_t controlled=0; /* the son process pid */
+pid_t logger=0;     /* the logger process pid */
 static bool stopping=false;
 static bool doreload=false;
 static void (*handler_int)(int)=NULL;
@@ -562,10 +565,53 @@
     return(freopen(outfile,mode,stream));
 }

+static int logger_child (int outpipe, int errpipe, char *procname) {
+  /* Read from file descriptors. Log to syslog. */
+  fd_set rfds;
+  struct timeval tv;
+  int retval, n;
+  int bufsz = 1024;
+  char buf[bufsz];
+
+  if (outpipe > errpipe) {
+    n = outpipe + 1;
+  } else {
+    n = errpipe + 1;
+  }
+
+  openlog(procname, LOG_PID, LOG_LOCAL0);
+
+  while (1) {
+    /* Watch two pipes for input */
+    FD_ZERO(&rfds);
+    FD_SET(outpipe, &rfds);
+    FD_SET(errpipe, &rfds);
+    /* Wait for a minute */
+    tv.tv_sec = 60;
+    tv.tv_usec = 0;
+
+    retval = select (n, &rfds, NULL, NULL, &tv);
+    if (retval == -1)
+      perror("select()");
+    else if (retval) {
+      if (FD_ISSET(outpipe, &rfds)) {
+        read(outpipe, buf, bufsz);
+        syslog(LOG_INFO, "%s", buf);
+      }
+      if (FD_ISSET(errpipe, &rfds)) {
+        read(errpipe, buf, bufsz);
+        syslog(LOG_ERR, "%s", buf);
+      }
+    }
+  }
+}
+
 /**
  *  Redirect stdin, stdout, stderr.
  */
-static void set_output(char *outfile, char *errfile) {
+static void set_output(char *outfile, char *errfile, char *procname) {
+    int stdoutdes[2] = {0,0}, stderrdes[2] = {0,0},
+        forkoutlogger=0, forkerrlogger=0;
     freopen("/dev/null", "r", stdin);
     log_debug("redirecting stdout to %s and stderr to %s",outfile,errfile);

@@ -577,11 +623,28 @@
     if(strcmp(outfile, "&2") == 0 && strcmp(errfile,"&1") == 0) {
       outfile="/dev/null";
     }
-    if(strcmp(outfile, "&2") != 0) {
+
+    if (strcmp(outfile, "SYSLOG") == 0) {
+      /* Send stdout to syslog through a logger process */
+      if (pipe(stdoutdes)) {
+        fprintf(stderr, "Unable to create stdout pipe for syslog: %s\n",
+                strerror(errno));
+      } else {
+        forkoutlogger=1;
+      }
+    } else if(strcmp(outfile, "&2") != 0) {
       loc_freopen(outfile, "a", stdout);
     }

-    if(strcmp(errfile,"&1") != 0) {
+    if (strcmp(errfile, "SYSLOG") == 0) {
+      /* Send stderr to syslog through a logger process */
+      if (pipe(stderrdes)) {
+        fprintf(stderr, "Unable to create stderr pipe for syslog: %s\n",
+                strerror(errno));
+      } else {
+        forkerrlogger=1;
+      }
+    } else if(strcmp(errfile,"&1") != 0) {
       loc_freopen(errfile, "a", stderr);
     } else {
       close(2);
@@ -591,6 +654,33 @@
       close(1);
       dup(2);
     }
+
+    if (forkoutlogger || forkerrlogger) {
+      int pid;
+      if ((pid=fork())!=-1) {
+        if (pid) {
+          if (stdoutdes[0] != 0) {
+            close(stdoutdes[0]);
+            if (dup2(stdoutdes[1],1) == -1) {
+              fprintf(stderr,"Unable to redirect stdout to pipe for syslog: %s\n",
+                strerror(errno));
+            }
+          }
+          if (stderrdes[0] != 0) {
+            close(stderrdes[0]);
+            if (dup2(stderrdes[1],2) == -1) {
+              fprintf(stderr,"Unable to redirect stderr to pipe for syslog: %s\n",
+                strerror(errno));
+            }
+          }
+        } else {
+          exit (logger_child(stdoutdes[1],stderrdes[1],procname));
+        }
+      } else {
+        fprintf(stderr, "Unable to create logger child process: %s\n",
+           strerror(errno));
+      }
+    }
 }

 int main(int argc, char *argv[]) {
@@ -678,7 +768,7 @@
 #endif
     }

-    set_output(args->outfile, args->errfile);
+    set_output(args->outfile, args->errfile, args->procname);

     /* We have to fork: this process will become the controller and the other
        will be the child */
@@ -734,10 +824,16 @@
 void main_reload(void) {
     log_debug("Killing self with HUP signal");
     kill(controlled,SIGHUP);
+    if (logger != 0) {
+      kill(logger,SIGHUP);
+    }
 }

 void main_shutdown(void) {
     log_debug("Killing self with TERM signal");
     kill(controlled,SIGTERM);
+    if (logger != 0) {
+      kill(logger,SIGTERM);
+    }
 }

-- 
Configure bugmail: http://issues.apache.org/bugzilla/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
You are the assignee for the bug, or are watching the assignee.

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org