Browse Source

[core] struct log_error_st for error logging

personal/stbuehler/ci-build
Glenn Strauss 3 years ago
parent
commit
cbad7517c8
  1. 9
      src/base.h
  2. 3
      src/base_decls.h
  3. 1
      src/connections.c
  4. 67
      src/log.c
  5. 15
      src/log.h
  6. 50
      src/server.c
  7. 6
      src/t/test_keyvalue.c
  8. 8
      src/t/test_request.c

9
src/base.h

@ -256,6 +256,8 @@ struct connection {
unsigned int mode; /* DIRECT (0) or plugin id */
int async_callback;
log_error_st *errh;
void **plugin_ctx; /* plugin connection specific config */
specific_config conf; /* global connection specific config */
@ -367,11 +369,6 @@ typedef struct {
struct server {
server_socket_array srv_sockets;
/* the errorlog */
int errorlog_fd;
enum { ERRORLOG_FILE, ERRORLOG_FD, ERRORLOG_SYSLOG, ERRORLOG_PIPE } errorlog_mode;
buffer *errorlog_buf;
struct fdevents *ev;
buffer_plugin plugins;
@ -409,6 +406,8 @@ struct server {
array *split_vals;
log_error_st *errh;
/* Timestamps */
time_t cur_ts;
time_t last_generated_date_ts;

3
src/base_decls.h

@ -15,6 +15,9 @@ typedef union sock_addr sock_addr;
struct fdnode_st;
typedef struct fdnode_st fdnode;
struct log_error_st;
typedef struct log_error_st log_error_st;
enum handler_t {
HANDLER_UNSET,
HANDLER_GO_ON,

1
src/connections.c

@ -1092,6 +1092,7 @@ connection *connection_accepted(server *srv, server_socket *srv_socket, sock_add
srv->con_opened++;
con = connections_get_new_connection(srv);
con->errh = srv->errh;
con->fd = cnt;
con->fdn = fdevent_register(srv->ev, con->fd, connection_handle_fdevent, con);

67
src/log.c

@ -8,6 +8,7 @@
#include <time.h>
#include <string.h>
#include <stdarg.h>
#include <stdlib.h> /* malloc() free() */
#include <unistd.h>
#ifdef HAVE_SYSLOG_H
@ -115,21 +116,20 @@ static void log_buffer_append_printf(buffer *out, const char *fmt, va_list ap) {
}
}
static int log_buffer_prepare(buffer *b, server *srv, const char *filename, unsigned int line) {
switch(srv->errorlog_mode) {
static int log_buffer_prepare(const log_error_st *errh, const char *filename, unsigned int line, buffer *b) {
switch(errh->errorlog_mode) {
case ERRORLOG_PIPE:
case ERRORLOG_FILE:
case ERRORLOG_FD:
if (-1 == srv->errorlog_fd) return -1;
if (-1 == errh->errorlog_fd) return -1;
/* cache the generated timestamp */
if (srv->cur_ts != srv->last_generated_debug_ts) {
buffer_clear(srv->ts_debug_str);
buffer_append_strftime(srv->ts_debug_str, "%Y-%m-%d %H:%M:%S", localtime(&(srv->cur_ts)));
srv->last_generated_debug_ts = srv->cur_ts;
if (*errh->last_ts != *errh->cur_ts) {
*errh->last_ts = *errh->cur_ts;
buffer_clear(errh->tb);
buffer_append_strftime(errh->tb, "%Y-%m-%d %H:%M:%S", localtime(errh->cur_ts));
}
buffer_copy_buffer(b, srv->ts_debug_str);
buffer_copy_buffer(b, errh->tb);
buffer_append_string_len(b, CONST_STR_LEN(": ("));
break;
case ERRORLOG_SYSLOG:
@ -146,13 +146,13 @@ static int log_buffer_prepare(buffer *b, server *srv, const char *filename, unsi
return 0;
}
static void log_write(server *srv, buffer *b) {
switch(srv->errorlog_mode) {
static void log_write(const log_error_st *errh, buffer *b) {
switch(errh->errorlog_mode) {
case ERRORLOG_PIPE:
case ERRORLOG_FILE:
case ERRORLOG_FD:
buffer_append_string_len(b, CONST_STR_LEN("\n"));
write_all(srv->errorlog_fd, CONST_BUF_LEN(b));
write_all(errh->errorlog_fd, CONST_BUF_LEN(b));
break;
case ERRORLOG_SYSLOG:
syslog(LOG_ERR, "%s", b->ptr);
@ -161,28 +161,30 @@ static void log_write(server *srv, buffer *b) {
}
int log_error_write(server *srv, const char *filename, unsigned int line, const char *fmt, ...) {
va_list ap;
if (-1 == log_buffer_prepare(srv->errorlog_buf, srv, filename, line)) return 0;
const log_error_st *errh = srv->errh;
buffer *b = errh->b;
if (-1 == log_buffer_prepare(errh, filename, line, b)) return 0;
va_list ap;
va_start(ap, fmt);
log_buffer_append_printf(srv->errorlog_buf, fmt, ap);
log_buffer_append_printf(b, fmt, ap);
va_end(ap);
log_write(srv, srv->errorlog_buf);
log_write(errh, b);
return 0;
}
int log_error_write_multiline_buffer(server *srv, const char *filename, unsigned int line, buffer *multiline, const char *fmt, ...) {
const log_error_st *errh = srv->errh;
buffer *b = errh->b;
va_list ap;
size_t prefix_len;
buffer *b = srv->errorlog_buf;
char *pos, *end, *current_line;
if (buffer_string_is_empty(multiline)) return 0;
if (-1 == log_buffer_prepare(b, srv, filename, line)) return 0;
if (-1 == log_buffer_prepare(errh, filename, line, b)) return 0;
va_start(ap, fmt);
log_buffer_append_printf(b, fmt, ap);
@ -203,7 +205,7 @@ int log_error_write_multiline_buffer(server *srv, const char *filename, unsigned
buffer_string_set_length(b, prefix_len);
buffer_append_string_len(b, current_line, pos - current_line);
log_write(srv, b);
log_write(errh, b);
}
current_line = pos + 1;
break;
@ -214,3 +216,28 @@ int log_error_write_multiline_buffer(server *srv, const char *filename, unsigned
return 0;
}
log_error_st *
log_error_st_init (time_t *cur_ts_ptr, time_t *last_ts_ptr)
{
log_error_st *errh = calloc(1, sizeof(log_error_st));
force_assert(errh);
errh->errorlog_fd = STDERR_FILENO;
errh->errorlog_mode = ERRORLOG_FD;
errh->b = buffer_init();
errh->tb = buffer_init();
errh->cur_ts = cur_ts_ptr;
errh->last_ts = last_ts_ptr;
return errh;
}
void
log_error_st_free (log_error_st *errh)
{
if (NULL == errh) return;
buffer_free(errh->tb);
buffer_free(errh->b);
free(errh);
}

15
src/log.h

@ -16,4 +16,19 @@ int log_error_write(server *srv, const char *filename, unsigned int line, const
__attribute_cold__
int log_error_write_multiline_buffer(server *srv, const char *filename, unsigned int line, buffer *multiline, const char *fmt, ...);
struct log_error_st {
enum { ERRORLOG_FILE, ERRORLOG_FD, ERRORLOG_SYSLOG, ERRORLOG_PIPE } errorlog_mode;
int errorlog_fd;
buffer *b;
buffer *tb;
time_t *cur_ts;
time_t *last_ts;
};
__attribute_cold__
log_error_st * log_error_st_init (time_t *cur_ts_ptr, time_t *last_ts_ptr);
__attribute_cold__
void log_error_st_free (log_error_st *errh);
#endif

50
src/server.c

@ -232,9 +232,7 @@ static server *server_init(void) {
CLEAN(response_header);
CLEAN(parse_full_path);
CLEAN(ts_debug_str);
CLEAN(ts_date_str);
CLEAN(errorlog_buf);
CLEAN(response_range);
CLEAN(tmp_buf);
srv->empty_string = buffer_init_string("");
@ -280,6 +278,8 @@ static server *server_init(void) {
srv->fdwaitqueue = calloc(1, sizeof(*srv->fdwaitqueue));
force_assert(srv->fdwaitqueue);
srv->errh = log_error_st_init(&srv->cur_ts, &srv->last_generated_debug_ts);
srv->srvconf.modules = array_init();
srv->srvconf.modules_dir = buffer_init_string(LIBRARY_DIR);
srv->srvconf.network_backend = buffer_init();
@ -306,10 +306,6 @@ static server *server_init(void) {
srv->srvconf.compat_module_load = 1;
srv->srvconf.systemd_socket_activation = 0;
/* use syslog */
srv->errorlog_fd = STDERR_FILENO;
srv->errorlog_mode = ERRORLOG_FD;
srv->split_vals = array_init();
srv->request_env = plugins_call_handle_request_env;
@ -333,9 +329,7 @@ static void server_free(server *srv) {
CLEAN(response_header);
CLEAN(parse_full_path);
CLEAN(ts_debug_str);
CLEAN(ts_date_str);
CLEAN(errorlog_buf);
CLEAN(response_range);
CLEAN(tmp_buf);
CLEAN(empty_string);
@ -403,6 +397,7 @@ static void server_free(server *srv) {
li_rand_cleanup();
chunkqueue_chunk_pool_free();
log_error_st_free(srv->errh);
free(srv);
}
@ -674,6 +669,7 @@ static void show_help (void) {
*/
static int log_error_open(server *srv) {
log_error_st *errh = srv->errh;
int errfd;
#ifdef HAVE_SYSLOG_H
/* perhaps someone wants to use syslog() */
@ -743,11 +739,11 @@ static int log_error_open(server *srv) {
openlog("lighttpd", LOG_CONS|LOG_PID, -1==facility ? LOG_DAEMON : facility);
#endif
srv->errorlog_mode = ERRORLOG_FD;
srv->errorlog_fd = STDERR_FILENO;
errh->errorlog_mode = ERRORLOG_FD;
errh->errorlog_fd = STDERR_FILENO;
if (srv->srvconf.errorlog_use_syslog) {
srv->errorlog_mode = ERRORLOG_SYSLOG;
errh->errorlog_mode = ERRORLOG_SYSLOG;
}
else if (!buffer_string_is_empty(srv->srvconf.errorlog_file)) {
const char *logfile = srv->srvconf.errorlog_file->ptr;
@ -758,24 +754,24 @@ static int log_error_open(server *srv) {
"' failed: ", strerror(errno));
return -1;
}
srv->errorlog_fd = fd;
srv->errorlog_mode = logfile[0] == '|' ? ERRORLOG_PIPE : ERRORLOG_FILE;
errh->errorlog_fd = fd;
errh->errorlog_mode = logfile[0] == '|' ? ERRORLOG_PIPE : ERRORLOG_FILE;
}
if (srv->errorlog_mode == ERRORLOG_FD && !srv->srvconf.dont_daemonize) {
if (errh->errorlog_mode == ERRORLOG_FD && !srv->srvconf.dont_daemonize) {
/* We can only log to stderr in dont-daemonize mode;
* if we do daemonize and no errorlog file is specified,
* we log into /dev/null
*/
srv->errorlog_fd = -1;
errh->errorlog_fd = -1;
}
if (!buffer_string_is_empty(srv->srvconf.breakagelog_file)) {
const char *logfile = srv->srvconf.breakagelog_file->ptr;
if (srv->errorlog_mode == ERRORLOG_FD) {
srv->errorlog_fd = dup(STDERR_FILENO);
fdevent_setfd_cloexec(srv->errorlog_fd);
if (errh->errorlog_mode == ERRORLOG_FD) {
errh->errorlog_fd = dup(STDERR_FILENO);
fdevent_setfd_cloexec(errh->errorlog_fd);
}
if (-1 == (errfd = fdevent_open_logger(logfile))) {
@ -823,9 +819,10 @@ static int log_error_open(server *srv) {
static int log_error_cycle(server *srv) {
/* cycle only if the error log is a file */
if (srv->errorlog_mode == ERRORLOG_FILE) {
log_error_st *errh = srv->errh;
if (errh->errorlog_mode == ERRORLOG_FILE) {
const char *logfile = srv->srvconf.errorlog_file->ptr;
if (-1 == fdevent_cycle_logger(logfile, &srv->errorlog_fd)) {
if (-1 == fdevent_cycle_logger(logfile, &errh->errorlog_fd)) {
/* write to old log */
log_error_write(srv, __FILE__, __LINE__, "SSSS",
"cycling errorlog '", logfile,
@ -838,18 +835,19 @@ static int log_error_cycle(server *srv) {
__attribute_cold__
static int log_error_close(server *srv) {
switch(srv->errorlog_mode) {
log_error_st *errh = srv->errh;
switch(errh->errorlog_mode) {
case ERRORLOG_PIPE:
case ERRORLOG_FILE:
case ERRORLOG_FD:
if (-1 != srv->errorlog_fd) {
if (-1 != errh->errorlog_fd) {
/* don't close STDERR */
/* fdevent_close_logger_pipes() closes ERRORLOG_PIPE */
if (STDERR_FILENO != srv->errorlog_fd
&& srv->errorlog_mode != ERRORLOG_PIPE) {
close(srv->errorlog_fd);
if (STDERR_FILENO != errh->errorlog_fd
&& ERRORLOG_PIPE != errh->errorlog_mode) {
close(errh->errorlog_fd);
}
srv->errorlog_fd = -1;
errh->errorlog_fd = -1;
}
break;
case ERRORLOG_SYSLOG:

6
src/t/test_keyvalue.c

@ -16,9 +16,7 @@ static pcre_keyvalue_buffer * test_keyvalue_test_kvb_init (void) {
server srv;
memset(&srv, 0, sizeof(srv));
srv.errorlog_fd = STDERR_FILENO;
srv.errorlog_mode = ERRORLOG_FD;
srv.errorlog_buf = buffer_init();
srv.errh = log_error_st_init(&srv.cur_ts, &srv.last_generated_debug_ts);
buffer_copy_string_len(k, CONST_STR_LEN("^/foo($|\\?.+)"));
buffer_copy_string_len(v, CONST_STR_LEN("/foo/$1"));
@ -35,7 +33,7 @@ static pcre_keyvalue_buffer * test_keyvalue_test_kvb_init (void) {
buffer_free(k);
buffer_free(v);
buffer_free(srv.errorlog_buf);
log_error_st_free(srv.errh);
return kvb;
}

8
src/t/test_request.c

@ -9,6 +9,7 @@
#include "request.h"
#include "base.h"
#include "burl.h"
#include "log.h"
static void test_request_connection_reset(connection *con)
{
@ -453,9 +454,8 @@ int main (void)
connection con;
memset(&srv, 0, sizeof(server));
srv.errorlog_fd = -1; /* use 2 for STDERR_FILENO from unistd.h */
srv.errorlog_mode = ERRORLOG_FD;
srv.errorlog_buf = buffer_init();
srv.errh = log_error_st_init(&srv.cur_ts, &srv.last_generated_debug_ts);
srv.errh->errorlog_fd = -1; /* (disable) */
srv.split_vals = array_init();
memset(&con, 0, sizeof(connection));
@ -478,7 +478,7 @@ int main (void)
array_free(con.request.headers);
array_free(srv.split_vals);
buffer_free(srv.errorlog_buf);
log_error_st_free(srv.errh);
return 0;
}

Loading…
Cancel
Save