From 06d0dcc009f6d8b16d02f65fc20f7e1d76c77721 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Wed, 3 Apr 2024 02:21:19 +0900 Subject: [PATCH 1/5] man/example: fix build failure of hwdb-usb-device.c STRLEN() and xsprintf() is our internal macros. --- man/hwdb-usb-device.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/man/hwdb-usb-device.c b/man/hwdb-usb-device.c index 19a5db80229..3ac012070eb 100644 --- a/man/hwdb-usb-device.c +++ b/man/hwdb-usb-device.c @@ -5,13 +5,13 @@ #include int print_usb_properties(uint16_t vid, uint16_t pid) { - char match[STRLEN("usb:vp") + DECIMAL_STR_MAX(uint16_t) * 2]; + char match[128]; sd_hwdb *hwdb; const char *key, *value; int r; /* Match this USB vendor and product ID combination */ - xsprintf(match, "usb:v%04Xp%04X", vid, pid); + snprintf(match, sizeof match, "usb:v%04Xp%04X", vid, pid); r = sd_hwdb_new(&hwdb); if (r < 0) From e84f70e16da15cbff69a9fd4fd043abeea1634d0 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Wed, 3 Apr 2024 03:40:05 +0900 Subject: [PATCH 2/5] man/examples: use strerror() instead of %m --- man/journal-enumerate-fields.c | 3 +- man/journal-iterate-foreach.c | 7 +- man/journal-iterate-unique.c | 6 +- man/journal-iterate-wait.c | 15 ++-- man/journal-stream-fd.c | 7 +- man/logcontrol-example.c | 44 ++++++---- man/print-unit-path-call-method.c | 3 +- man/print-unit-path.c | 3 +- man/sd_bus_error-example.c | 2 +- man/sd_bus_service_reconnect.c | 140 ++++++++++++++++++++---------- man/vtable-example.c | 82 +++++++++++------ 11 files changed, 197 insertions(+), 115 deletions(-) diff --git a/man/journal-enumerate-fields.c b/man/journal-enumerate-fields.c index bb0931970a6..3d35b001786 100644 --- a/man/journal-enumerate-fields.c +++ b/man/journal-enumerate-fields.c @@ -11,8 +11,7 @@ int main(int argc, char *argv[]) { r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to open journal: %m\n"); + fprintf(stderr, "Failed to open journal: %s\n", strerror(-r)); return 1; } SD_JOURNAL_FOREACH_FIELD(j, field) diff --git a/man/journal-iterate-foreach.c b/man/journal-iterate-foreach.c index 381b50f9ceb..9c0fa0eaf13 100644 --- a/man/journal-iterate-foreach.c +++ b/man/journal-iterate-foreach.c @@ -7,10 +7,10 @@ int main(int argc, char *argv[]) { int r; sd_journal *j; + r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to open journal: %m\n"); + fprintf(stderr, "Failed to open journal: %s\n", strerror(-r)); return 1; } SD_JOURNAL_FOREACH(j) { @@ -19,8 +19,7 @@ int main(int argc, char *argv[]) { r = sd_journal_get_data(j, "MESSAGE", (const void **)&d, &l); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to read message field: %m\n"); + fprintf(stderr, "Failed to read message field: %s\n", strerror(-r)); continue; } diff --git a/man/journal-iterate-unique.c b/man/journal-iterate-unique.c index 5fe98b36b75..f44303d75cd 100644 --- a/man/journal-iterate-unique.c +++ b/man/journal-iterate-unique.c @@ -12,14 +12,12 @@ int main(int argc, char *argv[]) { r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to open journal: %m\n"); + fprintf(stderr, "Failed to open journal: %s\n", strerror(-r)); return 1; } r = sd_journal_query_unique(j, "_SYSTEMD_UNIT"); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to query journal: %m\n"); + fprintf(stderr, "Failed to query journal: %s\n", strerror(-r)); return 1; } SD_JOURNAL_FOREACH_UNIQUE(j, d, l) diff --git a/man/journal-iterate-wait.c b/man/journal-iterate-wait.c index ac4b60b8e9b..69d3cccb34a 100644 --- a/man/journal-iterate-wait.c +++ b/man/journal-iterate-wait.c @@ -7,39 +7,38 @@ int main(int argc, char *argv[]) { int r; sd_journal *j; + r = sd_journal_open(&j, SD_JOURNAL_LOCAL_ONLY); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to open journal: %m\n"); + fprintf(stderr, "Failed to open journal: %s\n", strerror(-r)); return 1; } + for (;;) { const void *d; size_t l; r = sd_journal_next(j); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to iterate to next entry: %m\n"); + fprintf(stderr, "Failed to iterate to next entry: %s\n", strerror(-r)); break; } if (r == 0) { /* Reached the end, let's wait for changes, and try again */ r = sd_journal_wait(j, (uint64_t) -1); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to wait for changes: %m\n"); + fprintf(stderr, "Failed to wait for changes: %s\n", strerror(-r)); break; } continue; } r = sd_journal_get_data(j, "MESSAGE", &d, &l); if (r < 0) { - errno = -r; - fprintf(stderr, "Failed to read message field: %m\n"); + fprintf(stderr, "Failed to read message field: %s\n", strerror(-r)); continue; } printf("%.*s\n", (int) l, (const char*) d); } + sd_journal_close(j); return 0; } diff --git a/man/journal-stream-fd.c b/man/journal-stream-fd.c index 8aad5ff8c66..c70d7986b29 100644 --- a/man/journal-stream-fd.c +++ b/man/journal-stream-fd.c @@ -10,15 +10,16 @@ int main(int argc, char *argv[]) { int fd; FILE *log; + fd = sd_journal_stream_fd("test", LOG_INFO, 1); if (fd < 0) { - errno = -fd; - fprintf(stderr, "Failed to create stream fd: %m\n"); + fprintf(stderr, "Failed to create stream fd: %s\n", strerror(-fd)); return 1; } + log = fdopen(fd, "w"); if (!log) { - fprintf(stderr, "Failed to create file object: %m\n"); + fprintf(stderr, "Failed to create file object: %s\n", strerror(errno)); close(fd); return 1; } diff --git a/man/logcontrol-example.c b/man/logcontrol-example.c index c199ec7a0f2..8c45369fc3b 100644 --- a/man/logcontrol-example.c +++ b/man/logcontrol-example.c @@ -43,13 +43,10 @@ #define _cleanup_(f) __attribute__((cleanup(f))) -#define check(log_level, x) ({ \ - int _r = (x); \ - errno = _r < 0 ? -_r : 0; \ - sd_journal_print((log_level), #x ": %m"); \ - if (_r < 0) \ - return EXIT_FAILURE; \ - }) +static int log_error(int log_level, int error, const char *str) { + sd_journal_print(log_level, "%s failed: %s", str, strerror(-error)); + return error; +} typedef enum LogTarget { LOG_TARGET_JOURNAL, @@ -193,6 +190,7 @@ int main(int argc, char **argv) { .log_target = LOG_TARGET_JOURNAL, .syslog_identifier = "example", }; + int r; /* https://man7.org/linux/man-pages/man3/setlogmask.3.html * Programs using syslog() instead of sd_journal can use this API to cut logs @@ -203,37 +201,49 @@ int main(int argc, char **argv) { /* 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)); + r = sd_bus_default(&bus); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_default()"); /* 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)); + r = sd_bus_add_object_vtable(bus, NULL, + "/org/freedesktop/LogControl1", + "org.freedesktop.LogControl1", + vtable, + &o); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_add_object_vtable()"); /* 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)); + r = sd_bus_request_name(bus, "org.freedesktop.Example", 0); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_request_name()"); for (;;) { /* https://www.freedesktop.org/software/systemd/man/sd_bus_wait.html */ - check(o.log_level, sd_bus_wait(bus, UINT64_MAX)); + r = sd_bus_wait(bus, UINT64_MAX); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_wait()"); /* https://www.freedesktop.org/software/systemd/man/sd_bus_process.html */ - check(o.log_level, sd_bus_process(bus, NULL)); + r = sd_bus_process(bus, NULL); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_process()"); } /* https://www.freedesktop.org/software/systemd/man/sd_bus_release_name.html */ - check(o.log_level, sd_bus_release_name(bus, "org.freedesktop.Example")); + r = sd_bus_release_name(bus, "org.freedesktop.Example"); + if (r < 0) + return log_error(o.log_level, r, "sd_bus_release_name()"); return 0; } diff --git a/man/print-unit-path-call-method.c b/man/print-unit-path-call-method.c index f73dd073f98..15e8d3f51b2 100644 --- a/man/print-unit-path-call-method.c +++ b/man/print-unit-path-call-method.c @@ -21,8 +21,7 @@ #define MEMBER "GetUnitByPID" static int log_error(int error, const char *message) { - errno = -error; - fprintf(stderr, "%s: %m\n", message); + fprintf(stderr, "%s: %s\n", message, strerror(-error)); return error; } diff --git a/man/print-unit-path.c b/man/print-unit-path.c index 0b89318736a..737244feb0d 100644 --- a/man/print-unit-path.c +++ b/man/print-unit-path.c @@ -21,8 +21,7 @@ #define MEMBER "GetUnitByPID" static int log_error(int error, const char *message) { - errno = -error; - fprintf(stderr, "%s: %m\n", message); + fprintf(stderr, "%s: %s\n", message, strerror(-error)); return error; } diff --git a/man/sd_bus_error-example.c b/man/sd_bus_error-example.c index 9b162eb6cc3..0f70a629f31 100644 --- a/man/sd_bus_error-example.c +++ b/man/sd_bus_error-example.c @@ -14,5 +14,5 @@ int writer_with_negative_errno_return(int fd, sd_bus_error *error) { /* On error, initialize the error structure, and also propagate the errno * value that write(2) set for us. */ - return sd_bus_error_set_errnof(error, errno, "Failed to write to fd %i: %m", fd); + return sd_bus_error_set_errnof(error, errno, "Failed to write to fd %i: %s", fd, strerror(errno)); } diff --git a/man/sd_bus_service_reconnect.c b/man/sd_bus_service_reconnect.c index c0818689f29..fc7c3b1a724 100644 --- a/man/sd_bus_service_reconnect.c +++ b/man/sd_bus_service_reconnect.c @@ -42,13 +42,10 @@ #define _cleanup_(f) __attribute__((cleanup(f))) -#define check(x) ({ \ - int _r = (x); \ - errno = _r < 0 ? -_r : 0; \ - printf(#x ": %m\n"); \ - if (_r < 0) \ - return EXIT_FAILURE; \ - }) +static int log_error(int r, const char *str) { + fprintf(stderr, "%s failed: %s\n", str, strerror(-r)); + return r; +} typedef struct object { const char *example; @@ -90,13 +87,24 @@ static const sd_bus_vtable vtable[] = { static int setup(object *o); static int on_disconnect(sd_bus_message *message, void *userdata, sd_bus_error *ret_error) { - check(setup((object *)userdata)); - return 0; + int r; + + r = setup((object *)userdata); + if (r < 0) { + object *o = userdata; + r = sd_event_exit(*o->event, r); + if (r < 0) + return log_error(r, "sd_event_exit()"); + } + + return 1; } /* Ensure the event loop exits with a clear error if acquiring the well-known * service name fails */ static int request_name_callback(sd_bus_message *m, void *userdata, sd_bus_error *ret_error) { + int r; + if (!sd_bus_message_is_method_error(m, NULL)) return 1; @@ -105,21 +113,27 @@ static int request_name_callback(sd_bus_message *m, void *userdata, sd_bus_error if (sd_bus_error_has_names(error, SD_BUS_ERROR_TIMEOUT, SD_BUS_ERROR_NO_REPLY)) return 1; /* The bus is not available, try again later */ - printf("Failed to request name: %s\n", error->message); + fprintf(stderr, "Failed to request name: %s\n", error->message); object *o = userdata; - check(sd_event_exit(*o->event, -sd_bus_error_get_errno(error))); + r = sd_event_exit(*o->event, -sd_bus_error_get_errno(error)); + if (r < 0) + return log_error(r, "sd_event_exit()"); return 1; } static int setup(object *o) { + int r; + /* If we are reconnecting, then the bus object needs to be closed, detached * from the event loop and recreated. * https://www.freedesktop.org/software/systemd/man/sd_bus_detach_event.html * https://www.freedesktop.org/software/systemd/man/sd_bus_close_unref.html */ if (*o->bus) { - check(sd_bus_detach_event(*o->bus)); + r = sd_bus_detach_event(*o->bus); + if (r < 0) + return log_error(r, "sd_bus_detach_event()"); *o->bus = sd_bus_close_unref(*o->bus); } @@ -135,55 +149,75 @@ static int setup(object *o) { * https://www.freedesktop.org/software/systemd/man/sd_bus_set_connected_signal.html * https://www.freedesktop.org/software/systemd/man/sd_bus_start.html */ - check(sd_bus_new(o->bus)); - check(sd_bus_set_address(*o->bus, "unix:path=/run/dbus/system_bus_socket")); - check(sd_bus_set_bus_client(*o->bus, 1)); - check(sd_bus_negotiate_creds(*o->bus, 1, SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_EFFECTIVE_CAPS)); - check(sd_bus_set_watch_bind(*o->bus, 1)); - check(sd_bus_start(*o->bus)); + r = sd_bus_new(o->bus); + if (r < 0) + return log_error(r, "sd_bus_new()"); + r = sd_bus_set_address(*o->bus, "unix:path=/run/dbus/system_bus_socket"); + if (r < 0) + return log_error(r, "sd_bus_set_address()"); + r = sd_bus_set_bus_client(*o->bus, 1); + if (r < 0) + return log_error(r, "sd_bus_set_bus_client()"); + r = sd_bus_negotiate_creds(*o->bus, 1, SD_BUS_CREDS_UID|SD_BUS_CREDS_EUID|SD_BUS_CREDS_EFFECTIVE_CAPS); + if (r < 0) + return log_error(r, "sd_bus_negotiate_creds()"); + r = sd_bus_set_watch_bind(*o->bus, 1); + if (r < 0) + return log_error(r, "sd_bus_set_watch_bind()"); + r = sd_bus_start(*o->bus); + if (r < 0) + return log_error(r, "sd_bus_start()"); /* 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(sd_bus_add_object_vtable(*o->bus, - NULL, - "/org/freedesktop/ReconnectExample", - "org.freedesktop.ReconnectExample", - vtable, - o)); + r = sd_bus_add_object_vtable(*o->bus, + NULL, + "/org/freedesktop/ReconnectExample", + "org.freedesktop.ReconnectExample", + vtable, + o); + if (r < 0) + return log_error(r, "sd_bus_add_object_vtable()"); /* By default the service is only assigned an ephemeral name. Also add a * well-known one, so that clients know whom to call. This needs to be * asynchronous, as D-Bus might not be yet available. The callback will check * whether the error is expected or not, in case it fails. * https://www.freedesktop.org/software/systemd/man/sd_bus_request_name.html */ - check(sd_bus_request_name_async(*o->bus, - NULL, - "org.freedesktop.ReconnectExample", - 0, - request_name_callback, - o)); + r = sd_bus_request_name_async(*o->bus, + NULL, + "org.freedesktop.ReconnectExample", + 0, + request_name_callback, + o); + if (r < 0) + return log_error(r, "sd_bus_request_name_async()"); /* When D-Bus is disconnected this callback will be invoked, which will set up * the connection again. This needs to be asynchronous, as D-Bus might not yet * be available. * https://www.freedesktop.org/software/systemd/man/sd_bus_match_signal_async.html */ - check(sd_bus_match_signal_async(*o->bus, - NULL, - "org.freedesktop.DBus.Local", - NULL, - "org.freedesktop.DBus.Local", - "Disconnected", - on_disconnect, - NULL, - o)); + r = sd_bus_match_signal_async(*o->bus, + NULL, + "org.freedesktop.DBus.Local", + NULL, + "org.freedesktop.DBus.Local", + "Disconnected", + on_disconnect, + NULL, + o); + if (r < 0) + return log_error(r, "sd_bus_match_signal_async()"); /* Attach the bus object to the event loop so that calls and signals are * processed. * https://www.freedesktop.org/software/systemd/man/sd_bus_attach_event.html */ - check(sd_bus_attach_event(*o->bus, *o->event, 0)); + r = sd_bus_attach_event(*o->bus, *o->event, 0); + if (r < 0) + return log_error(r, "sd_bus_attach_event()"); return 0; } @@ -199,28 +233,42 @@ int main(int argc, char **argv) { .bus = &bus, .event = &event, }; + int r; /* Create an event loop data structure, with default parameters. * https://www.freedesktop.org/software/systemd/man/sd_event_default.html */ - check(sd_event_default(&event)); + r = sd_event_default(&event); + if (r < 0) + return log_error(r, "sd_event_default()"); /* By default the event loop will terminate when all sources have disappeared, * so we have to keep it 'occupied'. Register signal handling to do so. * https://www.freedesktop.org/software/systemd/man/sd_event_add_signal.html */ - check(sd_event_add_signal(event, NULL, SIGINT|SD_EVENT_SIGNAL_PROCMASK, NULL, NULL)); - check(sd_event_add_signal(event, NULL, SIGTERM|SD_EVENT_SIGNAL_PROCMASK, NULL, NULL)); + r = sd_event_add_signal(event, NULL, SIGINT|SD_EVENT_SIGNAL_PROCMASK, NULL, NULL); + if (r < 0) + return log_error(r, "sd_event_add_signal(SIGINT)"); - check(setup(&o)); + r = sd_event_add_signal(event, NULL, SIGTERM|SD_EVENT_SIGNAL_PROCMASK, NULL, NULL); + if (r < 0) + return log_error(r, "sd_event_add_signal(SIGTERM)"); + + r = setup(&o); + if (r < 0) + return EXIT_FAILURE; /* Enter the main loop, it will exit only on sigint/sigterm. * https://www.freedesktop.org/software/systemd/man/sd_event_loop.html */ - check(sd_event_loop(event)); + r = sd_event_loop(event); + if (r < 0) + return log_error(r, "sd_event_loop()"); /* https://www.freedesktop.org/software/systemd/man/sd_bus_release_name.html */ - check(sd_bus_release_name(bus, "org.freedesktop.ReconnectExample")); + r = sd_bus_release_name(bus, "org.freedesktop.ReconnectExample"); + if (r < 0) + return log_error(r, "sd_bus_release_name()"); return 0; } diff --git a/man/vtable-example.c b/man/vtable-example.c index e3346a80211..417ee0ccf13 100644 --- a/man/vtable-example.c +++ b/man/vtable-example.c @@ -9,20 +9,14 @@ #define _cleanup_(f) __attribute__((cleanup(f))) -#define check(x) ({ \ - int r = (x); \ - errno = r < 0 ? -r : 0; \ - printf(#x ": %m\n"); \ - if (r < 0) \ - return EXIT_FAILURE; \ - }) - typedef struct object { char *name; uint32_t number; } object; static int method(sd_bus_message *m, void *userdata, sd_bus_error *error) { + int r; + printf("Got called with userdata=%p\n", userdata); if (sd_bus_message_is_method_call(m, @@ -31,8 +25,17 @@ static int method(sd_bus_message *m, void *userdata, sd_bus_error *error) { return 1; const char *string; - check(sd_bus_message_read(m, "s", &string)); - check(sd_bus_reply_method_return(m, "s", string)); + r = sd_bus_message_read(m, "s", &string); + if (r < 0) { + fprintf(stderr, "sd_bus_message_read() failed: %s\n", strerror(-r)); + return 0; + } + + r = sd_bus_reply_method_return(m, "s", string); + if (r < 0) { + fprintf(stderr, "sd_bus_reply_method_return() failed: %s\n", strerror(-r)); + return 0; + } return 1; } @@ -84,28 +87,55 @@ static const sd_bus_vtable vtable[] = { int main(int argc, char **argv) { _cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL; + int r; sd_bus_default(&bus); object object = { .number = 666 }; - check((object.name = strdup("name")) != NULL); - - check(sd_bus_add_object_vtable(bus, NULL, - "/org/freedesktop/systemd/VtableExample", - "org.freedesktop.systemd.VtableExample", - vtable, - &object)); - - check(sd_bus_request_name(bus, - "org.freedesktop.systemd.VtableExample", - 0)); - - for (;;) { - check(sd_bus_wait(bus, UINT64_MAX)); - check(sd_bus_process(bus, NULL)); + object.name = strdup("name"); + if (!object.name) { + fprintf(stderr, "OOM\n"); + return EXIT_FAILURE; + } + + r = sd_bus_add_object_vtable(bus, NULL, + "/org/freedesktop/systemd/VtableExample", + "org.freedesktop.systemd.VtableExample", + vtable, + &object); + if (r < 0) { + fprintf(stderr, "sd_bus_add_object_vtable() failed: %s\n", strerror(-r)); + return EXIT_FAILURE; + } + + r = sd_bus_request_name(bus, + "org.freedesktop.systemd.VtableExample", + 0); + if (r < 0) { + fprintf(stderr, "sd_bus_request_name() failed: %s\n", strerror(-r)); + return EXIT_FAILURE; + } + + for (;;) { + r = sd_bus_wait(bus, UINT64_MAX); + if (r < 0) { + fprintf(stderr, "sd_bus_wait() failed: %s\n", strerror(-r)); + return EXIT_FAILURE; + } + + r = sd_bus_process(bus, NULL); + if (r < 0) { + fprintf(stderr, "sd_bus_process() failed: %s\n", strerror(-r)); + return EXIT_FAILURE; + } + } + + r = sd_bus_release_name(bus, "org.freedesktop.systemd.VtableExample"); + if (r < 0) { + fprintf(stderr, "sd_bus_release_name() failed: %s\n", strerror(-r)); + return EXIT_FAILURE; } - check(sd_bus_release_name(bus, "org.freedesktop.systemd.VtableExample")); free(object.name); return 0; From 2548ce6a30a1183a7bbbd699aafdf81249a5fe4e Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Wed, 3 Apr 2024 04:22:36 +0900 Subject: [PATCH 3/5] man/examples: fix sd- header path --- man/event-quick-child.c | 2 +- man/hwdb-usb-device.c | 2 +- man/path-documents.c | 2 +- man/sd_bus_error-example.c | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/man/event-quick-child.c b/man/event-quick-child.c index 8195efbaa5e..b95ee1bef63 100644 --- a/man/event-quick-child.c +++ b/man/event-quick-child.c @@ -3,7 +3,7 @@ #include #include #include -#include +#include int main(int argc, char **argv) { pid_t pid = fork(); diff --git a/man/hwdb-usb-device.c b/man/hwdb-usb-device.c index 3ac012070eb..facd8c43b29 100644 --- a/man/hwdb-usb-device.c +++ b/man/hwdb-usb-device.c @@ -2,7 +2,7 @@ #include #include -#include +#include int print_usb_properties(uint16_t vid, uint16_t pid) { char match[128]; diff --git a/man/path-documents.c b/man/path-documents.c index a357dd659a8..994f20bcf4e 100644 --- a/man/path-documents.c +++ b/man/path-documents.c @@ -2,7 +2,7 @@ #include #include -#include +#include int main(void) { int r; diff --git a/man/sd_bus_error-example.c b/man/sd_bus_error-example.c index 0f70a629f31..3836f5e642a 100644 --- a/man/sd_bus_error-example.c +++ b/man/sd_bus_error-example.c @@ -3,7 +3,7 @@ #include #include #include -#include +#include int writer_with_negative_errno_return(int fd, sd_bus_error *error) { const char *message = "Hello, World!\n"; From e10409ad55dccda89a1f1ca23c6dabca20488d51 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Wed, 3 Apr 2024 11:52:23 +0900 Subject: [PATCH 4/5] sd-bus-vtable: add dummy macro to support compile without GNU extension MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If SD_BUS_METHOD_WITH_ARGS() is set with SD_BUS_NO_ARGS and/or SD_BUS_NO_RESULT, then it introduces _SD_VARARGS_FOREACH_EVEN(_SD_ECHO, NULL) -> _SD_VARARGS_FOREACH_SEQ(_01, …, _50, NULL) Hence, the variadic argument `...` in _SD_VARARGS_FOREACH_SEQ() has no argument, but it is not allowed if built without GNU extension, e.g. -std=c11. Let's introduce one more unused dummy argument to support such situation. --- src/systemd/sd-bus-vtable.h | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/systemd/sd-bus-vtable.h b/src/systemd/sd-bus-vtable.h index 5e80ea895d4..d06c5c30155 100644 --- a/src/systemd/sd-bus-vtable.h +++ b/src/systemd/sd-bus-vtable.h @@ -208,6 +208,7 @@ struct sd_bus_vtable { _41, _42, _43, _44, _45, _46, _47, _48, _49, _50, \ NAME, ...) NAME +#define _SD_VARARGS_FOREACH_EVEN_00(FN) #define _SD_VARARGS_FOREACH_EVEN_01(FN, X) FN(X) #define _SD_VARARGS_FOREACH_EVEN_02(FN, X, Y) FN(X) #define _SD_VARARGS_FOREACH_EVEN_04(FN, X, Y, ...) FN(X) _SD_VARARGS_FOREACH_EVEN_02(FN, __VA_ARGS__) @@ -261,9 +262,11 @@ struct sd_bus_vtable { _SD_VARARGS_FOREACH_EVEN_08, _SD_VARARGS_FOREACH_EVEN_07, \ _SD_VARARGS_FOREACH_EVEN_06, _SD_VARARGS_FOREACH_EVEN_05, \ _SD_VARARGS_FOREACH_EVEN_04, _SD_VARARGS_FOREACH_EVEN_03, \ - _SD_VARARGS_FOREACH_EVEN_02, _SD_VARARGS_FOREACH_EVEN_01) \ + _SD_VARARGS_FOREACH_EVEN_02, _SD_VARARGS_FOREACH_EVEN_01, \ + _SD_VARARGS_FOREACH_EVEN_00) \ (FN, __VA_ARGS__) +#define _SD_VARARGS_FOREACH_ODD_00(FN) #define _SD_VARARGS_FOREACH_ODD_01(FN, X) #define _SD_VARARGS_FOREACH_ODD_02(FN, X, Y) FN(Y) #define _SD_VARARGS_FOREACH_ODD_04(FN, X, Y, ...) FN(Y) _SD_VARARGS_FOREACH_ODD_02(FN, __VA_ARGS__) @@ -317,7 +320,8 @@ struct sd_bus_vtable { _SD_VARARGS_FOREACH_ODD_08, _SD_VARARGS_FOREACH_ODD_07, \ _SD_VARARGS_FOREACH_ODD_06, _SD_VARARGS_FOREACH_ODD_05, \ _SD_VARARGS_FOREACH_ODD_04, _SD_VARARGS_FOREACH_ODD_03, \ - _SD_VARARGS_FOREACH_ODD_02, _SD_VARARGS_FOREACH_ODD_01) \ + _SD_VARARGS_FOREACH_ODD_02, _SD_VARARGS_FOREACH_ODD_01, \ + _SD_VARARGS_FOREACH_ODD_00) \ (FN, __VA_ARGS__) #define SD_BUS_ARGS(...) __VA_ARGS__ From e98d4c3599691a4e7a934092ca62793b6a7706c8 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Wed, 3 Apr 2024 03:42:55 +0900 Subject: [PATCH 5/5] man/meson: add simple build test for example code --- man/meson.build | 84 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 84 insertions(+) diff --git a/man/meson.build b/man/meson.build index 488ff702209..22ac236b273 100644 --- a/man/meson.build +++ b/man/meson.build @@ -248,3 +248,87 @@ update_man_rules = custom_target( '@0@/man/*.xml'.format(project_source_root), '@0@/rules/meson.build'.format(meson.current_source_dir())], depends : man_page_depends) + +############################################################ + +simple_examples = files( + 'event-quick-child.c', + 'hwdb-usb-device.c', + 'id128-app-specific.c', + 'inotify-watch-tmp.c', + 'journal-enumerate-fields.c', + 'journal-iterate-foreach.c', + 'journal-iterate-poll.c', + 'journal-iterate-unique.c', + 'journal-iterate-wait.c', + 'journal-stream-fd.c', + 'logcontrol-example.c', + 'notify-selfcontained-example.c', + 'path-documents.c', + 'print-unit-path-call-method.c', + 'print-unit-path.c', + 'sd-bus-container-append.c', + 'sd-bus-container-read.c', + 'sd_bus_error-example.c', + 'sd_bus_service_reconnect.c', + 'send-unit-files-changed.c', + 'vtable-example.c', +) + +examples = [] +foreach example : simple_examples + examples += [ { 'file' : example } ] +endforeach + +if conf.get('HAVE_GLIB') == 1 + examples += [ + { + 'file' : files('glib-event-glue.c'), + 'opts' : [ + '-I', libglib.get_variable('includedir') / 'glib-2.0', + '-I', libglib.get_variable('libdir') / 'glib-2.0/include', + ], + }, + ] +endif + +default_args = [ + cc.cmd_array(), + '-c', + '-x', 'c', + '-pedantic', + '-Wall', + '-Werror', + '-Wextra', + '-Wno-unused-parameter', + '-o', '/dev/null', + '-I', meson.current_source_dir() / '../src', +] + +std_args_in = [ + [ '-std=c99', '-D_GNU_SOURCE', ], + [ '-std=c11', '-D_GNU_SOURCE', ], + [ '-std=c17', '-D_GNU_SOURCE', ], + [ '-std=c23', '-D_GNU_SOURCE', ], + [ '-std=gnu99', ], + [ '-std=gnu11', ], + [ '-std=gnu17', ], + [ '-std=gnu23', ], +] + +std_args = [] +foreach std : std_args_in + if cc.has_argument(std[0]) + std_args += [std] + endif +endforeach + +foreach item : examples + foreach std : std_args + file = item.get('file') + test('cc-' + fs.stem(file) + '-' + std[0].split('=')[1], + env, + suite : 'example', + args : default_args + std + item.get('opts', []) + [file]) + endforeach +endforeach