/
githubmirror
/
dbus-broker
Обзор
Документация
Войти
/
githubmirror
/
dbus-broker
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
v21
src/launch/main.c
185 строк
6 KB
David Rheinsberg
dbus-broker: switch to c-stdaux
09 апр 2019, 17:01
09 апр 2019, 17:01
6a35f0e
Код
Авторство
О чём код?
/* * D-Bus Broker Launch Main Entry */ #include <c-stdaux.h> #include <fcntl.h> #include <getopt.h> #include <stdlib.h> #include <systemd/sd-daemon.h> #include "launch/launcher.h" #include "util/error.h" enum { _MAIN_SUCCESS, MAIN_EXIT, MAIN_FAILED, }; static bool main_arg_audit = false; static const char * main_arg_configfile = NULL; static bool main_arg_user_scope = false; static int main_fd_listen = -1; static void help(void) { printf("%s [GLOBALS...] ...\n\n" "Linux D-Bus Message Broker Launcher\n\n" " -h --help Show this help\n" " --version Show package version\n" " --audit Enable audit support\n" " --config-file PATH Specify path to configuration file\n" " --scope SCOPE Scope of message bus\n" , program_invocation_short_name); } static int parse_argv(int argc, char *argv[]) { enum { ARG_VERSION = 0x100, ARG_VERBOSE, ARG_AUDIT, ARG_CONFIG, ARG_SCOPE, }; static const struct option options[] = { { "help", no_argument, NULL, 'h' }, { "version", no_argument, NULL, ARG_VERSION }, { "verbose", no_argument, NULL, ARG_VERBOSE }, { "audit", no_argument, NULL, ARG_AUDIT }, { "config-file", required_argument, NULL, ARG_CONFIG, }, { "scope", required_argument, NULL, ARG_SCOPE }, {} }; int c; while ((c = getopt_long(argc, argv, "h", options, NULL)) >= 0) { switch (c) { case 'h': help(); return MAIN_EXIT; case ARG_VERSION: printf("dbus-broker-launch %d\n", PACKAGE_VERSION); return MAIN_EXIT; /* noop for backward compatibility */ case ARG_VERBOSE: break; case ARG_AUDIT: main_arg_audit = true; break; case ARG_CONFIG: main_arg_configfile = optarg; break; case ARG_SCOPE: if (!strcmp(optarg, "system")) { main_arg_user_scope = false; } else if (!strcmp(optarg, "user")) { main_arg_user_scope = true; } else { fprintf(stderr, "%s: invalid message bus scope -- '%s'\n", program_invocation_name, optarg); return MAIN_FAILED; } break; case '?': /* getopt_long() prints warning */ return MAIN_FAILED; default: return error_origin(-EINVAL); } } if (optind != argc) { fprintf(stderr, "%s: invalid arguments -- '%s'\n", program_invocation_name, argv[optind]); return MAIN_FAILED; } return 0; } static int inherit_fds(void) { int s, r, n; n = sd_listen_fds(true); if (n < 0) return error_origin(n); if (n == 0) { fprintf(stderr, "No listener socket inherited\n"); return MAIN_FAILED; } if (n > 1) { fprintf(stderr, "More than one listener socket passed\n"); return MAIN_FAILED; } s = SD_LISTEN_FDS_START; r = sd_is_socket(s, PF_UNIX, SOCK_STREAM, 1); if (r < 0) return error_origin(r); if (!r) { fprintf(stderr, "Non unix-domain-socket passed as listener\n"); return MAIN_FAILED; } r = fcntl(s, F_GETFL); if (r < 0) return error_origin(-errno); r = fcntl(s, F_SETFL, r | O_NONBLOCK); if (r < 0) return error_origin(-errno); main_fd_listen = s; return 0; } static int run(void) { _c_cleanup_(launcher_freep) Launcher *launcher = NULL; int r; r = launcher_new(&launcher, main_fd_listen, main_arg_audit, main_arg_configfile, main_arg_user_scope); if (r) return error_trace(r); r = launcher_run(launcher); if (r) r = error_trace(r); return r; } int main(int argc, char **argv) { sigset_t mask_new, mask_old; int r; r = parse_argv(argc, argv); if (r) goto exit; r = inherit_fds(); if (r) goto exit; sigemptyset(&mask_new); sigaddset(&mask_new, SIGCHLD); sigaddset(&mask_new, SIGTERM); sigaddset(&mask_new, SIGINT); sigaddset(&mask_new, SIGHUP); sigprocmask(SIG_BLOCK, &mask_new, &mask_old); r = run(); sigprocmask(SIG_SETMASK, &mask_old, NULL); exit: r = error_trace(r); if (r < 0) fprintf(stderr, "Exiting due to fatal error: %d\n", r); return (r == 0 || r == MAIN_EXIT) ? 0 : 1; }