1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2010 Lennart Poettering
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
30 #include <sys/signalfd.h>
31 #include <sys/socket.h>
38 #include "sd-messages.h"
40 #include "alloc-util.h"
42 #include "formats-util.h"
47 #include "parse-util.h"
48 #include "proc-cmdline.h"
49 #include "process-util.h"
50 #include "signal-util.h"
51 #include "socket-util.h"
52 #include "stdio-util.h"
53 #include "string-table.h"
54 #include "string-util.h"
55 #include "syslog-util.h"
56 #include "terminal-util.h"
57 #include "time-util.h"
60 #define SNDBUF_SIZE (8*1024*1024)
62 static LogTarget log_target
= LOG_TARGET_CONSOLE
;
63 static int log_max_level
= LOG_INFO
;
64 static int log_facility
= LOG_DAEMON
;
66 static int console_fd
= STDERR_FILENO
;
67 static int syslog_fd
= -1;
68 static int kmsg_fd
= -1;
69 static int journal_fd
= -1;
71 static bool syslog_is_stream
= false;
73 static bool show_color
= false;
74 static bool show_location
= false;
76 static bool upgrade_syslog_to_journal
= false;
78 /* Akin to glibc's __abort_msg; which is private and we hence cannot
80 static char *log_abort_msg
= NULL
;
82 void log_close_console(void) {
89 safe_close(console_fd
);
95 static int log_open_console(void) {
101 console_fd
= open_terminal("/dev/console", O_WRONLY
|O_NOCTTY
|O_CLOEXEC
);
105 console_fd
= STDERR_FILENO
;
110 void log_close_kmsg(void) {
111 kmsg_fd
= safe_close(kmsg_fd
);
114 static int log_open_kmsg(void) {
119 kmsg_fd
= open("/dev/kmsg", O_WRONLY
|O_NOCTTY
|O_CLOEXEC
);
126 void log_close_syslog(void) {
127 syslog_fd
= safe_close(syslog_fd
);
130 static int create_log_socket(int type
) {
134 fd
= socket(AF_UNIX
, type
|SOCK_CLOEXEC
, 0);
138 fd_inc_sndbuf(fd
, SNDBUF_SIZE
);
140 /* We need a blocking fd here since we'd otherwise lose
141 messages way too early. However, let's not hang forever in the
142 unlikely case of a deadlock. */
144 timeval_store(&tv
, 10 * USEC_PER_MSEC
);
146 timeval_store(&tv
, 10 * USEC_PER_SEC
);
147 (void) setsockopt(fd
, SOL_SOCKET
, SO_SNDTIMEO
, &tv
, sizeof(tv
));
152 static int log_open_syslog(void) {
154 static const union sockaddr_union sa
= {
155 .un
.sun_family
= AF_UNIX
,
156 .un
.sun_path
= "/dev/log",
164 syslog_fd
= create_log_socket(SOCK_DGRAM
);
170 if (connect(syslog_fd
, &sa
.sa
, offsetof(struct sockaddr_un
, sun_path
) + strlen(sa
.un
.sun_path
)) < 0) {
171 safe_close(syslog_fd
);
173 /* Some legacy syslog systems still use stream
174 * sockets. They really shouldn't. But what can we
176 syslog_fd
= create_log_socket(SOCK_STREAM
);
182 if (connect(syslog_fd
, &sa
.sa
, offsetof(struct sockaddr_un
, sun_path
) + strlen(sa
.un
.sun_path
)) < 0) {
187 syslog_is_stream
= true;
189 syslog_is_stream
= false;
198 void log_close_journal(void) {
199 journal_fd
= safe_close(journal_fd
);
202 static int log_open_journal(void) {
204 static const union sockaddr_union sa
= {
205 .un
.sun_family
= AF_UNIX
,
206 .un
.sun_path
= "/run/systemd/journal/socket",
214 journal_fd
= create_log_socket(SOCK_DGRAM
);
215 if (journal_fd
< 0) {
220 if (connect(journal_fd
, &sa
.sa
, offsetof(struct sockaddr_un
, sun_path
) + strlen(sa
.un
.sun_path
)) < 0) {
235 /* If we don't use the console we close it here, to not get
236 * killed by SAK. If we don't use syslog we close it here so
237 * that we are not confused by somebody deleting the socket in
238 * the fs. If we don't use /dev/kmsg we still keep it open,
239 * because there is no reason to close it. */
241 if (log_target
== LOG_TARGET_NULL
) {
248 if ((log_target
!= LOG_TARGET_AUTO
&& log_target
!= LOG_TARGET_SAFE
) ||
250 isatty(STDERR_FILENO
) <= 0) {
252 if (log_target
== LOG_TARGET_AUTO
||
253 log_target
== LOG_TARGET_JOURNAL_OR_KMSG
||
254 log_target
== LOG_TARGET_JOURNAL
) {
255 r
= log_open_journal();
263 if (log_target
== LOG_TARGET_SYSLOG_OR_KMSG
||
264 log_target
== LOG_TARGET_SYSLOG
) {
265 r
= log_open_syslog();
273 if (log_target
== LOG_TARGET_AUTO
||
274 log_target
== LOG_TARGET_SAFE
||
275 log_target
== LOG_TARGET_JOURNAL_OR_KMSG
||
276 log_target
== LOG_TARGET_SYSLOG_OR_KMSG
||
277 log_target
== LOG_TARGET_KMSG
) {
291 return log_open_console();
294 void log_set_target(LogTarget target
) {
296 assert(target
< _LOG_TARGET_MAX
);
298 if (upgrade_syslog_to_journal
) {
299 if (target
== LOG_TARGET_SYSLOG
)
300 target
= LOG_TARGET_JOURNAL
;
301 else if (target
== LOG_TARGET_SYSLOG_OR_KMSG
)
302 target
= LOG_TARGET_JOURNAL_OR_KMSG
;
308 void log_close(void) {
315 void log_forget_fds(void) {
316 console_fd
= kmsg_fd
= syslog_fd
= journal_fd
= -1;
319 void log_set_max_level(int level
) {
320 assert((level
& LOG_PRIMASK
) == level
);
322 log_max_level
= level
;
325 void log_set_facility(int facility
) {
326 log_facility
= facility
;
329 static int write_to_console(
335 const char *object_field
,
337 const char *buffer
) {
339 char location
[64], prefix
[1 + DECIMAL_STR_MAX(int) + 2];
340 struct iovec iovec
[6] = {};
347 if (log_target
== LOG_TARGET_CONSOLE_PREFIXED
) {
348 sprintf(prefix
, "<%i>", level
);
349 IOVEC_SET_STRING(iovec
[n
++], prefix
);
352 highlight
= LOG_PRI(level
) <= LOG_ERR
&& show_color
;
355 xsprintf(location
, "(%s:%i) ", file
, line
);
356 IOVEC_SET_STRING(iovec
[n
++], location
);
360 IOVEC_SET_STRING(iovec
[n
++], ANSI_HIGHLIGHT_RED
);
361 IOVEC_SET_STRING(iovec
[n
++], buffer
);
363 IOVEC_SET_STRING(iovec
[n
++], ANSI_NORMAL
);
364 IOVEC_SET_STRING(iovec
[n
++], "\n");
366 if (writev(console_fd
, iovec
, n
) < 0) {
368 if (errno
== EIO
&& getpid() == 1) {
370 /* If somebody tried to kick us from our
371 * console tty (via vhangup() or suchlike),
372 * try to reconnect */
380 if (writev(console_fd
, iovec
, n
) < 0)
389 static int write_to_syslog(
395 const char *object_field
,
397 const char *buffer
) {
399 char header_priority
[2 + DECIMAL_STR_MAX(int) + 1],
401 header_pid
[4 + DECIMAL_STR_MAX(pid_t
) + 1];
402 struct iovec iovec
[5] = {};
403 struct msghdr msghdr
= {
405 .msg_iovlen
= ELEMENTSOF(iovec
),
413 xsprintf(header_priority
, "<%i>", level
);
415 t
= (time_t) (now(CLOCK_REALTIME
) / USEC_PER_SEC
);
420 if (strftime(header_time
, sizeof(header_time
), "%h %e %T ", tm
) <= 0)
423 xsprintf(header_pid
, "["PID_FMT
"]: ", getpid());
425 IOVEC_SET_STRING(iovec
[0], header_priority
);
426 IOVEC_SET_STRING(iovec
[1], header_time
);
427 IOVEC_SET_STRING(iovec
[2], program_invocation_short_name
);
428 IOVEC_SET_STRING(iovec
[3], header_pid
);
429 IOVEC_SET_STRING(iovec
[4], buffer
);
431 /* When using syslog via SOCK_STREAM separate the messages by NUL chars */
432 if (syslog_is_stream
)
438 n
= sendmsg(syslog_fd
, &msghdr
, MSG_NOSIGNAL
);
442 if (!syslog_is_stream
||
443 (size_t) n
>= IOVEC_TOTAL_SIZE(iovec
, ELEMENTSOF(iovec
)))
446 IOVEC_INCREMENT(iovec
, ELEMENTSOF(iovec
), n
);
452 static int write_to_kmsg(
458 const char *object_field
,
460 const char *buffer
) {
462 char header_priority
[2 + DECIMAL_STR_MAX(int) + 1],
463 header_pid
[4 + DECIMAL_STR_MAX(pid_t
) + 1];
464 struct iovec iovec
[5] = {};
469 xsprintf(header_priority
, "<%i>", level
);
470 xsprintf(header_pid
, "["PID_FMT
"]: ", getpid());
472 IOVEC_SET_STRING(iovec
[0], header_priority
);
473 IOVEC_SET_STRING(iovec
[1], program_invocation_short_name
);
474 IOVEC_SET_STRING(iovec
[2], header_pid
);
475 IOVEC_SET_STRING(iovec
[3], buffer
);
476 IOVEC_SET_STRING(iovec
[4], "\n");
478 if (writev(kmsg_fd
, iovec
, ELEMENTSOF(iovec
)) < 0)
484 static int log_do_header(
489 const char *file
, int line
, const char *func
,
490 const char *object_field
, const char *object
) {
492 snprintf(header
, size
,
494 "SYSLOG_FACILITY=%i\n"
500 "SYSLOG_IDENTIFIER=%s\n",
503 isempty(file
) ? "" : "CODE_FILE=",
504 isempty(file
) ? "" : file
,
505 isempty(file
) ? "" : "\n",
506 line
? "CODE_LINE=" : "",
507 line
? 1 : 0, line
, /* %.0d means no output too, special case for 0 */
509 isempty(func
) ? "" : "CODE_FUNCTION=",
510 isempty(func
) ? "" : func
,
511 isempty(func
) ? "" : "\n",
512 error
? "ERRNO=" : "",
513 error
? 1 : 0, error
,
515 isempty(object
) ? "" : object_field
,
516 isempty(object
) ? "" : object
,
517 isempty(object
) ? "" : "\n",
518 program_invocation_short_name
);
523 static int write_to_journal(
529 const char *object_field
,
531 const char *buffer
) {
533 char header
[LINE_MAX
];
534 struct iovec iovec
[4] = {};
535 struct msghdr mh
= {};
540 log_do_header(header
, sizeof(header
), level
, error
, file
, line
, func
, object_field
, object
);
542 IOVEC_SET_STRING(iovec
[0], header
);
543 IOVEC_SET_STRING(iovec
[1], "MESSAGE=");
544 IOVEC_SET_STRING(iovec
[2], buffer
);
545 IOVEC_SET_STRING(iovec
[3], "\n");
548 mh
.msg_iovlen
= ELEMENTSOF(iovec
);
550 if (sendmsg(journal_fd
, &mh
, MSG_NOSIGNAL
) < 0)
556 static int log_dispatch(
562 const char *object_field
,
568 if (log_target
== LOG_TARGET_NULL
)
571 /* Patch in LOG_DAEMON facility if necessary */
572 if ((level
& LOG_FACMASK
) == 0)
573 level
= log_facility
| LOG_PRI(level
);
582 buffer
+= strspn(buffer
, NEWLINE
);
587 if ((e
= strpbrk(buffer
, NEWLINE
)))
590 if (log_target
== LOG_TARGET_AUTO
||
591 log_target
== LOG_TARGET_JOURNAL_OR_KMSG
||
592 log_target
== LOG_TARGET_JOURNAL
) {
594 k
= write_to_journal(level
, error
, file
, line
, func
, object_field
, object
, buffer
);
602 if (log_target
== LOG_TARGET_SYSLOG_OR_KMSG
||
603 log_target
== LOG_TARGET_SYSLOG
) {
605 k
= write_to_syslog(level
, error
, file
, line
, func
, object_field
, object
, buffer
);
614 (log_target
== LOG_TARGET_AUTO
||
615 log_target
== LOG_TARGET_SAFE
||
616 log_target
== LOG_TARGET_SYSLOG_OR_KMSG
||
617 log_target
== LOG_TARGET_JOURNAL_OR_KMSG
||
618 log_target
== LOG_TARGET_KMSG
)) {
620 k
= write_to_kmsg(level
, error
, file
, line
, func
, object_field
, object
, buffer
);
628 (void) write_to_console(level
, error
, file
, line
, func
, object_field
, object
, buffer
);
636 int log_dump_internal(
646 /* This modifies the buffer... */
651 if (_likely_(LOG_PRI(level
) > log_max_level
))
654 return log_dispatch(level
, error
, file
, line
, func
, NULL
, NULL
, buffer
);
667 char buffer
[LINE_MAX
];
672 if (_likely_(LOG_PRI(level
) > log_max_level
))
675 /* Make sure that %m maps to the specified error */
679 vsnprintf(buffer
, sizeof(buffer
), format
, ap
);
681 return log_dispatch(level
, error
, file
, line
, func
, NULL
, NULL
, buffer
);
690 const char *format
, ...) {
695 va_start(ap
, format
);
696 r
= log_internalv(level
, error
, file
, line
, func
, format
, ap
);
702 int log_object_internalv(
708 const char *object_field
,
720 if (_likely_(LOG_PRI(level
) > log_max_level
))
723 /* Make sure that %m maps to the specified error */
727 /* Prepend the object name before the message */
732 l
= n
+ 2 + LINE_MAX
;
734 buffer
= newa(char, l
);
735 b
= stpcpy(stpcpy(buffer
, object
), ": ");
738 b
= buffer
= newa(char, l
);
741 vsnprintf(b
, l
, format
, ap
);
743 return log_dispatch(level
, error
, file
, line
, func
, object_field
, object
, buffer
);
746 int log_object_internal(
752 const char *object_field
,
754 const char *format
, ...) {
759 va_start(ap
, format
);
760 r
= log_object_internalv(level
, error
, file
, line
, func
, object_field
, object
, format
, ap
);
766 static void log_assert(
772 const char *format
) {
774 static char buffer
[LINE_MAX
];
776 if (_likely_(LOG_PRI(level
) > log_max_level
))
779 DISABLE_WARNING_FORMAT_NONLITERAL
;
780 xsprintf(buffer
, format
, text
, file
, line
, func
);
783 log_abort_msg
= buffer
;
785 log_dispatch(level
, 0, file
, line
, func
, NULL
, NULL
, buffer
);
788 noreturn
void log_assert_failed(const char *text
, const char *file
, int line
, const char *func
) {
789 log_assert(LOG_CRIT
, text
, file
, line
, func
, "Assertion '%s' failed at %s:%u, function %s(). Aborting.");
793 noreturn
void log_assert_failed_unreachable(const char *text
, const char *file
, int line
, const char *func
) {
794 log_assert(LOG_CRIT
, text
, file
, line
, func
, "Code should not be reached '%s' at %s:%u, function %s(). Aborting.");
798 void log_assert_failed_return(const char *text
, const char *file
, int line
, const char *func
) {
800 log_assert(LOG_DEBUG
, text
, file
, line
, func
, "Assertion '%s' failed at %s:%u, function %s(). Ignoring.");
803 int log_oom_internal(const char *file
, int line
, const char *func
) {
804 log_internal(LOG_ERR
, ENOMEM
, file
, line
, func
, "Out of memory.");
808 int log_format_iovec(
812 bool newline_separator
,
817 static const char nl
= '\n';
819 while (format
&& *n
+ 1 < iovec_len
) {
824 /* We need to copy the va_list structure,
825 * since vasprintf() leaves it afterwards at
826 * an undefined location */
832 r
= vasprintf(&m
, format
, aq
);
837 /* Now, jump enough ahead, so that we point to
838 * the next format string */
839 VA_FORMAT_ADVANCE(format
, ap
);
841 IOVEC_SET_STRING(iovec
[(*n
)++], m
);
843 if (newline_separator
) {
844 iovec
[*n
].iov_base
= (char*) &nl
;
845 iovec
[*n
].iov_len
= 1;
849 format
= va_arg(ap
, char *);
854 int log_struct_internal(
860 const char *format
, ...) {
870 if (_likely_(LOG_PRI(level
) > log_max_level
))
873 if (log_target
== LOG_TARGET_NULL
)
876 if ((level
& LOG_FACMASK
) == 0)
877 level
= log_facility
| LOG_PRI(level
);
879 if ((log_target
== LOG_TARGET_AUTO
||
880 log_target
== LOG_TARGET_JOURNAL_OR_KMSG
||
881 log_target
== LOG_TARGET_JOURNAL
) &&
883 char header
[LINE_MAX
];
884 struct iovec iovec
[17] = {};
890 bool fallback
= false;
892 /* If the journal is available do structured logging */
893 log_do_header(header
, sizeof(header
), level
, error
, file
, line
, func
, NULL
, NULL
);
894 IOVEC_SET_STRING(iovec
[n
++], header
);
896 va_start(ap
, format
);
897 r
= log_format_iovec(iovec
, ELEMENTSOF(iovec
), &n
, true, error
, format
, ap
);
902 (void) sendmsg(journal_fd
, &mh
, MSG_NOSIGNAL
);
906 for (i
= 1; i
< n
; i
+= 2)
907 free(iovec
[i
].iov_base
);
913 /* Fallback if journal logging is not available or didn't work. */
915 va_start(ap
, format
);
923 vsnprintf(buf
, sizeof(buf
), format
, aq
);
926 if (startswith(buf
, "MESSAGE=")) {
931 VA_FORMAT_ADVANCE(format
, ap
);
933 format
= va_arg(ap
, char *);
940 return log_dispatch(level
, error
, file
, line
, func
, NULL
, NULL
, buf
+ 8);
943 int log_set_target_from_string(const char *e
) {
946 t
= log_target_from_string(e
);
954 int log_set_max_level_from_string(const char *e
) {
957 t
= log_level_from_string(e
);
961 log_set_max_level(t
);
965 static int parse_proc_cmdline_item(const char *key
, const char *value
) {
968 * The systemd.log_xyz= settings are parsed by all tools, and
971 * However, "quiet" is only parsed by PID 1, and only turns of
972 * status output to /dev/console, but does not alter the log
976 if (streq(key
, "debug") && !value
)
977 log_set_max_level(LOG_DEBUG
);
979 else if (streq(key
, "systemd.log_target") && value
) {
981 if (log_set_target_from_string(value
) < 0)
982 log_warning("Failed to parse log target '%s'. Ignoring.", value
);
984 } else if (streq(key
, "systemd.log_level") && value
) {
986 if (log_set_max_level_from_string(value
) < 0)
987 log_warning("Failed to parse log level '%s'. Ignoring.", value
);
989 } else if (streq(key
, "systemd.log_color") && value
) {
991 if (log_show_color_from_string(value
) < 0)
992 log_warning("Failed to parse log color setting '%s'. Ignoring.", value
);
994 } else if (streq(key
, "systemd.log_location") && value
) {
996 if (log_show_location_from_string(value
) < 0)
997 log_warning("Failed to parse log location setting '%s'. Ignoring.", value
);
1003 void log_parse_environment(void) {
1006 if (get_ctty_devnr(0, NULL
) < 0)
1007 /* Only try to read the command line in daemons.
1008 We assume that anything that has a controlling
1009 tty is user stuff. */
1010 (void) parse_proc_cmdline(parse_proc_cmdline_item
);
1012 e
= secure_getenv("SYSTEMD_LOG_TARGET");
1013 if (e
&& log_set_target_from_string(e
) < 0)
1014 log_warning("Failed to parse log target '%s'. Ignoring.", e
);
1016 e
= secure_getenv("SYSTEMD_LOG_LEVEL");
1017 if (e
&& log_set_max_level_from_string(e
) < 0)
1018 log_warning("Failed to parse log level '%s'. Ignoring.", e
);
1020 e
= secure_getenv("SYSTEMD_LOG_COLOR");
1021 if (e
&& log_show_color_from_string(e
) < 0)
1022 log_warning("Failed to parse bool '%s'. Ignoring.", e
);
1024 e
= secure_getenv("SYSTEMD_LOG_LOCATION");
1025 if (e
&& log_show_location_from_string(e
) < 0)
1026 log_warning("Failed to parse bool '%s'. Ignoring.", e
);
1029 LogTarget
log_get_target(void) {
1033 int log_get_max_level(void) {
1034 return log_max_level
;
1037 void log_show_color(bool b
) {
1041 bool log_get_show_color(void) {
1045 void log_show_location(bool b
) {
1049 bool log_get_show_location(void) {
1050 return show_location
;
1053 int log_show_color_from_string(const char *e
) {
1056 t
= parse_boolean(e
);
1064 int log_show_location_from_string(const char *e
) {
1067 t
= parse_boolean(e
);
1071 log_show_location(t
);
1075 bool log_on_console(void) {
1076 if (log_target
== LOG_TARGET_CONSOLE
||
1077 log_target
== LOG_TARGET_CONSOLE_PREFIXED
)
1080 return syslog_fd
< 0 && kmsg_fd
< 0 && journal_fd
< 0;
1083 static const char *const log_target_table
[_LOG_TARGET_MAX
] = {
1084 [LOG_TARGET_CONSOLE
] = "console",
1085 [LOG_TARGET_CONSOLE_PREFIXED
] = "console-prefixed",
1086 [LOG_TARGET_KMSG
] = "kmsg",
1087 [LOG_TARGET_JOURNAL
] = "journal",
1088 [LOG_TARGET_JOURNAL_OR_KMSG
] = "journal-or-kmsg",
1089 [LOG_TARGET_SYSLOG
] = "syslog",
1090 [LOG_TARGET_SYSLOG_OR_KMSG
] = "syslog-or-kmsg",
1091 [LOG_TARGET_AUTO
] = "auto",
1092 [LOG_TARGET_SAFE
] = "safe",
1093 [LOG_TARGET_NULL
] = "null"
1096 DEFINE_STRING_TABLE_LOOKUP(log_target
, LogTarget
);
1098 void log_received_signal(int level
, const struct signalfd_siginfo
*si
) {
1099 if (si
->ssi_pid
> 0) {
1100 _cleanup_free_
char *p
= NULL
;
1102 get_process_comm(si
->ssi_pid
, &p
);
1105 "Received SIG%s from PID %"PRIu32
" (%s).",
1106 signal_to_string(si
->ssi_signo
),
1107 si
->ssi_pid
, strna(p
));
1111 signal_to_string(si
->ssi_signo
));
1115 void log_set_upgrade_syslog_to_journal(bool b
) {
1116 upgrade_syslog_to_journal
= b
;
1119 int log_syntax_internal(
1122 const char *config_file
,
1123 unsigned config_line
,
1128 const char *format
, ...) {
1131 char buffer
[LINE_MAX
];
1138 if (_likely_(LOG_PRI(level
) > log_max_level
))
1141 if (log_target
== LOG_TARGET_NULL
)
1147 va_start(ap
, format
);
1148 vsnprintf(buffer
, sizeof(buffer
), format
, ap
);
1152 r
= log_struct_internal(
1155 getpid() == 1 ? "UNIT=%s" : "USER_UNIT=%s", unit
,
1156 LOG_MESSAGE_ID(SD_MESSAGE_INVALID_CONFIGURATION
),
1157 "CONFIG_FILE=%s", config_file
,
1158 "CONFIG_LINE=%u", config_line
,
1159 LOG_MESSAGE("[%s:%u] %s", config_file
, config_line
, buffer
),
1162 r
= log_struct_internal(
1165 LOG_MESSAGE_ID(SD_MESSAGE_INVALID_CONFIGURATION
),
1166 "CONFIG_FILE=%s", config_file
,
1167 "CONFIG_LINE=%u", config_line
,
1168 LOG_MESSAGE("[%s:%u] %s", config_file
, config_line
, buffer
),