blob: e2079d1ff2ba29488066ce10878100c3b4ffe307 [file] [log] [blame]
Radek Krejci5fe60cc2015-09-01 17:14:39 +02001/**
Michal Vasko95ea9ff2021-11-09 12:29:14 +01002 * @file log.c
3 * @author Radek Krejci <rkrejci@cesnet.cz>
4 * @brief libnetconf2 - log functions
Radek Krejci5fe60cc2015-09-01 17:14:39 +02005 *
Michal Vasko95ea9ff2021-11-09 12:29:14 +01006 * @copyright
Michal Vasko05532772021-06-03 12:12:38 +02007 * Copyright (c) 2015 - 2021 CESNET, z.s.p.o.
Radek Krejci5fe60cc2015-09-01 17:14:39 +02008 *
Radek Krejci9b81f5b2016-02-24 13:14:49 +01009 * This source code is licensed under BSD 3-Clause License (the "License").
10 * You may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
Michal Vaskoafd416b2016-02-25 14:51:46 +010012 *
Radek Krejci9b81f5b2016-02-24 13:14:49 +010013 * https://opensource.org/licenses/BSD-3-Clause
Radek Krejci5fe60cc2015-09-01 17:14:39 +020014 */
15
Michal Vaskoba9f3582023-02-22 10:26:32 +010016#define _GNU_SOURCE /* pthread_rwlock_t */
17
Radek Krejci5fe60cc2015-09-01 17:14:39 +020018#include <stdarg.h>
Radek Krejci5fe60cc2015-09-01 17:14:39 +020019#include <stdio.h>
roman3f9b65c2023-06-05 14:26:58 +020020#include <stdlib.h>
Radek Krejci5fe60cc2015-09-01 17:14:39 +020021
Michal Vaskoa601f5c2015-12-08 14:33:03 +010022#include <libyang/libyang.h>
23
roman2eab4742023-06-06 10:00:26 +020024#ifdef NC_ENABLED_SSH_TLS
Michal Vaskob078fee2016-09-29 11:30:31 +020025 #include <libssh/libssh.h>
roman2eab4742023-06-06 10:00:26 +020026#endif /* NC_ENABLED_SSH_TLS */
Michal Vaskob078fee2016-09-29 11:30:31 +020027
Michal Vasko7a20d2e2021-05-19 16:40:23 +020028#include "compat.h"
roman3f9b65c2023-06-05 14:26:58 +020029#include "config.h"
Michal Vaskob078fee2016-09-29 11:30:31 +020030#include "log.h"
roman3f9b65c2023-06-05 14:26:58 +020031#include "session_p.h"
Radek Krejci5fe60cc2015-09-01 17:14:39 +020032
33/**
34 * @brief libnetconf verbose level variable
35 */
Václav Kubernáta4474cf2022-01-17 12:37:22 +010036ATOMIC_T verbose_level = 0;
Radek Krejci5fe60cc2015-09-01 17:14:39 +020037
Michal Vasko05532772021-06-03 12:12:38 +020038void (*print_clb)(const struct nc_session *session, NC_VERB_LEVEL level, const char *msg);
Michal Vasko206d3b12015-12-04 11:08:42 +010039
Radek Krejci5fe60cc2015-09-01 17:14:39 +020040API void
41nc_verbosity(NC_VERB_LEVEL level)
42{
Václav Kubernáta4474cf2022-01-17 12:37:22 +010043 ATOMIC_STORE_RELAXED(verbose_level, level);
Michal Vasko77367452021-02-16 16:32:18 +010044 ly_log_level((LY_LOG_LEVEL)level);
Radek Krejci5fe60cc2015-09-01 17:14:39 +020045}
46
47struct {
48 NC_VERB_LEVEL level;
49 const char *label;
50} verb[] = {
bhartb186eba2018-11-12 15:35:09 -060051 {NC_VERB_ERROR, "[ERR]"},
52 {NC_VERB_WARNING, "[WRN]"},
53 {NC_VERB_VERBOSE, "[INF]"},
Michal Vasko2733aad2020-04-16 09:01:52 +020054 {NC_VERB_DEBUG, "[DBG]"},
55 {NC_VERB_DEBUG_LOWLVL, "[DBL]"}
Radek Krejci5fe60cc2015-09-01 17:14:39 +020056};
57
roman2eab4742023-06-06 10:00:26 +020058#ifdef NC_ENABLED_SSH_TLS
Michal Vaskob078fee2016-09-29 11:30:31 +020059
60API void
61nc_libssh_thread_verbosity(int level)
62{
63 ssh_set_log_level(level);
64}
65
roman2eab4742023-06-06 10:00:26 +020066#endif /* NC_ENABLED_SSH_TLS */
Michal Vaskob078fee2016-09-29 11:30:31 +020067
Radek Krejci5fe60cc2015-09-01 17:14:39 +020068static void
Michal Vasko05532772021-06-03 12:12:38 +020069prv_vprintf(const struct nc_session *session, NC_VERB_LEVEL level, const char *format, va_list args)
Radek Krejci5fe60cc2015-09-01 17:14:39 +020070{
Michal Vaskofe5e8c92021-04-14 08:23:12 +020071#define PRV_MSG_INIT_SIZE 256
72 va_list args2;
73 char *prv_msg;
74 void *mem;
75 int req_len;
Radek Krejci5fe60cc2015-09-01 17:14:39 +020076
Michal Vaskofe5e8c92021-04-14 08:23:12 +020077 prv_msg = malloc(PRV_MSG_INIT_SIZE);
78 if (!prv_msg) {
79 return;
80 }
81
82 va_copy(args2, args);
83
84 req_len = vsnprintf(prv_msg, PRV_MSG_INIT_SIZE - 1, format, args);
85 if (req_len == -1) {
86 goto cleanup;
87 } else if (req_len >= PRV_MSG_INIT_SIZE - 1) {
88 /* the length is not enough */
89 ++req_len;
90 mem = realloc(prv_msg, req_len);
91 if (!mem) {
92 goto cleanup;
93 }
94 prv_msg = mem;
95
96 /* now print the full message */
97 req_len = vsnprintf(prv_msg, req_len, format, args2);
98 if (req_len == -1) {
99 goto cleanup;
100 }
101 }
Radek Krejci5fe60cc2015-09-01 17:14:39 +0200102
Michal Vasko206d3b12015-12-04 11:08:42 +0100103 if (print_clb) {
Michal Vasko05532772021-06-03 12:12:38 +0200104 print_clb(session, level, prv_msg);
Michal Vasko05532772021-06-03 12:12:38 +0200105 } else if (session && session->id) {
Michal Vasko16374712024-04-26 14:13:00 +0200106 fprintf(stderr, "Session %" PRIu32 " %s: %s\n", session->id, verb[level].label, prv_msg);
Michal Vasko206d3b12015-12-04 11:08:42 +0100107 } else {
108 fprintf(stderr, "%s: %s\n", verb[level].label, prv_msg);
109 }
Radek Krejci5fe60cc2015-09-01 17:14:39 +0200110
Michal Vaskofe5e8c92021-04-14 08:23:12 +0200111cleanup:
112 free(prv_msg);
113#undef PRV_MSG_INIT_SIZE
Radek Krejci5fe60cc2015-09-01 17:14:39 +0200114}
115
116void
Michal Vasko05532772021-06-03 12:12:38 +0200117prv_printf(const struct nc_session *session, NC_VERB_LEVEL level, const char *format, ...)
Radek Krejci5fe60cc2015-09-01 17:14:39 +0200118{
119 va_list ap;
120
121 va_start(ap, format);
Michal Vasko05532772021-06-03 12:12:38 +0200122 prv_vprintf(session, level, format, ap);
Radek Krejci5fe60cc2015-09-01 17:14:39 +0200123 va_end(ap);
124}
125
126API void
Michal Vasko05532772021-06-03 12:12:38 +0200127nc_set_print_clb_session(void (*clb)(const struct nc_session *, NC_VERB_LEVEL, const char *))
128{
Michal Vasko206d3b12015-12-04 11:08:42 +0100129 print_clb = clb;
130}