1 /*
2 * Copyright (c) 2015-2016 Red Hat, Inc.
3 *
4 * All rights reserved.
5 *
6 * Author: Jan Friesse (jfriesse@redhat.com)
7 *
8 * This software licensed under BSD license, the text of which follows:
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions are met:
12 *
13 * - Redistributions of source code must retain the above copyright notice,
14 * this list of conditions and the following disclaimer.
15 * - Redistributions in binary form must reproduce the above copyright notice,
16 * this list of conditions and the following disclaimer in the documentation
17 * and/or other materials provided with the distribution.
18 * - Neither the name of the Red Hat, Inc. nor the names of its
19 * contributors may be used to endorse or promote products derived from this
20 * software without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
23 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
26 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
27 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
28 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
29 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
30 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
31 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
32 * THE POSSIBILITY OF SUCH DAMAGE.
33 */
34
35 #include <syslog.h>
36 #include <stdio.h>
37 #include <time.h>
38
39 #include "qnet-config.h"
40 #include "qnetd-log.h"
41
42 static int qnetd_log_config_target = 0;
43 static int qnetd_log_config_debug = 0;
44 static int qnetd_log_config_priority_bump = 0;
45
46 static const char qnetd_log_month_str[][4] = {
47 "Jan", "Feb", "Mar", "Apr", "May", "Jun",
48 "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
49 };
50
51 struct qnetd_log_syslog_prio_to_str_item {
52 int priority;
53 const char *priority_str;
54 };
55
56 static struct qnetd_log_syslog_prio_to_str_item qnetd_syslog_prio_to_str_array[] = {
57 {LOG_EMERG, "emerg"},
58 {LOG_ALERT, "alert"},
59 {LOG_CRIT, "crit"},
60 {LOG_ERR, "error"},
61 {LOG_WARNING, "warning"},
62 {LOG_NOTICE, "notice"},
63 {LOG_INFO, "info"},
64 {LOG_DEBUG, "debug"},
65 {-1, NULL}};
66
67 void
qnetd_log_init(int target)68 qnetd_log_init(int target)
69 {
70
71 qnetd_log_config_target = target;
72
73 if (qnetd_log_config_target & QNETD_LOG_TARGET_SYSLOG) {
74 openlog(QNETD_PROGRAM_NAME, LOG_PID, LOG_DAEMON);
75 }
76 }
77
78 static const char *
qnetd_log_syslog_prio_to_str(int priority)79 qnetd_log_syslog_prio_to_str(int priority)
80 {
81
82 if (priority >= LOG_EMERG && priority <= LOG_DEBUG) {
83 return (qnetd_syslog_prio_to_str_array[priority].priority_str);
84 } else {
85 return ("none");
86 }
87 }
88
89 void
qnetd_log_vprintf(int priority,const char * format,va_list ap)90 qnetd_log_vprintf(int priority, const char *format, va_list ap)
91 {
92 time_t current_time;
93 struct tm tm_res;
94 int final_priority;
95 va_list ap_copy;
96
97 if (priority != LOG_DEBUG || (qnetd_log_config_debug)) {
98 if (qnetd_log_config_target & QNETD_LOG_TARGET_STDERR) {
99 current_time = time(NULL);
100 localtime_r(¤t_time, &tm_res);
101
102 fprintf(stderr, "%s %02d %02d:%02d:%02d ",
103 qnetd_log_month_str[tm_res.tm_mon], tm_res.tm_mday, tm_res.tm_hour,
104 tm_res.tm_min, tm_res.tm_sec);
105
106 fprintf(stderr, "%-7s ", qnetd_log_syslog_prio_to_str(priority));
107
108 va_copy(ap_copy, ap);
109 vfprintf(stderr, format, ap_copy);
110 va_end(ap_copy);
111 fprintf(stderr, "\n");
112 }
113
114 if (qnetd_log_config_target & QNETD_LOG_TARGET_SYSLOG) {
115 final_priority = priority;
116 if (qnetd_log_config_priority_bump && priority > LOG_INFO) {
117 final_priority = LOG_INFO;
118 }
119
120 va_copy(ap_copy, ap);
121 vsyslog(final_priority, format, ap);
122 va_end(ap_copy);
123 }
124 }
125 }
126
127 void
qnetd_log_printf(int priority,const char * format,...)128 qnetd_log_printf(int priority, const char *format, ...)
129 {
130 va_list ap;
131
132 va_start(ap, format);
133
134 qnetd_log_vprintf(priority, format, ap);
135
136 va_end(ap);
137 }
138
139 void
qnetd_log_close(void)140 qnetd_log_close(void)
141 {
142
143 if (qnetd_log_config_target & QNETD_LOG_TARGET_SYSLOG) {
144 closelog();
145 }
146 }
147
148 void
qnetd_log_set_debug(int enabled)149 qnetd_log_set_debug(int enabled)
150 {
151
152 qnetd_log_config_debug = enabled;
153 }
154
155 void
qnetd_log_set_priority_bump(int enabled)156 qnetd_log_set_priority_bump(int enabled)
157 {
158
159 qnetd_log_config_priority_bump = enabled;
160 }
161
162 void
qnetd_log_msg_decode_error(int ret)163 qnetd_log_msg_decode_error(int ret)
164 {
165
166 switch (ret) {
167 case -1:
168 qnetd_log(LOG_WARNING, "Received message with option with invalid length");
169 break;
170 case -2:
171 qnetd_log(LOG_CRIT, "Can't allocate memory");
172 break;
173 case -3:
174 qnetd_log(LOG_WARNING, "Received inconsistent msg (tlv len > msg size)");
175 break;
176 case -4:
177 qnetd_log(LOG_WARNING, "Received message with option with invalid value");
178 break;
179 default:
180 qnetd_log(LOG_ERR, "Unknown error occurred when decoding message");
181 break;
182 }
183 }
184