diff options
Diffstat (limited to 'upstream/archlinux/man5/org.freedesktop.LogControl1.5')
-rw-r--r-- | upstream/archlinux/man5/org.freedesktop.LogControl1.5 | 391 |
1 files changed, 391 insertions, 0 deletions
diff --git a/upstream/archlinux/man5/org.freedesktop.LogControl1.5 b/upstream/archlinux/man5/org.freedesktop.LogControl1.5 new file mode 100644 index 00000000..70733a8e --- /dev/null +++ b/upstream/archlinux/man5/org.freedesktop.LogControl1.5 @@ -0,0 +1,391 @@ +'\" t +.TH "ORG\&.FREEDESKTOP\&.LOGCONTROL1" "5" "" "systemd 255" "org.freedesktop.LogControl1" +.\" ----------------------------------------------------------------- +.\" * Define some portability stuff +.\" ----------------------------------------------------------------- +.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +.\" http://bugs.debian.org/507673 +.\" http://lists.gnu.org/archive/html/groff/2009-02/msg00013.html +.\" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +.ie \n(.g .ds Aq \(aq +.el .ds Aq ' +.\" ----------------------------------------------------------------- +.\" * set default formatting +.\" ----------------------------------------------------------------- +.\" disable hyphenation +.nh +.\" disable justification (adjust text to left margin only) +.ad l +.\" ----------------------------------------------------------------- +.\" * MAIN CONTENT STARTS HERE * +.\" ----------------------------------------------------------------- +.SH "NAME" +org.freedesktop.LogControl1 \- D\-Bus interface to query and set logging configuration +.SH "INTRODUCTION" +.PP +org\&.freedesktop\&.LogControl1 +is a generic interface that is intended to be used by any daemon which allows the log level and target to be set over D\-Bus\&. It is implemented by various daemons that are part of the +\fBsystemd\fR(1) +suite\&. +.PP +It is assumed that those settings are global for the whole program, so a fixed object path is used\&. The interface should always be available under the path +/org/freedesktop/LogControl1\&. +.SH "DESCRIPTION" +.PP +The following interface is exposed: +.sp +.if n \{\ +.RS 4 +.\} +.nf +node /org/freedesktop/LogControl1 { + interface org\&.freedesktop\&.LogControl1 { + properties: + @org\&.freedesktop\&.DBus\&.Property\&.EmitsChangedSignal("false") + @org\&.freedesktop\&.systemd1\&.Privileged("true") + readwrite s LogLevel = \*(Aq\&.\&.\&.\*(Aq; + @org\&.freedesktop\&.DBus\&.Property\&.EmitsChangedSignal("false") + @org\&.freedesktop\&.systemd1\&.Privileged("true") + readwrite s LogTarget = \*(Aq\&.\&.\&.\*(Aq; + @org\&.freedesktop\&.DBus\&.Property\&.EmitsChangedSignal("false") + readonly s SyslogIdentifier = \*(Aq\&.\&.\&.\*(Aq; + }; + interface org\&.freedesktop\&.DBus\&.Peer { \&.\&.\&. }; + interface org\&.freedesktop\&.DBus\&.Introspectable { \&.\&.\&. }; + interface org\&.freedesktop\&.DBus\&.Properties { \&.\&.\&. }; +}; + +.fi +.if n \{\ +.RE +.\} + + + + +.SS "Properties" +.PP +\fILogLevel\fR +describes the +\fBsyslog\fR(3)\-style log\-level, and should be one of +"emerg", +"alert", +"crit", +"err", +"warning", +"notice", +"info", +"debug", in order of increasing verbosity\&. +.PP +\fILogTarget\fR +describes the log target (mechanism)\&. It should be one of +"console" +(log to the console or standard output), +"kmsg" +(log to the kernel ring buffer), +"journal" +(log to the journal natively, see +\fBsystemd-journald.service\fR(8)), +"syslog" +(log using the +\fBsyslog\fR(3) +call)\&. +.PP +Those two properties are writable, so they may be set by sufficiently privileged users\&. +.PP +\fISyslogIdentifier\fR +is a read\-only property that shows the "syslog identifier"\&. It is a short string that identifies the program that is the source of log messages that is passed to the +\fBsyslog\fR(3) +call\&. +.SH "TOOLS" +.PP +\fBjournalctl\fR +option +\fB\-p\fR/\fB\-\-priority=\fR +may be used to filter log messages by log level, option +\fB\-t\fR/\fB\-\-identifier=\fR +may be used to by the syslog identifier, and filters like +"_TRANSPORT=syslog", +"_TRANSPORT=journal", and +"_TRANSPORT=kernel" +may be used to filter messages by the mechanism through which they reached +\fBsystemd\-journald\fR\&. +.PP +\fBsystemctl log\-level\fR +and +\fBsystemctl log\-target\fR +verbs may be used to query and set the +\fILogLevel\fR +and +\fILogTarget\fR +properties of the service manager\&. +\fBsystemctl service\-log\-level\fR +and +\fBsystemctl service\-log\-target\fR +may similarly be used for individual services\&. (Services must have the +\fIBusName=\fR +property set and must implement the interface described here\&. See +\fBsystemd.service\fR(5) +for details about +\fIBusName=\fR\&.) +.SH "EXAMPLE" +.PP +\fBExample\ \&1.\ \&Create a simple listener on the bus that implements LogControl1\fR +.sp +.if n \{\ +.RS 4 +.\} +.nf +/* SPDX\-License\-Identifier: MIT\-0 */ + +/* Implements the LogControl1 interface as per specification: + * https://www\&.freedesktop\&.org/software/systemd/man/org\&.freedesktop\&.LogControl1\&.html + * + * Compile with \*(Aqcc logcontrol\-example\&.c $(pkg\-config \-\-libs \-\-cflags libsystemd)\*(Aq + * + * To get and set properties via busctl: + * + * $ busctl \-\-user get\-property org\&.freedesktop\&.Example \e + * /org/freedesktop/LogControl1 \e + * org\&.freedesktop\&.LogControl1 \e + * SyslogIdentifier + * s "example" + * $ busctl \-\-user get\-property org\&.freedesktop\&.Example \e + * /org/freedesktop/LogControl1 \e + * org\&.freedesktop\&.LogControl1 \e + * LogTarget + * s "journal" + * $ busctl \-\-user get\-property org\&.freedesktop\&.Example \e + * /org/freedesktop/LogControl1 \e + * org\&.freedesktop\&.LogControl1 \e + * LogLevel + * s "info" + * $ busctl \-\-user set\-property org\&.freedesktop\&.Example \e + * /org/freedesktop/LogControl1 \e + * org\&.freedesktop\&.LogControl1 \e + * LogLevel \e + * "s" debug + * $ busctl \-\-user get\-property org\&.freedesktop\&.Example \e + * /org/freedesktop/LogControl1 \e + * org\&.freedesktop\&.LogControl1 \e + * LogLevel + * s "debug" + */ + +#include <errno\&.h> +#include <stdlib\&.h> +#include <stdio\&.h> +#include <syslog\&.h> +#include <systemd/sd\-bus\&.h> +#include <systemd/sd\-journal\&.h> + +#define _cleanup_(f) __attribute__((cleanup(f))) + +#define check(log_level, x) ({ \e + int _r = (x); \e + errno = _r < 0 ? \-_r : 0; \e + sd_journal_print((log_level), #x ": %m"); \e + if (_r < 0) \e + return EXIT_FAILURE; \e + }) + +typedef enum LogTarget { + LOG_TARGET_JOURNAL, + LOG_TARGET_KMSG, + LOG_TARGET_SYSLOG, + LOG_TARGET_CONSOLE, + _LOG_TARGET_MAX, +} LogTarget; + +static const char* const log_target_table[_LOG_TARGET_MAX] = { + [LOG_TARGET_JOURNAL] = "journal", + [LOG_TARGET_KMSG] = "kmsg", + [LOG_TARGET_SYSLOG] = "syslog", + [LOG_TARGET_CONSOLE] = "console", +}; + +static const char* const log_level_table[LOG_DEBUG + 1] = { + [LOG_EMERG] = "emerg", + [LOG_ALERT] = "alert", + [LOG_CRIT] = "crit", + [LOG_ERR] = "err", + [LOG_WARNING] = "warning", + [LOG_NOTICE] = "notice", + [LOG_INFO] = "info", + [LOG_DEBUG] = "debug", +}; + +typedef struct object { + const char *syslog_identifier; + LogTarget log_target; + int log_level; +} object; + +static int property_get( + sd_bus *bus, + const char *path, + const char *interface, + const char *property, + sd_bus_message *reply, + void *userdata, + sd_bus_error *error) { + + object *o = userdata; + + if (strcmp(property, "LogLevel") == 0) + return sd_bus_message_append(reply, "s", log_level_table[o\->log_level]); + + if (strcmp(property, "LogTarget") == 0) + return sd_bus_message_append(reply, "s", log_target_table[o\->log_target]); + + if (strcmp(property, "SyslogIdentifier") == 0) + return sd_bus_message_append(reply, "s", o\->syslog_identifier); + + return sd_bus_error_setf(error, + SD_BUS_ERROR_UNKNOWN_PROPERTY, + "Unknown property \*(Aq%s\*(Aq", + property); +} + +static int property_set( + sd_bus *bus, + const char *path, + const char *interface, + const char *property, + sd_bus_message *message, + void *userdata, + sd_bus_error *error) { + + object *o = userdata; + const char *value; + int r; + + r = sd_bus_message_read(message, "s", &value); + if (r < 0) + return r; + + if (strcmp(property, "LogLevel") == 0) { + for (int i = 0; i < LOG_DEBUG + 1; i++) + if (strcmp(value, log_level_table[i]) == 0) { + o\->log_level = i; + setlogmask(LOG_UPTO(i)); + return 0; + } + + return sd_bus_error_setf(error, + SD_BUS_ERROR_INVALID_ARGS, + "Invalid value for LogLevel: \*(Aq%s\*(Aq", + value); + } + + if (strcmp(property, "LogTarget") == 0) { + for (LogTarget i = 0; i < _LOG_TARGET_MAX; i++) + if (strcmp(value, log_target_table[i]) == 0) { + o\->log_target = i; + return 0; + } + + return sd_bus_error_setf(error, + SD_BUS_ERROR_INVALID_ARGS, + "Invalid value for LogTarget: \*(Aq%s\*(Aq", + value); + } + + return sd_bus_error_setf(error, + SD_BUS_ERROR_UNKNOWN_PROPERTY, + "Unknown property \*(Aq%s\*(Aq", + property); +} + +/* https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_add_object\&.html + */ +static const sd_bus_vtable vtable[] = { + SD_BUS_VTABLE_START(0), + SD_BUS_WRITABLE_PROPERTY( + "LogLevel", "s", + property_get, property_set, + 0, + 0), + SD_BUS_WRITABLE_PROPERTY( + "LogTarget", "s", + property_get, property_set, + 0, + 0), + SD_BUS_PROPERTY( + "SyslogIdentifier", "s", + property_get, + 0, + SD_BUS_VTABLE_PROPERTY_CONST), + SD_BUS_VTABLE_END +}; + +int main(int argc, char **argv) { + /* The bus should be relinquished before the program terminates\&. The cleanup + * attribute allows us to do it nicely and cleanly whenever we exit the + * block\&. + */ + _cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL; + + object o = { + \&.log_level = LOG_INFO, + \&.log_target = LOG_TARGET_JOURNAL, + \&.syslog_identifier = "example", + }; + + /* https://man7\&.org/linux/man\-pages/man3/setlogmask\&.3\&.html + * Programs using syslog() instead of sd_journal can use this API to cut logs + * emission at the source\&. + */ + setlogmask(LOG_UPTO(o\&.log_level)); + + /* Acquire a connection to the bus, letting the library work out the details\&. + * https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_default\&.html + */ + check(o\&.log_level, sd_bus_default(&bus)); + + /* Publish an interface on the bus, specifying our well\-known object access + * path and public interface name\&. + * https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_add_object\&.html + * https://dbus\&.freedesktop\&.org/doc/dbus\-tutorial\&.html + */ + check(o\&.log_level, sd_bus_add_object_vtable(bus, NULL, + "/org/freedesktop/LogControl1", + "org\&.freedesktop\&.LogControl1", + vtable, + &o)); + + /* By default the service is assigned an ephemeral name\&. Also add a fixed + * one, so that clients know whom to call\&. + * https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_request_name\&.html + */ + check(o\&.log_level, sd_bus_request_name(bus, "org\&.freedesktop\&.Example", 0)); + + for (;;) { + /* https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_wait\&.html + */ + check(o\&.log_level, sd_bus_wait(bus, UINT64_MAX)); + /* https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_process\&.html + */ + check(o\&.log_level, sd_bus_process(bus, NULL)); + } + + /* https://www\&.freedesktop\&.org/software/systemd/man/sd_bus_release_name\&.html + */ + check(o\&.log_level, sd_bus_release_name(bus, "org\&.freedesktop\&.Example")); + + return 0; +} +.fi +.if n \{\ +.RE +.\} +.PP +This creates a simple server on the bus\&. It implements the LogControl1 interface by providing the required properties and allowing to set the writable ones\&. It logs at the configured log level using +\fBsd_journal_print\fR(3)\&. +.SH "SEE ALSO" +.PP +\fBsystemd\fR(1), +\fBjournalctl\fR(1), +\fBsystemctl\fR(1), +\fBsystemd.service\fR(5), +\fBsyslog\fR(3) |