]> git.proxmox.com Git - mirror_frr.git/blobdiff - lib/log_vty.c
*: auto-convert to SPDX License IDs
[mirror_frr.git] / lib / log_vty.c
index 621949ab57f74eb16e14277c7933ef8567bf605c..fc28ffc6faf4c695806d1ceff315b555d3dc1bb2 100644 (file)
@@ -1,21 +1,8 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
 /*
  * Logging - VTY code
  * Copyright (C) 2019 Cumulus Networks, Inc.
  *                    Stephen Worley
- *
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the Free
- * Software Foundation; either version 2 of the License, or (at your option)
- * any later version.
- *
- * This program 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 General Public License for
- * more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; see the file COPYING; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
  */
 
 #include <zebra.h>
 #include "command.h"
 #include "lib/log.h"
 #include "lib/zlog_targets.h"
+#include "lib/zlog_5424.h"
 #include "lib/lib_errors.h"
 #include "lib/printfrr.h"
+#include "lib/systemd.h"
 
-#ifndef VTYSH_EXTRACT_PL
 #include "lib/log_vty_clippy.c"
-#endif
 
 #define ZLOG_MAXLVL(a, b) MAX(a, b)
 
@@ -51,15 +38,34 @@ static struct zlog_cfg_file zt_file_cmdline = {
 static struct zlog_cfg_file zt_file = {
        .prio_min = ZLOG_DISABLED,
 };
-static struct zlog_cfg_file zt_stdout = {
-       .prio_min = ZLOG_DISABLED,
-};
 static struct zlog_cfg_filterfile zt_filterfile = {
        .parent = {
                .prio_min = ZLOG_DISABLED,
        },
 };
 
+static struct zlog_cfg_file zt_stdout_file = {
+       .prio_min = ZLOG_DISABLED,
+};
+static struct zlog_cfg_5424 zt_stdout_journald = {
+       .prio_min = ZLOG_DISABLED,
+
+       .fmt = ZLOG_FMT_JOURNALD,
+       .dst = ZLOG_5424_DST_UNIX,
+       .filename = "/run/systemd/journal/socket",
+
+       /* this can't be changed through config since this target substitutes
+        * in for the "plain" stdout target
+        */
+       .facility = LOG_DAEMON,
+       .kw_version = false,
+       .kw_location = true,
+       .kw_uid = true,
+       .kw_ec = true,
+       .kw_args = true,
+};
+static bool stdout_journald_in_use;
+
 const char *zlog_progname;
 static const char *zlog_protoname;
 
@@ -138,6 +144,7 @@ void zlog_rotate(void)
 {
        zlog_file_rotate(&zt_file);
        zlog_file_rotate(&zt_filterfile.parent);
+       zlog_file_rotate(&zt_file_cmdline);
        hook_call(zlog_rotate);
 }
 
@@ -162,14 +169,18 @@ DEFUN_NOSH (show_logging,
            SHOW_STR
            "Show current logging configuration\n")
 {
+       int stdout_prio;
+
        log_show_syslog(vty);
 
+       stdout_prio = stdout_journald_in_use ? zt_stdout_journald.prio_min
+                                            : zt_stdout_file.prio_min;
+
        vty_out(vty, "Stdout logging: ");
-       if (zt_stdout.prio_min == ZLOG_DISABLED)
+       if (stdout_prio == ZLOG_DISABLED)
                vty_out(vty, "disabled");
        else
-               vty_out(vty, "level %s",
-                       zlog_priority[zt_stdout.prio_min]);
+               vty_out(vty, "level %s", zlog_priority[stdout_prio]);
        vty_out(vty, "\n");
 
        vty_out(vty, "File logging: ");
@@ -209,6 +220,21 @@ DEFUN_NOSH (show_logging,
        return CMD_SUCCESS;
 }
 
+static void log_stdout_apply_level(void)
+{
+       int maxlvl;
+
+       maxlvl = ZLOG_MAXLVL(log_config_stdout_lvl, log_cmdline_stdout_lvl);
+
+       if (stdout_journald_in_use) {
+               zt_stdout_journald.prio_min = maxlvl;
+               zlog_5424_apply_meta(&zt_stdout_journald);
+       } else {
+               zt_stdout_file.prio_min = maxlvl;
+               zlog_file_set_other(&zt_stdout_file);
+       }
+}
+
 DEFPY (config_log_stdout,
        config_log_stdout_cmd,
        "log stdout [<emergencies|alerts|critical|errors|warnings|notifications|informational|debugging>$levelarg]",
@@ -226,9 +252,7 @@ DEFPY (config_log_stdout,
                level = log_default_lvl;
 
        log_config_stdout_lvl = level;
-       zt_stdout.prio_min = ZLOG_MAXLVL(log_config_stdout_lvl,
-                                        log_cmdline_stdout_lvl);
-       zlog_file_set_other(&zt_stdout);
+       log_stdout_apply_level();
        return CMD_SUCCESS;
 }
 
@@ -241,9 +265,7 @@ DEFUN (no_config_log_stdout,
        LOG_LEVEL_DESC)
 {
        log_config_stdout_lvl = ZLOG_DISABLED;
-       zt_stdout.prio_min = ZLOG_MAXLVL(log_config_stdout_lvl,
-                                        log_cmdline_stdout_lvl);
-       zlog_file_set_other(&zt_stdout);
+       log_stdout_apply_level();
        return CMD_SUCCESS;
 }
 
@@ -377,9 +399,7 @@ void command_setup_early_logging(const char *dest, const char *level)
 
        if (strcmp(type, "stdout") == 0) {
                log_cmdline_stdout_lvl = nlevel;
-               zt_stdout.prio_min = ZLOG_MAXLVL(log_config_stdout_lvl,
-                                                log_cmdline_stdout_lvl);
-               zlog_file_set_other(&zt_stdout);
+               log_stdout_apply_level();
                return;
        }
        if (strcmp(type, "syslog") == 0) {
@@ -393,6 +413,22 @@ void command_setup_early_logging(const char *dest, const char *level)
                set_log_file(&zt_file_cmdline, NULL, sep, nlevel);
                return;
        }
+       if (strcmp(type, "monitor") == 0 && sep) {
+               struct zlog_live_cfg cfg = {};
+               unsigned long fd;
+               char *endp;
+
+               sep++;
+               fd = strtoul(sep, &endp, 10);
+               if (!*sep || *endp) {
+                       fprintf(stderr, "invalid monitor fd \"%s\"\n", sep);
+                       exit(1);
+               }
+
+               zlog_live_open_fd(&cfg, nlevel, fd);
+               zlog_live_disown(&cfg);
+               return;
+       }
 
        fprintf(stderr, "invalid log target \"%s\" (\"%s\")\n", type, dest);
        exit(1);
@@ -413,9 +449,7 @@ DEFUN (clear_log_cmdline,
                                             log_cmdline_syslog_lvl));
 
        log_cmdline_stdout_lvl = ZLOG_DISABLED;
-       zt_stdout.prio_min = ZLOG_MAXLVL(log_config_stdout_lvl,
-                                        log_cmdline_stdout_lvl);
-       zlog_file_set_other(&zt_stdout);
+       log_stdout_apply_level();
 
        return CMD_SUCCESS;
 }
@@ -523,8 +557,10 @@ DEFUN (config_log_record_priority,
 {
        zt_file.record_priority = true;
        zlog_file_set_other(&zt_file);
-       zt_stdout.record_priority = true;
-       zlog_file_set_other(&zt_stdout);
+       if (!stdout_journald_in_use) {
+               zt_stdout_file.record_priority = true;
+               zlog_file_set_other(&zt_stdout_file);
+       }
        zt_filterfile.parent.record_priority = true;
        zlog_file_set_other(&zt_filterfile.parent);
        return CMD_SUCCESS;
@@ -539,8 +575,10 @@ DEFUN (no_config_log_record_priority,
 {
        zt_file.record_priority = false;
        zlog_file_set_other(&zt_file);
-       zt_stdout.record_priority = false;
-       zlog_file_set_other(&zt_stdout);
+       if (!stdout_journald_in_use) {
+               zt_stdout_file.record_priority = false;
+               zlog_file_set_other(&zt_stdout_file);
+       }
        zt_filterfile.parent.record_priority = false;
        zlog_file_set_other(&zt_filterfile.parent);
        return CMD_SUCCESS;
@@ -556,8 +594,10 @@ DEFPY (config_log_timestamp_precision,
 {
        zt_file.ts_subsec = precision;
        zlog_file_set_other(&zt_file);
-       zt_stdout.ts_subsec = precision;
-       zlog_file_set_other(&zt_stdout);
+       if (!stdout_journald_in_use) {
+               zt_stdout_file.ts_subsec = precision;
+               zlog_file_set_other(&zt_stdout_file);
+       }
        zt_filterfile.parent.ts_subsec = precision;
        zlog_file_set_other(&zt_filterfile.parent);
        return CMD_SUCCESS;
@@ -574,8 +614,10 @@ DEFUN (no_config_log_timestamp_precision,
 {
        zt_file.ts_subsec = 0;
        zlog_file_set_other(&zt_file);
-       zt_stdout.ts_subsec = 0;
-       zlog_file_set_other(&zt_stdout);
+       if (!stdout_journald_in_use) {
+               zt_stdout_file.ts_subsec = 0;
+               zlog_file_set_other(&zt_stdout_file);
+       }
        zt_filterfile.parent.ts_subsec = 0;
        zlog_file_set_other(&zt_filterfile.parent);
        return CMD_SUCCESS;
@@ -704,8 +746,8 @@ DEFPY (log_immediate_mode,
        log_immediate_mode_cmd,
        "[no] log immediate-mode",
        NO_STR
-       "Logging control"
-       "Output immediately, without buffering")
+       "Logging control\n"
+       "Output immediately, without buffering\n")
 {
        zlog_set_immediate(!no);
        return CMD_SUCCESS;
@@ -821,7 +863,12 @@ static int log_vty_init(const char *progname, const char *protoname,
 
        zlog_filterfile_init(&zt_filterfile);
 
-       zlog_file_set_fd(&zt_stdout, STDOUT_FILENO);
+       if (sd_stdout_is_journal) {
+               stdout_journald_in_use = true;
+               zlog_5424_init(&zt_stdout_journald);
+               zlog_5424_apply_dst(&zt_stdout_journald);
+       } else
+               zlog_file_set_fd(&zt_stdout_file, STDOUT_FILENO);
        return 0;
 }
 
@@ -861,4 +908,6 @@ void log_cmd_init(void)
 
        install_element(ENABLE_NODE, &debug_uid_backtrace_cmd);
        install_element(CONFIG_NODE, &debug_uid_backtrace_cmd);
+
+       log_5424_cmd_init();
 }