Author: rjung
Date: Tue Jul 24 14:56:33 2007
New Revision: 559234
URL: http://svn.apache.org/viewvc?view=rev&rev=559234
Log:
Apache: add milliseconds (%Q) and microseconds (%q) as possible
JkLogStampFormat conversion specifiers. This does not use strftime(),
but needs gettimeofday().
Also add milliseconds to the default timestamp format,
if we have gettimeofday().
Modified:
tomcat/connectors/trunk/jk/native/apache-1.3/mod_jk.c
tomcat/connectors/trunk/jk/native/apache-2.0/mod_jk.c
tomcat/connectors/trunk/jk/native/common/jk_logger.h
tomcat/connectors/trunk/jk/native/common/jk_util.c
tomcat/connectors/trunk/jk/native/common/jk_util.h
tomcat/connectors/trunk/jk/xdocs/miscellaneous/changelog.xml
tomcat/connectors/trunk/jk/xdocs/reference/apache.xml
Modified: tomcat/connectors/trunk/jk/native/apache-1.3/mod_jk.c
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/native/apache-1.3/mod_jk.c?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/native/apache-1.3/mod_jk.c (original)
+++ tomcat/connectors/trunk/jk/native/apache-1.3/mod_jk.c Tue Jul 24 14:56:33
2007
@@ -2496,12 +2496,14 @@
if (jkl && flp) {
jkl->log = jk_log_to_file;
jkl->level = conf->log_level;
- jkl->log_fmt = conf->stamp_format_string;
+ jk_set_time_fmt(jkl, conf->stamp_format_string);
jkl->logger_private = flp;
flp->log_fd = conf->log_fd;
conf->log = jkl;
if (main_log == NULL)
main_log = conf->log;
+ jk_log(conf->log, JK_LOG_DEBUG, "log time stamp format is '%s'",
+ conf->log->log_fmt);
return;
}
Modified: tomcat/connectors/trunk/jk/native/apache-2.0/mod_jk.c
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/native/apache-2.0/mod_jk.c?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/native/apache-2.0/mod_jk.c (original)
+++ tomcat/connectors/trunk/jk/native/apache-2.0/mod_jk.c Tue Jul 24 14:56:33
2007
@@ -2637,7 +2637,7 @@
if (jkl && flp) {
jkl->log = jk_log_to_file;
jkl->level = conf->log_level;
- jkl->log_fmt = conf->stamp_format_string;
+ jk_set_time_fmt(jkl, conf->stamp_format_string);
jkl->logger_private = flp;
flp->jklogfp = conf->jklogfp;
conf->log = jkl;
@@ -2649,6 +2649,8 @@
/* Also should we pass pointer (ie: main_log) or handle
(*main_log) ? */
apr_pool_cleanup_register(p, &main_log, jklog_cleanup,
jklog_cleanup);
}
+ jk_log(conf->log, JK_LOG_DEBUG, "log time stamp format is '%s'",
+ conf->log->log_fmt);
return 0;
}
Modified: tomcat/connectors/trunk/jk/native/common/jk_logger.h
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/native/common/jk_logger.h?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/native/common/jk_logger.h (original)
+++ tomcat/connectors/trunk/jk/native/common/jk_logger.h Tue Jul 24 14:56:33
2007
@@ -36,7 +36,12 @@
{
void *logger_private;
int level;
- const char *log_fmt;
+ const char *log_fmt; /* the configured timestamp format for logging */
+ const char *log_fmt_subsec; /* like log_fmt, but milli/micro seconds
+ marker replaced, because strftie() doesn't
handle those */
+ int log_fmt_type; /* do we want milli or microseconds */
+ int log_fmt_offset; /* at which position shoukd they occur */
+ int log_fmt_size; /* how long is this format string */
int (JK_METHOD * log) (jk_logger_t *l, int level, int used, char *what);
Modified: tomcat/connectors/trunk/jk/native/common/jk_util.c
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/native/common/jk_util.c?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/native/common/jk_util.c (original)
+++ tomcat/connectors/trunk/jk/native/common/jk_util.c Tue Jul 24 14:56:33 2007
@@ -127,9 +127,16 @@
* [Mon Mar 26 19:44:48 2001] [jk_uri_worker_map.c (155)]: Into
jk_uri_worker_map_t::uri_worker_map_alloc
* log format used by apache in error.log
*/
-#ifndef JK_TIME_FORMAT
-#define JK_TIME_FORMAT "[%a %b %d %H:%M:%S %Y] "
-#endif
+#define JK_STRFTIME_MILLI "%Q"
+#define JK_STRFTIME_MICRO "%q"
+#define JK_PATTERN_MILLI "XXX"
+#define JK_PATTERN_MICRO "XXXXXX"
+#define JK_TIME_FORMAT_NONE "[%a %b %d %H:%M:%S %Y] "
+#define JK_TIME_FORMAT_MILLI "[%a %b %d %H:%M:%S." JK_STRFTIME_MILLI " %Y] "
+#define JK_TIME_FORMAT_MICRO "[%a %b %d %H:%M:%S." JK_STRFTIME_MICRO " %Y] "
+#define JK_TIME_SUBSEC_NONE (0)
+#define JK_TIME_SUBSEC_MILLI (1)
+#define JK_TIME_SUBSEC_MICRO (2)
/* Visual C++ Toolkit 2003 support */
#if defined (_MSC_VER) && (_MSC_VER == 1310)
@@ -343,15 +350,110 @@
#endif
}
-static int set_time_str(char *str, int len, const char *jk_log_fmt)
+void jk_set_time_fmt(jk_logger_t *l, const char *jk_log_fmt)
{
- time_t t = time(NULL);
+ if (l) {
+ char *s;
+ char log_fmt_safe[LOG_LINE_SIZE];
+ char *fmt;
+
+ if (!jk_log_fmt) {
+#ifndef NO_GETTIMEOFDAY
+ jk_log_fmt = JK_TIME_FORMAT_MILLI;
+#else
+ jk_log_fmt = JK_TIME_FORMAT_NONE;
+#endif
+ }
+ l->log_fmt_type = JK_TIME_SUBSEC_NONE;
+ l->log_fmt_offset = 0;
+ l->log_fmt_size = 0;
+ l->log_fmt_subsec = jk_log_fmt;
+ l->log_fmt = jk_log_fmt;
+
+ fmt = (char *)malloc(LOG_LINE_SIZE + strlen(JK_PATTERN_MICRO));
+ if ( fmt ) {
+ strncpy(log_fmt_safe, jk_log_fmt, LOG_LINE_SIZE);
+ if ( (s = strstr(log_fmt_safe, JK_STRFTIME_MILLI)) ) {
+ int offset = s - log_fmt_safe;
+ int len = strlen(JK_PATTERN_MILLI);
+
+ l->log_fmt_type = JK_TIME_SUBSEC_MILLI;
+ l->log_fmt_offset = offset;
+ strncpy(fmt, log_fmt_safe, offset);
+ strncpy(fmt + offset, JK_PATTERN_MILLI, len);
+ strncpy(fmt + offset + len,
+ s + strlen(JK_STRFTIME_MILLI),
+ LOG_LINE_SIZE - offset - len);
+ fmt[LOG_LINE_SIZE-1] = '\0';
+ l->log_fmt_subsec = fmt;
+ l->log_fmt_size = strlen(fmt);
+ }
+ else if ( (s = strstr(log_fmt_safe, JK_STRFTIME_MICRO)) ) {
+ int offset = s - log_fmt_safe;
+ int len = strlen(JK_PATTERN_MICRO);
+
+ l->log_fmt_type = JK_TIME_SUBSEC_MICRO;
+ l->log_fmt_offset = offset;
+ strncpy(fmt, log_fmt_safe, offset);
+ strncpy(fmt + offset, JK_PATTERN_MICRO, len);
+ strncpy(fmt + offset + len,
+ s + strlen(JK_STRFTIME_MICRO),
+ LOG_LINE_SIZE - offset - len);
+ fmt[LOG_LINE_SIZE-1] = '\0';
+ l->log_fmt_subsec = fmt;
+ l->log_fmt_size = strlen(fmt);
+ }
+ }
+ }
+}
+
+static int set_time_str(char *str, int len, jk_logger_t *l)
+{
+ time_t t;
struct tm *tms;
+ int done;
+ char log_fmt[LOG_LINE_SIZE];
+ if ( !l || !l->log_fmt ) {
+ return 0;
+ }
+
+ log_fmt[0] = '\0';
+
+#ifndef NO_GETTIMEOFDAY
+ if ( l->log_fmt_type != JK_TIME_SUBSEC_NONE ) {
+ struct timeval tv;
+ int rc = gettimeofday(&tv, NULL);
+ if ( rc == 0 ) {
+ char subsec[7];
+ t = tv.tv_sec;
+ strncpy(log_fmt, l->log_fmt_subsec, l->log_fmt_size + 1);
+ if ( l->log_fmt_type == JK_TIME_SUBSEC_MILLI ) {
+ sprintf(subsec, "%03d", (int)(tv.tv_usec/1000));
+ strncpy(log_fmt + l->log_fmt_offset, subsec, 3);
+ }
+ else if ( l->log_fmt_type == JK_TIME_SUBSEC_MICRO ) {
+ sprintf(subsec, "%06d", (int)(tv.tv_usec));
+ strncpy(log_fmt + l->log_fmt_offset, subsec, 6);
+ }
+ }
+ else {
+ t = time(NULL);
+ }
+ }
+ else {
+ t = time(NULL);
+ }
+#else
+ t = time(NULL);
+#endif
tms = localtime(&t);
- if (jk_log_fmt)
- return (int)strftime(str, len, jk_log_fmt, tms);
- return (int)strftime(str, len, JK_TIME_FORMAT, tms);
+ if (log_fmt[0])
+ done = (int)strftime(str, len, log_fmt, tms);
+ else
+ done = (int)strftime(str, len, l->log_fmt, tms);
+ return done;
+
}
static int JK_METHOD log_to_file(jk_logger_t *l, int level, int used, char
*what)
@@ -410,7 +512,7 @@
if (rc && p) {
rc->log = log_to_file;
rc->level = level;
- rc->log_fmt = NULL;
+ jk_set_time_fmt(rc, NULL);
rc->logger_private = p;
#if defined(AS400) && !defined(AS400_UTF8)
p->logfile = fopen(file, "a+, o_ccsid=0");
@@ -419,6 +521,7 @@
#endif
if (p->logfile) {
*l = rc;
+ jk_log(rc, JK_LOG_DEBUG, "log time stamp format is '%s'",
rc->log_fmt);
return JK_TRUE;
}
}
@@ -490,7 +593,7 @@
if (NULL == buf)
return -1;
#endif
- used = set_time_str(buf, usable_size, l->log_fmt);
+ used = set_time_str(buf, usable_size, l);
if (line) { /* line==0 only used for request log item */
/* Log [pid:threadid] for all levels except REQUEST. */
Modified: tomcat/connectors/trunk/jk/native/common/jk_util.h
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/native/common/jk_util.h?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/native/common/jk_util.h (original)
+++ tomcat/connectors/trunk/jk/native/common/jk_util.h Tue Jul 24 14:56:33 2007
@@ -39,6 +39,8 @@
void jk_sleep(int ms);
+void jk_set_time_fmt(jk_logger_t *l, const char *jk_log_fmt);
+
int jk_parse_log_level(const char *level);
int jk_open_file_logger(jk_logger_t **l, const char *file, int level);
Modified: tomcat/connectors/trunk/jk/xdocs/miscellaneous/changelog.xml
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/xdocs/miscellaneous/changelog.xml?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/xdocs/miscellaneous/changelog.xml (original)
+++ tomcat/connectors/trunk/jk/xdocs/miscellaneous/changelog.xml Tue Jul 24
14:56:33 2007
@@ -28,6 +28,15 @@
<subsection name="Native">
<changelog>
<update>
+ Logging: add milliseconds to the default timestamp format,
+ if we have gettimeofday(). (rjung)
+ </update>
+ <update>
+ Apache: add milliseconds (%Q) and microseconds (%q) as possible
+ JkLogStampFormat conversion specifiers. This does not use strftime(),
+ but needs gettimeofday(). (rjung)
+ </update>
+ <update>
IIS & Sun: Log service failures also, if return code is negative.
(rjung)
</update>
<fix>
Modified: tomcat/connectors/trunk/jk/xdocs/reference/apache.xml
URL:
http://svn.apache.org/viewvc/tomcat/connectors/trunk/jk/xdocs/reference/apache.xml?view=diff&rev=559234&r1=559233&r2=559234
==============================================================================
--- tomcat/connectors/trunk/jk/xdocs/reference/apache.xml (original)
+++ tomcat/connectors/trunk/jk/xdocs/reference/apache.xml Tue Jul 24 14:56:33
2007
@@ -170,10 +170,17 @@
The default value is info.
</p></attribute>
<attribute name="JkLogStampFormat" required="false"><p>
-The Tomcat Connector module <b>date</b> log format, follow strftime syntax.
+The Tomcat Connector module <b>date</b> log format, follow an
+extended strftime syntax.
This format will be used for the time stamps in the JkLogFile.
+Besides the usual strftime conversion specifications,
+you can also use %Q for adding milliseconds to the log and
+%q for microseconds. This will only work with mod_jk minimum
+version 1.2.24 on platforms with a gettimeofday() function.
<br/>
-The default value is "[%a %b %d %H:%M:%S %Y] ".
+The default value is "[%a %b %d %H:%M:%S %Y] " and beginning
+with version 1.2.24 on platforms with a gettimeofday()
+function it is "[%a %b %d %H:%M:%S.%Q %Y] ".
</p></attribute>
<attribute name="JkRequestLogFormat" required="false"><p>
Request log format string. See detailed description below.
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]