log.c revision cb9e6e5c78f5a1690214e9548250fc6af1fc73b5
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny/* ====================================================================
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * The Apache Software License, Version 1.1
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Copyright (c) 2000-2001 The Apache Software Foundation. All rights
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Redistribution and use in source and binary forms, with or without
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * modification, are permitted provided that the following conditions
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * 1. Redistributions of source code must retain the above copyright
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * notice, this list of conditions and the following disclaimer.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * 2. Redistributions in binary form must reproduce the above copyright
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * notice, this list of conditions and the following disclaimer in
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * the documentation and/or other materials provided with the
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * distribution.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * 3. The end-user documentation included with the redistribution,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * if any, must include the following acknowledgment:
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * "This product includes software developed by the
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Apache Software Foundation (http://www.apache.org/)."
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Alternately, this acknowledgment may appear in the software itself,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * if and wherever such third-party acknowledgments normally appear.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * 4. The names "Apache" and "Apache Software Foundation" must
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny * not be used to endorse or promote products derived from this
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * software without prior written permission. For written
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * permission, please contact apache@apache.org.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * 5. Products derived from this software may not be called "Apache",
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * nor may "Apache" appear in their name, without prior written
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * permission of the Apache Software Foundation.
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * SUCH DAMAGE.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * ====================================================================
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * This software consists of voluntary contributions made by many
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * individuals on behalf of the Apache Software Foundation. For more
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * information on the Apache Software Foundation, please see
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Portions of this software are based upon public domain software
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * originally written at the National Center for Supercomputing Applications,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * University of Illinois, Urbana-Champaign.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * http_log.c: Dealing with the logs and errors
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * Rob McCool
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zelenytypedef struct {
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zelenyint AP_DECLARE_DATA ap_default_loglevel = DEFAULT_LOGLEVEL;
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan ZelenyAP_DECLARE(void) ap_open_stderr_log(apr_pool_t *p)
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zelenystatic int log_child(apr_pool_t *p, const char *progname,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* Child process code for 'ErrorLog "|..."';
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * may want a common framework for this, since I expect it will
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * be common for other foo-loggers to want this sort of thing...
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* No concept of a child process on Win32 */
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny#endif /* ndef SIGHUP */
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny if (((rc = apr_procattr_create(&procattr, p)) == APR_SUCCESS) &&
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny const char *pname;
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny procnew = (apr_proc_t *)apr_pcalloc(p, sizeof(*procnew));
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny rc = apr_proc_create(procnew, pname, (const char * const *)args,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny apr_pool_note_subprocess(p, procnew, kill_after_timeout);
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zelenystatic void open_error_log(server_rec *s, apr_pool_t *p)
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny const char *fname;
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* This starts a new process... */
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny ap_log_error(APLOG_MARK, APLOG_STARTUP, rc, NULL,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny "Couldn't start ErrorLog process");
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny else if (!strncasecmp(s->error_fname, "syslog", 6)) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny openlog(ap_server_argv0, LOG_NDELAY|LOG_CONS|LOG_PID,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny openlog(ap_server_argv0, LOG_NDELAY|LOG_CONS|LOG_PID, LOG_LOCAL7);
74f857536411b46712f9b3dc0f1c53924b36dc02Stephen Gallagher fname = ap_server_root_relative(p, s->error_fname);
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny ap_log_error(APLOG_MARK, APLOG_STARTUP, rc, NULL,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny "%s: could not open error log file %s.",
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zelenyvoid ap_open_logs(server_rec *s_main, apr_pool_t *p)
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* replace stderr with this new log */
fdab7bbf8933351f6254438c30ff361cd748b15aJan Zeleny rc = apr_file_dup2(&errfile, s_main->error_log, p);
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny "unable to replace stderr with error_log");
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* note that stderr may still need to be replaced with something
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * because it points to the old error log, or back to the tty
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * of the submitter.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny if (replace_stderr && freopen("/dev/null", "w", stderr) == NULL) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny ap_log_error(APLOG_MARK, APLOG_CRIT, errno, s_main,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny "unable to replace stderr with /dev/null");
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny for (virt = s_main->next; virt; virt = virt->next) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny strcmp(q->error_fname, virt->error_fname) == 0) {
07002c911aa643000856f78707f1fee72b5eea29Jakub HrozekAP_DECLARE(void) ap_error_log2stderr(server_rec *s) {
07002c911aa643000856f78707f1fee72b5eea29Jakub Hrozek apr_file_open_stderr(&errfile, s->process->pool);
07002c911aa643000856f78707f1fee72b5eea29Jakub Hrozek apr_file_dup2(&(s->error_log), errfile, s->process->pool);
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zelenystatic void log_error_core(const char *file, int line, int level,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * If we are doing stderr logging (startup), don't log messages that are
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * above the default server log level unless it is a startup/shutdown
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny else if (s->error_log) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * If we are doing normal logging, don't log messages that are
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * above the server log level unless it is a startup/shutdown notice
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * If we are doing normal logging, don't log messages that are
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * above the server log level unless it is a startup/shutdown notice
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny#endif /* TPF */
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * If we are doing syslog logging, don't log messages that are
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * above the server log level (including a startup/shutdown notice)
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny if (logf && ((level & APLOG_STARTUP) != APLOG_STARTUP)) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny len += apr_snprintf(errstr + len, MAX_STRING_LEN - len,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* In OSD/POSIX, the compiler returns for __FILE__
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * a string like: __FILE__="*POSIX(/usr/include/stdio.h)"
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * (it even returns an absolute path for sources in
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * the current directory). Here we try to strip this
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * down to the basename.
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny if (*e == ')') {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny#endif /*_OSD_POSIX*/
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny len += apr_snprintf(errstr + len, MAX_STRING_LEN - len,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny#endif /* TPF */
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny if (r && r->connection) {
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny /* XXX: TODO: add a method of selecting whether logged client
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * addresses are in dotted quad or resolved form... dotted
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * quad is the most secure, which is why I'm implementing it
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny * first. -djg
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny len += apr_snprintf(errstr + len, MAX_STRING_LEN - len,
ad07ed37b6b51ef134d4524edaf2259e19ac984fJan Zeleny len += apr_snprintf(errstr + len, MAX_STRING_LEN - len,
if (logf) {
#ifdef HAVE_SYSLOG
const char *fmt, ...)
const char *fmt, ...)
const char *fmt, ...)
args)));
if (!fname)
fname));
!= APR_SUCCESS) {
int nLine)
abort();
#ifdef AP_HAVE_RELIABLE_PIPED_LOGS
int rc;
#ifdef SIGHUP
!= APR_SUCCESS)) {
char **args;
const char *pname;
switch (reason) {
case APR_OC_REASON_DEATH:
case APR_OC_REASON_LOST:
case APR_OC_REASON_UNWRITABLE:
case APR_OC_REASON_RESTART:
case APR_OC_REASON_UNREGISTER:
return APR_SUCCESS;
pl->p = p;
return NULL;
return NULL;
return pl;
return APR_SUCCESS;
int rc;
pl->p = p;
return pl;