1
0
mirror of https://github.com/systemd/systemd.git synced 2025-01-12 13:18:14 +03:00

Merge pull request #18580 from keszybz/signal-list

Add systemctl --signal=list
This commit is contained in:
Lennart Poettering 2021-02-15 14:37:03 +01:00 committed by GitHub
commit 458ab40f35
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
33 changed files with 272 additions and 170 deletions

View File

@ -334,13 +334,14 @@
<term><option>-s</option></term> <term><option>-s</option></term>
<term><option>--signal=</option></term> <term><option>--signal=</option></term>
<listitem><para>When used with <command>kill-session</command> <listitem><para>When used with <command>kill-session</command> or <command>kill-user</command>,
or <command>kill-user</command>, choose which signal to send choose which signal to send to selected processes. Must be one of the well known signal specifiers,
to selected processes. Must be one of the well known signal such as <constant>SIGTERM</constant>, <constant>SIGINT</constant> or <constant>SIGSTOP</constant>.
specifiers, such as <constant>SIGTERM</constant>, If omitted, defaults to <constant>SIGTERM</constant>.</para>
<constant>SIGINT</constant> or <constant>SIGSTOP</constant>.
If omitted, defaults to <para>The special value <literal>help</literal> will list the known values and the program will exit
<constant>SIGTERM</constant>.</para></listitem> immediately, and the special value <literal>list</literal> will list known values along with the
numerical signal numbers and the program will exit immediately.</para></listitem>
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>

View File

@ -699,17 +699,7 @@
<option>all</option>.</para></listitem> <option>all</option>.</para></listitem>
</varlistentry> </varlistentry>
<varlistentry> <xi:include href="standard-options.xml" xpointer="signal" />
<term><option>-s</option></term>
<term><option>--signal=</option></term>
<listitem><para>When used with <command>kill</command>, choose
which signal to send to selected processes. Must be one of the
well-known signal specifiers, such as
<constant>SIGTERM</constant>, <constant>SIGINT</constant> or
<constant>SIGSTOP</constant>. If omitted, defaults to
<constant>SIGTERM</constant>.</para></listitem>
</varlistentry>
<varlistentry> <varlistentry>
<term><option>--uid=</option></term> <term><option>--uid=</option></term>

View File

@ -61,4 +61,20 @@
(for a pretty version of the same, with indentation and line breaks) or <literal>off</literal> (to turn (for a pretty version of the same, with indentation and line breaks) or <literal>off</literal> (to turn
off JSON output, the default).</para></listitem> off JSON output, the default).</para></listitem>
</varlistentry> </varlistentry>
<varlistentry id='signal'>
<term><option>-s</option></term>
<term><option>--signal=</option></term>
<listitem>
<para>When used with <command>kill</command>, choose which signal to send to selected processes. Must
be one of the well-known signal specifiers such as <constant>SIGTERM</constant>,
<constant>SIGINT</constant> or <constant>SIGSTOP</constant>. If omitted, defaults to
<option>SIGTERM</option>.</para>
<para>The special value <literal>help</literal> will list the known values and the program will exit
immediately, and the special value <literal>list</literal> will list known values along with the
numerical signal numbers and the program will exit immediately.</para>
</listitem>
</varlistentry>
</variablelist> </variablelist>

View File

@ -2067,21 +2067,9 @@ Jan 12 10:46:45 example.com bluetoothd[8900]: gatt-time-server: Input/output err
is defined. If omitted, defaults to is defined. If omitted, defaults to
<option>all</option>.</para> <option>all</option>.</para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry> <xi:include href="standard-options.xml" xpointer="signal" />
<term><option>-s</option></term>
<term><option>--signal=</option></term>
<listitem>
<para>When used with <command>kill</command>, choose which
signal to send to selected processes. Must be one of the
well-known signal specifiers such as <constant>SIGTERM</constant>, <constant>SIGINT</constant> or
<constant>SIGSTOP</constant>. If omitted, defaults to
<option>SIGTERM</option>.</para>
</listitem>
</varlistentry>
<varlistentry> <varlistentry>
<term><option>--what=</option></term> <term><option>--what=</option></term>

View File

@ -752,38 +752,6 @@ int fsck_exists(const char *fstype) {
return executable_is_good(checker); return executable_is_good(checker);
} }
int parse_path_argument_and_warn(const char *path, bool suppress_root, char **arg) {
char *p;
int r;
/*
* This function is intended to be used in command line
* parsers, to handle paths that are passed in. It makes the
* path absolute, and reduces it to NULL if omitted or
* root (the latter optionally).
*
* NOTE THAT THIS WILL FREE THE PREVIOUS ARGUMENT POINTER ON
* SUCCESS! Hence, do not pass in uninitialized pointers.
*/
if (isempty(path)) {
*arg = mfree(*arg);
return 0;
}
r = path_make_absolute_cwd(path, &p);
if (r < 0)
return log_error_errno(r, "Failed to parse path \"%s\" and make it absolute: %m", path);
path_simplify(p, false);
if (suppress_root && empty_or_root(p))
p = mfree(p);
free_and_replace(*arg, p);
return 0;
}
char* dirname_malloc(const char *path) { char* dirname_malloc(const char *path) {
char *d, *dir, *dir2; char *d, *dir, *dir2;

View File

@ -144,8 +144,6 @@ int fsck_exists(const char *fstype);
_ret; \ _ret; \
}) })
int parse_path_argument_and_warn(const char *path, bool suppress_root, char **arg);
char* dirname_malloc(const char *path); char* dirname_malloc(const char *path);
const char *last_path_component(const char *path); const char *last_path_component(const char *path);
int path_extract_filename(const char *p, char **ret); int path_extract_filename(const char *p, char **ret);

View File

@ -198,7 +198,7 @@ static const char *const __signal_table[] = {
DEFINE_PRIVATE_STRING_TABLE_LOOKUP(__signal, int); DEFINE_PRIVATE_STRING_TABLE_LOOKUP(__signal, int);
const char *signal_to_string(int signo) { const char *signal_to_string(int signo) {
static thread_local char buf[STRLEN("RTMIN+") + DECIMAL_STR_MAX(int) + 1]; static thread_local char buf[STRLEN("RTMIN+") + DECIMAL_STR_MAX(int)];
const char *name; const char *name;
name = __signal_to_string(signo); name = __signal_to_string(signo);

View File

@ -103,9 +103,8 @@ ssize_t string_table_lookup(const char * const *table, size_t len, const char *k
#define DUMP_STRING_TABLE(name,type,max) \ #define DUMP_STRING_TABLE(name,type,max) \
do { \ do { \
type _k; \
flockfile(stdout); \ flockfile(stdout); \
for (_k = 0; _k < (max); _k++) { \ for (type _k = 0; _k < (max); _k++) { \
const char *_t; \ const char *_t; \
_t = name##_to_string(_k); \ _t = name##_to_string(_k); \
if (!_t) \ if (!_t) \

View File

@ -21,6 +21,7 @@
#include "log.h" #include "log.h"
#include "main-func.h" #include "main-func.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -2523,7 +2524,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -58,6 +58,7 @@
#include "mount-setup.h" #include "mount-setup.h"
#include "os-util.h" #include "os-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -358,7 +359,7 @@ static int parse_proc_cmdline_item(const char *key, const char *value, void *dat
return 0; return 0;
if (path_is_absolute(value)) if (path_is_absolute(value))
(void) parse_path_argument_and_warn(value, false, &arg_early_core_pattern); (void) parse_path_argument(value, false, &arg_early_core_pattern);
else else
log_warning("Specified core pattern '%s' is not an absolute path, ignoring.", value); log_warning("Specified core pattern '%s' is not an absolute path, ignoring.", value);
@ -498,7 +499,7 @@ static int parse_proc_cmdline_item(const char *key, const char *value, void *dat
if (proc_cmdline_value_missing(key, value)) if (proc_cmdline_value_missing(key, value))
return 0; return 0;
(void) parse_path_argument_and_warn(value, false, &arg_watchdog_device); (void) parse_path_argument(value, false, &arg_watchdog_device);
} else if (proc_cmdline_key_streq(key, "systemd.clock_usec")) { } else if (proc_cmdline_key_streq(key, "systemd.clock_usec")) {

View File

@ -25,6 +25,7 @@
#include "macro.h" #include "macro.h"
#include "main-func.h" #include "main-func.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -320,7 +321,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -16,6 +16,7 @@
#include "libfido2-util.h" #include "libfido2-util.h"
#include "main-func.h" #include "main-func.h"
#include "memory-util.h" #include "memory-util.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pkcs11-util.h" #include "pkcs11-util.h"
@ -323,7 +324,7 @@ static int parse_argv(int argc, char *argv[]) {
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"Too many arguments, refusing."); "Too many arguments, refusing.");
r = parse_path_argument_and_warn(argv[optind], false, &arg_node); r = parse_path_argument(argv[optind], false, &arg_node);
if (r < 0) if (r < 0)
return r; return r;

View File

@ -22,6 +22,7 @@
#include "mkdir.h" #include "mkdir.h"
#include "mount-util.h" #include "mount-util.h"
#include "namespace-util.h" #include "namespace-util.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -245,7 +246,7 @@ static int parse_argv(int argc, char *argv[]) {
} }
case ARG_VERITY_DATA: case ARG_VERITY_DATA:
r = parse_path_argument_and_warn(optarg, false, &arg_verity_settings.data_path); r = parse_path_argument(optarg, false, &arg_verity_settings.data_path);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -259,7 +260,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -24,6 +24,7 @@
#include "mkdir.h" #include "mkdir.h"
#include "mount-util.h" #include "mount-util.h"
#include "os-util.h" #include "os-util.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -1046,13 +1047,13 @@ static int parse_argv(int argc, char *argv[]) {
return version(); return version();
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, true, &arg_root); r = parse_path_argument(optarg, true, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
case ARG_IMAGE: case ARG_IMAGE:
r = parse_path_argument_and_warn(optarg, false, &arg_image); r = parse_path_argument(optarg, false, &arg_image);
if (r < 0) if (r < 0)
return r; return r;
break; break;

View File

@ -23,6 +23,7 @@
#include "main-func.h" #include "main-func.h"
#include "memory-util.h" #include "memory-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pkcs11-util.h" #include "pkcs11-util.h"
@ -2260,7 +2261,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
} }
r = parse_path_argument_and_warn(optarg, false, &hd); r = parse_path_argument(optarg, false, &hd);
if (r < 0) if (r < 0)
return r; return r;
@ -2481,7 +2482,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
} }
r = parse_path_argument_and_warn(optarg, false, &v); r = parse_path_argument(optarg, false, &v);
if (r < 0) if (r < 0)
return r; return r;
@ -3233,7 +3234,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -55,6 +55,7 @@
#include "mountpoint-util.h" #include "mountpoint-util.h"
#include "nulstr-util.h" #include "nulstr-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pcre2-dlopen.h" #include "pcre2-dlopen.h"
@ -719,13 +720,13 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ true, &arg_root); r = parse_path_argument(optarg, /* suppress_root= */ true, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
case ARG_IMAGE: case ARG_IMAGE:
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ false, &arg_image); r = parse_path_argument(optarg, /* suppress_root= */ false, &arg_image);
if (r < 0) if (r < 0)
return r; return r;
break; break;

View File

@ -22,6 +22,7 @@
#include "main-func.h" #include "main-func.h"
#include "memory-util.h" #include "memory-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "process-util.h" #include "process-util.h"
@ -1395,14 +1396,9 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case 's': case 's':
if (streq(optarg, "help")) { r = parse_signal_argument(optarg, &arg_signal);
DUMP_STRING_TABLE(signal, int, _NSIG); if (r <= 0)
return 0; return r;
}
arg_signal = signal_from_string(optarg);
if (arg_signal < 0)
return log_error_errno(arg_signal, "Failed to parse signal string %s.", optarg);
break; break;
case 'H': case 'H':

View File

@ -10,6 +10,7 @@
#include "log.h" #include "log.h"
#include "machine-id-setup.h" #include "machine-id-setup.h"
#include "main-func.h" #include "main-func.h"
#include "parse-argument.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "util.h" #include "util.h"
@ -76,7 +77,7 @@ static int parse_argv(int argc, char *argv[]) {
return version(); return version();
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, true, &arg_root); r = parse_path_argument(optarg, true, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;

View File

@ -39,6 +39,7 @@
#include "mkdir.h" #include "mkdir.h"
#include "nulstr-util.h" #include "nulstr-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -2715,15 +2716,9 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case 's': case 's':
if (streq(optarg, "help")) { r = parse_signal_argument(optarg, &arg_signal);
DUMP_STRING_TABLE(signal, int, _NSIG); if (r <= 0)
return 0; return r;
}
r = signal_from_string(optarg);
if (r < 0)
return log_error_errno(r, "Failed to parse signal string %s.", optarg);
arg_signal = r;
break; break;
case ARG_NO_ASK_PASSWORD: case ARG_NO_ASK_PASSWORD:

View File

@ -78,6 +78,7 @@
#include "nulstr-util.h" #include "nulstr-util.h"
#include "os-util.h" #include "os-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -791,7 +792,7 @@ static int parse_argv(int argc, char *argv[]) {
return version(); return version();
case 'D': case 'D':
r = parse_path_argument_and_warn(optarg, false, &arg_directory); r = parse_path_argument(optarg, false, &arg_directory);
if (r < 0) if (r < 0)
return r; return r;
@ -799,7 +800,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_TEMPLATE: case ARG_TEMPLATE:
r = parse_path_argument_and_warn(optarg, false, &arg_template); r = parse_path_argument(optarg, false, &arg_template);
if (r < 0) if (r < 0)
return r; return r;
@ -807,7 +808,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case 'i': case 'i':
r = parse_path_argument_and_warn(optarg, false, &arg_image); r = parse_path_argument(optarg, false, &arg_image);
if (r < 0) if (r < 0)
return r; return r;
@ -815,7 +816,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_OCI_BUNDLE: case ARG_OCI_BUNDLE:
r = parse_path_argument_and_warn(optarg, false, &arg_oci_bundle); r = parse_path_argument(optarg, false, &arg_oci_bundle);
if (r < 0) if (r < 0)
return r; return r;
@ -934,7 +935,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_NETWORK_NAMESPACE_PATH: case ARG_NETWORK_NAMESPACE_PATH:
r = parse_path_argument_and_warn(optarg, false, &arg_network_namespace_path); r = parse_path_argument(optarg, false, &arg_network_namespace_path);
if (r < 0) if (r < 0)
return r; return r;
@ -1386,7 +1387,7 @@ static int parse_argv(int argc, char *argv[]) {
} }
case ARG_VERITY_DATA: case ARG_VERITY_DATA:
r = parse_path_argument_and_warn(optarg, false, &arg_verity_settings.data_path); r = parse_path_argument(optarg, false, &arg_verity_settings.data_path);
if (r < 0) if (r < 0)
return r; return r;
break; break;

View File

@ -45,6 +45,7 @@
#include "mkfs-util.h" #include "mkfs-util.h"
#include "mount-util.h" #include "mount-util.h"
#include "parse-util.h" #include "parse-util.h"
#include "parse-argument.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "proc-cmdline.h" #include "proc-cmdline.h"
@ -3623,7 +3624,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, false, &arg_root); r = parse_path_argument(optarg, false, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -3653,7 +3654,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_DEFINITIONS: case ARG_DEFINITIONS:
r = parse_path_argument_and_warn(optarg, false, &arg_definitions); r = parse_path_argument(optarg, false, &arg_definitions);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -3687,7 +3688,7 @@ static int parse_argv(int argc, char *argv[]) {
} }
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -21,6 +21,7 @@
#include "fd-util.h" #include "fd-util.h"
#include "format-util.h" #include "format-util.h"
#include "main-func.h" #include "main-func.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
@ -470,7 +471,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_WORKING_DIRECTORY: case ARG_WORKING_DIRECTORY:
r = parse_path_argument_and_warn(optarg, true, &arg_working_directory); r = parse_path_argument(optarg, true, &arg_working_directory);
if (r < 0) if (r < 0)
return r; return r;

View File

@ -4459,27 +4459,6 @@ int json_variant_unhex(JsonVariant *v, void **ret, size_t *ret_size) {
return unhexmem(json_variant_string(v), (size_t) -1, ret, ret_size); return unhexmem(json_variant_string(v), (size_t) -1, ret, ret_size);
} }
int json_parse_cmdline_parameter_and_warn(const char *s, JsonFormatFlags *ret) {
assert(s);
assert(ret);
if (streq(s, "pretty"))
*ret = JSON_FORMAT_PRETTY|JSON_FORMAT_COLOR_AUTO;
else if (streq(s, "short"))
*ret = JSON_FORMAT_NEWLINE;
else if (streq(s, "off"))
*ret = JSON_FORMAT_OFF;
else if (streq(s, "help")) {
puts("pretty\n"
"short\n"
"off");
return 0; /* 0 means → we showed a brief help, exit now */
} else
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Unknown argument to --json= switch: %s", s);
return 1; /* 1 means → properly parsed */
}
static const char* const json_variant_type_table[_JSON_VARIANT_TYPE_MAX] = { static const char* const json_variant_type_table[_JSON_VARIANT_TYPE_MAX] = {
[JSON_VARIANT_STRING] = "string", [JSON_VARIANT_STRING] = "string",
[JSON_VARIANT_INTEGER] = "integer", [JSON_VARIANT_INTEGER] = "integer",

View File

@ -357,7 +357,5 @@ int json_log_internal(JsonVariant *variant, int level, int error, const char *fi
int json_variant_unbase64(JsonVariant *v, void **ret, size_t *ret_size); int json_variant_unbase64(JsonVariant *v, void **ret, size_t *ret_size);
int json_variant_unhex(JsonVariant *v, void **ret, size_t *ret_size); int json_variant_unhex(JsonVariant *v, void **ret, size_t *ret_size);
int json_parse_cmdline_parameter_and_warn(const char *s, JsonFormatFlags *ret);
const char *json_variant_type_to_string(JsonVariantType t); const char *json_variant_type_to_string(JsonVariantType t);
JsonVariantType json_variant_type_from_string(const char *s); JsonVariantType json_variant_type_from_string(const char *s);

View File

@ -202,6 +202,8 @@ shared_sources = files('''
output-mode.h output-mode.h
pager.c pager.c
pager.h pager.h
parse-argument.c
parse-argument.h
pe-header.h pe-header.h
pkcs11-util.c pkcs11-util.c
pkcs11-util.h pkcs11-util.h

102
src/shared/parse-argument.c Normal file
View File

@ -0,0 +1,102 @@
/* SPDX-License-Identifier: LGPL-2.1-or-later */
#include "format-table.h"
#include "parse-argument.h"
#include "path-util.h"
#include "signal-util.h"
#include "stdio-util.h"
#include "string-table.h"
#include "string-util.h"
/* All functions in this file emit warnigs. */
int parse_json_argument(const char *s, JsonFormatFlags *ret) {
assert(s);
assert(ret);
if (streq(s, "pretty"))
*ret = JSON_FORMAT_PRETTY|JSON_FORMAT_COLOR_AUTO;
else if (streq(s, "short"))
*ret = JSON_FORMAT_NEWLINE;
else if (streq(s, "off"))
*ret = JSON_FORMAT_OFF;
else if (streq(s, "help")) {
puts("pretty\n"
"short\n"
"off");
return 0; /* 0 means → we showed a brief help, exit now */
} else
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "Unknown argument to --json= switch: %s", s);
return 1; /* 1 means → properly parsed */
}
int parse_path_argument(const char *path, bool suppress_root, char **arg) {
char *p;
int r;
/*
* This function is intended to be used in command line parsers, to handle paths that are passed
* in. It makes the path absolute, and reduces it to NULL if omitted or root (the latter optionally).
*
* NOTE THAT THIS WILL FREE THE PREVIOUS ARGUMENT POINTER ON SUCCESS!
* Hence, do not pass in uninitialized pointers.
*/
if (isempty(path)) {
*arg = mfree(*arg);
return 0;
}
r = path_make_absolute_cwd(path, &p);
if (r < 0)
return log_error_errno(r, "Failed to parse path \"%s\" and make it absolute: %m", path);
path_simplify(p, false);
if (suppress_root && empty_or_root(p))
p = mfree(p);
return free_and_replace(*arg, p);
}
int parse_signal_argument(const char *s, int *ret) {
int r;
assert(s);
assert(ret);
if (streq(s, "help")) {
DUMP_STRING_TABLE(signal, int, _NSIG);
return 0;
}
if (streq(s, "list")) {
_cleanup_(table_unrefp) Table *table = NULL;
table = table_new("signal", "name");
if (!table)
return log_oom();
for (int i = 1; i < _NSIG; i++) {
r = table_add_many(
table,
TABLE_INT, i,
TABLE_SIGNAL, i);
if (r < 0)
return table_log_add_error(r);
}
r = table_print(table, NULL);
if (r < 0)
return table_log_print_error(r);
return 0;
}
r = signal_from_string(s);
if (r < 0)
return log_error_errno(r, "Failed to parse signal string \"%s\".", s);
*ret = r;
return 1; /* work to do */
}

View File

@ -0,0 +1,8 @@
/* SPDX-License-Identifier: LGPL-2.1-or-later */
#pragma once
#include "json.h"
int parse_json_argument(const char *s, JsonFormatFlags *ret);
int parse_path_argument(const char *path, bool suppress_root, char **arg);
int parse_signal_argument(const char *s, int *ret);

View File

@ -22,6 +22,7 @@
#include "mountpoint-util.h" #include "mountpoint-util.h"
#include "os-util.h" #include "os-util.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "process-util.h" #include "process-util.h"
@ -943,13 +944,13 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, false, &arg_root); r = parse_path_argument(optarg, false, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
case ARG_JSON: case ARG_JSON:
r = json_parse_cmdline_parameter_and_warn(optarg, &arg_json_format_flags); r = parse_json_argument(optarg, &arg_json_format_flags);
if (r <= 0) if (r <= 0)
return r; return r;

View File

@ -11,6 +11,7 @@
#include "main-func.h" #include "main-func.h"
#include "output-mode.h" #include "output-mode.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "rlimit-util.h" #include "rlimit-util.h"
@ -492,14 +493,12 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
case ARG_VERSION: case ARG_VERSION:
return version(); return version();
case 't': { case 't':
const char *p;
if (isempty(optarg)) if (isempty(optarg))
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--type= requires arguments."); "--type= requires arguments.");
for (p = optarg;;) { for (const char *p = optarg;;) {
_cleanup_free_ char *type = NULL; _cleanup_free_ char *type = NULL;
r = extract_first_word(&p, &type, ",", 0); r = extract_first_word(&p, &type, ",", 0);
@ -533,7 +532,6 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
} }
break; break;
}
case 'P': case 'P':
arg_value = true; arg_value = true;
@ -546,10 +544,8 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
arg_properties = new0(char*, 1); arg_properties = new0(char*, 1);
if (!arg_properties) if (!arg_properties)
return log_oom(); return log_oom();
} else { } else
const char *p; for (const char *p = optarg;;) {
for (p = optarg;;) {
_cleanup_free_ char *prop = NULL; _cleanup_free_ char *prop = NULL;
r = extract_first_word(&p, &prop, ",", 0); r = extract_first_word(&p, &prop, ",", 0);
@ -561,7 +557,6 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
if (strv_consume(&arg_properties, TAKE_PTR(prop)) < 0) if (strv_consume(&arg_properties, TAKE_PTR(prop)) < 0)
return log_oom(); return log_oom();
} }
}
/* If the user asked for a particular property, show it, even if it is empty. */ /* If the user asked for a particular property, show it, even if it is empty. */
arg_all = true; arg_all = true;
@ -643,7 +638,7 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, false, &arg_root); r = parse_path_argument(optarg, false, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -679,16 +674,9 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
break; break;
case 's': case 's':
if (streq(optarg, "help")) { r = parse_signal_argument(optarg, &arg_signal);
DUMP_STRING_TABLE(signal, int, _NSIG); if (r <= 0)
return 0; return r;
}
arg_signal = signal_from_string(optarg);
if (arg_signal < 0)
return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"Failed to parse signal string %s.",
optarg);
break; break;
case ARG_NO_ASK_PASSWORD: case ARG_NO_ASK_PASSWORD:
@ -778,14 +766,12 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
arg_boot_loader_entry = empty_to_null(optarg); arg_boot_loader_entry = empty_to_null(optarg);
break; break;
case ARG_STATE: { case ARG_STATE:
const char *p;
if (isempty(optarg)) if (isempty(optarg))
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), return log_error_errno(SYNTHETIC_ERRNO(EINVAL),
"--state= requires arguments."); "--state= requires arguments.");
for (p = optarg;;) { for (const char *p = optarg;;) {
_cleanup_free_ char *s = NULL; _cleanup_free_ char *s = NULL;
r = extract_first_word(&p, &s, ",", 0); r = extract_first_word(&p, &s, ",", 0);
@ -803,7 +789,6 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
return log_oom(); return log_oom();
} }
break; break;
}
case 'r': case 'r':
if (geteuid() != 0) if (geteuid() != 0)
@ -843,13 +828,11 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
arg_with_dependencies = true; arg_with_dependencies = true;
break; break;
case ARG_WHAT: { case ARG_WHAT:
const char *p;
if (isempty(optarg)) if (isempty(optarg))
return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "--what= requires arguments."); return log_error_errno(SYNTHETIC_ERRNO(EINVAL), "--what= requires arguments.");
for (p = optarg;;) { for (const char *p = optarg;;) {
_cleanup_free_ char *k = NULL; _cleanup_free_ char *k = NULL;
r = extract_first_word(&p, &k, ",", 0); r = extract_first_word(&p, &k, ",", 0);
@ -873,7 +856,6 @@ static int systemctl_parse_argv(int argc, char *argv[]) {
} }
break; break;
}
case ARG_REBOOT_ARG: case ARG_REBOOT_ARG:
arg_reboot_argument = optarg; arg_reboot_argument = optarg;

View File

@ -17,6 +17,7 @@
#include "mount-util.h" #include "mount-util.h"
#include "nscd-flush.h" #include "nscd-flush.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "path-util.h" #include "path-util.h"
#include "pretty-print.h" #include "pretty-print.h"
#include "selinux-util.h" #include "selinux-util.h"
@ -1813,7 +1814,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ false, &arg_root); r = parse_path_argument(optarg, /* suppress_root= */ false, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -1823,7 +1824,7 @@ static int parse_argv(int argc, char *argv[]) {
return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP), return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP),
"This systemd-sysusers version is compiled without support for --image=."); "This systemd-sysusers version is compiled without support for --image=.");
#else #else
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ false, &arg_image); r = parse_path_argument(optarg, /* suppress_root= */ false, &arg_image);
if (r < 0) if (r < 0)
return r; return r;
break; break;

View File

@ -222,6 +222,8 @@ tests += [
[['src/test/test-extract-word.c']], [['src/test/test-extract-word.c']],
[['src/test/test-parse-argument.c']],
[['src/test/test-parse-util.c'], [['src/test/test-parse-util.c'],
[], [],
[libseccomp]], [libseccomp]],

View File

@ -0,0 +1,63 @@
/* SPDX-License-Identifier: LGPL-2.1-or-later */
#include "parse-argument.h"
#include "stdio-util.h"
#include "tests.h"
static void test_parse_json_argument(void) {
log_info("/* %s */", __func__);
JsonFormatFlags flags = JSON_FORMAT_PRETTY;
assert_se(parse_json_argument("help", &flags) == 0);
assert_se(flags == JSON_FORMAT_PRETTY);
assert_se(parse_json_argument("off", &flags) == 1);
assert_se(flags == JSON_FORMAT_OFF);
}
static void test_parse_path_argument(void) {
log_info("/* %s */", __func__);
_cleanup_free_ char *path = NULL;
assert_se(parse_path_argument("help", false, &path) == 0);
assert_se(streq(basename(path), "help"));
assert_se(parse_path_argument("/", false, &path) == 0);
assert_se(streq(path, "/"));
assert_se(parse_path_argument("/", true, &path) == 0);
assert_se(path == NULL);
}
static void test_parse_signal_argument(void) {
log_info("/* %s */", __func__);
int signal = -1;
assert_se(parse_signal_argument("help", &signal) == 0);
assert_se(signal == -1);
assert_se(parse_signal_argument("list", &signal) == 0);
assert_se(signal == -1);
assert_se(parse_signal_argument("SIGABRT", &signal) == 1);
assert_se(signal == SIGABRT);
assert_se(parse_signal_argument("ABRT", &signal) == 1);
assert_se(signal == SIGABRT);
char buf[DECIMAL_STR_MAX(int)];
xsprintf(buf, "%d", SIGABRT);
assert_se(parse_signal_argument(buf, &signal) == 1);
assert_se(signal == SIGABRT);
}
int main(int argc, char *argv[]) {
test_setup_logging(LOG_INFO);
test_parse_json_argument();
test_parse_path_argument();
test_parse_signal_argument();
}

View File

@ -46,6 +46,7 @@
#include "mountpoint-util.h" #include "mountpoint-util.h"
#include "offline-passwd.h" #include "offline-passwd.h"
#include "pager.h" #include "pager.h"
#include "parse-argument.h"
#include "parse-util.h" #include "parse-util.h"
#include "path-lookup.h" #include "path-lookup.h"
#include "path-util.h" #include "path-util.h"
@ -3114,7 +3115,7 @@ static int parse_argv(int argc, char *argv[]) {
break; break;
case ARG_ROOT: case ARG_ROOT:
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ false, &arg_root); r = parse_path_argument(optarg, /* suppress_root= */ false, &arg_root);
if (r < 0) if (r < 0)
return r; return r;
break; break;
@ -3124,7 +3125,7 @@ static int parse_argv(int argc, char *argv[]) {
return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP), return log_error_errno(SYNTHETIC_ERRNO(EOPNOTSUPP),
"This systemd-tmpfiles version is compiled without support for --image=."); "This systemd-tmpfiles version is compiled without support for --image=.");
#else #else
r = parse_path_argument_and_warn(optarg, /* suppress_root= */ false, &arg_image); r = parse_path_argument(optarg, /* suppress_root= */ false, &arg_image);
if (r < 0) if (r < 0)
return r; return r;
#endif #endif