ucx/logging.c

Fri, 08 Feb 2013 10:37:24 +0100

author
Mike Becker <universe@uap-core.de>
date
Fri, 08 Feb 2013 10:37:24 +0100
changeset 81
86a23238d8a1
parent 80
0125e4089f88
child 82
6068d965328b
permissions
-rw-r--r--

changed logger to behave more like printf + added possibility to specify write function

#include "logging.h"
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>

UcxLogger *ucx_logger_new(FILE *stream, unsigned int level, unsigned int mask) {
    UcxLogger *logger = (UcxLogger*) malloc(sizeof(UcxLogger));
    if (logger != NULL) {
        logger->stream = stream;
        logger->writer = fwrite;
        logger->level = level;
        logger->mask = mask;
        logger->levels = ucx_map_new(8);
        
        unsigned int l;
        l = UCX_LOGGER_ERROR;
        ucx_map_int_put(logger->levels, l, "[ERROR]");
        l = UCX_LOGGER_WARN;
        ucx_map_int_put(logger->levels, l, "[WARNING]");
        l = UCX_LOGGER_INFO;
        ucx_map_int_put(logger->levels, l, "[INFO]");
        l = UCX_LOGGER_TRACE;
        ucx_map_int_put(logger->levels, l, "[TRACE]");
    }

    return logger;
}

void ucx_logger_free(UcxLogger *logger) {
    ucx_map_free(logger->levels);
    free(logger);
}

void ucx_logger_setoutput(UcxLogger *logger, FILE *stream,
        size_t(*writer)(const void*,size_t,size_t,FILE*)) {
    if (stream) {
        logger->stream = stream;
    }
    if (writer) {
        logger->writer = writer;
    }
}

void ucx_logger_logf(UcxLogger *logger, unsigned int level, const char* file,
        const unsigned int line, const char *format, ...) {
    if (level <= logger->level) {
        const size_t max = 4096; // estimated maximum message length
        char msg[max];
        char *text;
        size_t k = 0;
        size_t n;
        
        if ((logger->mask & UCX_LOGGER_LEVEL) > 0) {
            text = (char*) ucx_map_int_get(logger->levels, level);
            n = strlen(text);
            memcpy(msg+k, text, n);
            k += n;
            msg[k++] = ' ';
        }
        // TODO: timestamp
        if ((logger->mask & UCX_LOGGER_SOURCE) > 0) {
            n = strlen(file);
            memcpy(msg+k, file, n);
            k += n;
            k += sprintf(msg+k, ":%d ", line);
        }
        
        msg[k++] = '-'; msg[k++] = ' ';
        
        va_list args;
        va_start (args, format);
        k += vsnprintf(msg+k, max-k-1, format, args);
        va_end (args);        
        
        msg[k++] = '\n';
        
        logger->writer(msg, 1, k, logger->stream);
        fflush(logger->stream);
    }
}

mercurial