simplelog.c

/*
 * Copyright (c) 2011 Red Hat, Inc.
 *
 * All rights reserved.
 *
 * Author: Angus Salkeld <asalkeld@redhat.com>
 *
 * libqb is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, either version 2.1 of the License, or
 * (at your option) any later version.
 *
 * libqb is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with libqb.  If not, see <http://www.gnu.org/licenses/>.
 */
#include "os_base.h"
#include <signal.h>
#include <syslog.h>

#include <qb/qbdefs.h>
#include <qb/qblog.h>

#define MY_TAG_ONE   (1)
#define MY_TAG_TWO   (1 << 1)
#define MY_TAG_THREE (1 << 2)

static uint8_t _log_priority = LOG_WARNING;

static void
func_one(void)
{
        FILE *fd;

        qb_enter();
        qb_logt(LOG_DEBUG, MY_TAG_TWO, "arf arf?");
        qb_logt(LOG_CRIT, MY_TAG_THREE, "arrrg!");
        qb_logt(134, MY_TAG_THREE, "big priority");
        qb_logt(LOG_ERR, MY_TAG_THREE, "oops, I did it again");
        qb_log(LOG_INFO, "are you aware ...");

        fd = fopen("/nothing.txt", "r+");
        if (fd == NULL) {
                qb_perror(LOG_ERR, "can't open(\"/nothing.txt\")");
        } else {
                fclose(fd);
        }
        qb_leave();
}

static void
func_two(void)
{
        qb_enter();
        qb_logt(LOG_DEBUG, 0, "arf arf?");
        qb_logt(LOG_CRIT, MY_TAG_ONE, "arrrg!");
        qb_log(LOG_ERR, "oops, I did it again");
        qb_logt(LOG_INFO, MY_TAG_THREE, "are you aware ...");
        qb_leave();
}

static void
show_usage(const char *name)
{
        printf("usage: \n");
        printf("%s <options>\n", name);
        printf("\n");
        printf("  options:\n");
        printf("\n");
        printf("  -v             verbose\n");
        printf("  -t             threaded logging\n");
        printf("  -o             log to stdout\n");
        printf("  -e             log to stderr\n");
        printf("  -b             log to blackbox\n");
        printf("  -f <filename>  log to a file\n");
        printf("  -h             show this help text\n");
        printf("\n");
}

static int32_t do_blackbox = QB_FALSE;
static int32_t do_threaded = QB_FALSE;

static void
sigsegv_handler(int sig)
{
        (void)signal(SIGSEGV, SIG_DFL);
        if (do_blackbox) {
                qb_log_blackbox_write_to_file("simple-log.fdata");
        }
        qb_log_ctl(QB_LOG_BLACKBOX, QB_LOG_CONF_ENABLED, QB_FALSE);
        raise(SIGSEGV);
}

static const char *
my_tags_stringify(uint32_t tags)
{
        if (qb_bit_is_set(tags, QB_LOG_TAG_LIBQB_MSG_BIT)) {
                return "libqb";
        } else if (qb_bit_is_set(tags, 0)) {
                return "ONE";
        } else if (qb_bit_is_set(tags, 1)) {
                return "TWO";
        } else if (qb_bit_is_set(tags, 2)) {
                return "THREE";
        } else {
                return "MAIN";
        }
}

static void
trace_logger(int32_t t,
             struct qb_log_callsite *cs, time_t timestamp, const char *msg)
{
        char output_buffer[QB_LOG_MAX_LEN];
        output_buffer[0] = '\0';
        qb_log_target_format(t, cs, timestamp, msg, output_buffer);
        fprintf(stderr, "%s\n", output_buffer);
}

static void
m_filter(struct qb_log_callsite *cs)
{
        if ((cs->priority >= LOG_ALERT &&
             cs->priority <= _log_priority) &&
            strcmp(cs->filename, __FILE__) == 0) {
                qb_bit_set(cs->targets, QB_LOG_STDERR);
        } else {
                qb_bit_clear(cs->targets, QB_LOG_STDERR);
        }
}

int32_t
main(int32_t argc, char *argv[])
{
        const char *options = "vhteobdf:";
        int32_t opt;
        int32_t tracer;
        int32_t do_stderr = QB_FALSE;
        int32_t do_stdout = QB_FALSE;
        int32_t do_dump_blackbox = QB_FALSE;
        char *logfile = NULL;
        int32_t log_fd = -1;

        while ((opt = getopt(argc, argv, options)) != -1) {
                switch (opt) {
                case 'd':
                        do_dump_blackbox = QB_TRUE;
                        break;
                case 't':
                        do_threaded = QB_TRUE;
                        break;
                case 'e':
                        do_stderr = QB_TRUE;
                        break;
                case 'o':
                        do_stdout = QB_TRUE;
                        break;
                case 'b':
                        do_blackbox = QB_TRUE;
                        break;
                case 'f':
                        logfile = optarg;
                        break;
                case 'v':
                        _log_priority++;
                        break;
                case 'h':
                default:
                        show_usage(argv[0]);
                        exit(0);
                        break;
                }
        }

        if (do_dump_blackbox) {
                qb_log_blackbox_print_from_file("simple-log.fdata");
                exit(0);
        }

        signal(SIGSEGV, sigsegv_handler);

        qb_log_init("simple-log", LOG_USER, LOG_INFO);
        qb_log_ctl(QB_LOG_SYSLOG, QB_LOG_CONF_THREADED, do_threaded);
        qb_log_tags_stringify_fn_set(my_tags_stringify);

        if (do_stderr) {
                qb_log_filter_fn_set(m_filter);
                qb_log_format_set(QB_LOG_STDERR, "[%p] %4g: %f:%l %b");
                qb_log_ctl(QB_LOG_STDERR, QB_LOG_CONF_ENABLED, QB_TRUE);

                tracer = qb_log_custom_open(trace_logger, NULL, NULL, NULL);
                qb_log_ctl(tracer, QB_LOG_CONF_ENABLED, QB_TRUE);
                qb_log_format_set(tracer, "%4g: %n() %b");
                qb_log_filter_ctl2(tracer, QB_LOG_FILTER_ADD,
                                   QB_LOG_FILTER_FILE, __FILE__,
                                   LOG_TRACE, 200);
        }
        if (do_stdout) {
                qb_log_filter_ctl2(QB_LOG_STDOUT, QB_LOG_FILTER_ADD,
                                   QB_LOG_FILTER_FILE, __FILE__,
                                   LOG_ALERT, QB_MIN(LOG_DEBUG, _log_priority));
                qb_log_format_set(QB_LOG_STDOUT, "[%p] %4g: %f:%l %b");
                qb_log_ctl(QB_LOG_STDOUT, QB_LOG_CONF_ENABLED, QB_TRUE);
        }
        if (do_blackbox) {
                qb_log_filter_ctl(QB_LOG_BLACKBOX, QB_LOG_FILTER_ADD,
                                  QB_LOG_FILTER_FILE, "*", LOG_DEBUG);
                qb_log_ctl(QB_LOG_BLACKBOX, QB_LOG_CONF_SIZE, 4096);
                qb_log_ctl(QB_LOG_BLACKBOX, QB_LOG_CONF_THREADED, QB_FALSE);
                qb_log_ctl(QB_LOG_BLACKBOX, QB_LOG_CONF_ENABLED, QB_TRUE);
        }
        if (logfile) {
                log_fd = qb_log_file_open(logfile);
                qb_log_filter_ctl(log_fd, QB_LOG_FILTER_ADD,
                                  QB_LOG_FILTER_FILE, __FILE__, _log_priority);
                qb_log_format_set(log_fd, "[%N] %t %n() [%p] %b");
                qb_log_ctl(log_fd, QB_LOG_CONF_THREADED, do_threaded);
                qb_log_ctl(log_fd, QB_LOG_CONF_ENABLED, QB_TRUE);
        }
        if (do_threaded) {
                qb_log_thread_start();
        }
        qb_log(LOG_DEBUG, "hello");
        qb_log(LOG_INFO, "this is an info");
        qb_log(LOG_NOTICE, "hello - notice?");
        {
                char * str = NULL;
                qb_log(LOG_ERR,
                       "%s-%d-%s-%u",
                       NULL, 952, str, 56);
        }
        func_one();
        func_two();

        if (!do_threaded) {
                /* Disabling syslog here will prevent the logs from
                 * getting flushed in qb_log_fini() if threaded
                 * logging is on.
                 */
                qb_log_ctl(QB_LOG_SYSLOG, QB_LOG_CONF_ENABLED, QB_FALSE);

                qb_log(LOG_WARNING, "no syslog");
                qb_log(LOG_ERR, "no syslog");
        }

        if (do_blackbox) {
                logfile = NULL;
                logfile[5] = 'a';
        } else {
                qb_log_fini();
        }
        return 0;
}
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Defines

Generated on 18 Mar 2016 for libqb by  doxygen 1.6.1