ask-password-tool: add --user/--system flag to systemd-ask-password tool

This allows selecting which agents to ask about this: system-level
agents, or per-user agents.

Fixes: #1232 #2217
This commit is contained in:
Lennart Poettering
2024-09-13 13:45:08 +02:00
parent 4dd2748b65
commit 9c1fa3c235
2 changed files with 44 additions and 22 deletions

View File

@@ -30,26 +30,22 @@
<refsect1>
<title>Description</title>
<para><command>systemd-ask-password</command> may be used to query
a system password or passphrase from the user, using a question
message specified on the command line. When run from a TTY it will
query a password on the TTY and print it to standard output. When
run with no TTY or with <option>--no-tty</option> it will use the
system-wide query mechanism, which allows active users to respond via
several agents, listed below.</para>
<para><command>systemd-ask-password</command> may be used to query a password or passphrase interactively
from the user, using a question prompt specified on the command line. When run from a TTY it will query a
password on the TTY and print it to standard output. When run with no TTY or with
<option>--no-tty</option> it will use a system-wide or per-user agent-based query mechanism, which allows
active users to respond via several agents, listed below.</para>
<para>The purpose of this tool is to query system-wide passwords
— that is passwords not attached to a specific user account.
Examples include: unlocking encrypted hard disks when they are
plugged in or at boot, entering an SSL certificate passphrase for
web and VPN servers.</para>
<para>The purpose of this tool is to query system-wide or per-user passwords — the former includes
passwords possibly not associated to a specific user account. Examples include: unlocking encrypted hard
disks when they are plugged in or at boot, entering an SSL certificate passphrase for web and VPN
servers.</para>
<para>Existing agents are:
<para>Existing system-level agents are:
<itemizedlist>
<listitem><para>A boot-time password agent asking the user for
passwords using
<citerefentry project='die-net'><refentrytitle>plymouth</refentrytitle><manvolnum>8</manvolnum></citerefentry>,
<listitem><para>A boot-time password agent asking the user for passwords using <citerefentry
project='die-net'><refentrytitle>plymouth</refentrytitle><manvolnum>8</manvolnum></citerefentry>,
</para></listitem>
<listitem><para>A boot-time password agent querying the user
@@ -77,17 +73,15 @@
all the agents listed above (except for the last one), run as privileged
system services. The last one also needs elevated privileges, so
should be run through
<citerefentry project='die-net'><refentrytitle>sudo</refentrytitle><manvolnum>8</manvolnum></citerefentry>
<citerefentry><refentrytitle>run0</refentrytitle><manvolnum>1</manvolnum></citerefentry>
or similar.</para>
<para>Additional password agents may be implemented according to
the <ulink url="https://systemd.io/PASSWORD_AGENTS/">systemd Password Agent
Specification</ulink>.</para>
<para>Additional password agents may be implemented according to the <ulink
url="https://systemd.io/PASSWORD_AGENTS/">systemd Password Agent Specification</ulink>.</para>
<para>If a password is queried on a TTY, the user may press TAB to
hide the asterisks normally shown for each character typed.
Pressing Backspace as first key achieves the same effect.</para>
</refsect1>
<refsect1>
@@ -241,6 +235,17 @@
<xi:include href="version-info.xml" xpointer="v249"/></listitem>
</varlistentry>
<varlistentry>
<term><option>--user</option></term>
<term><option>--system</option></term>
<listitem><para>Controls whether to query the system-wide or the per-user password agents. By default
if invoked privileged the system-wide agents are queried, otherwise the per-user ones. These options
allow to override this automatic behaviour.</para>
<xi:include href="version-info.xml" xpointer="v257"/></listitem>
</varlistentry>
<xi:include href="standard-options.xml" xpointer="help" />
</variablelist>

View File

@@ -38,7 +38,7 @@ static int help(void) {
return log_oom();
printf("%1$s [OPTIONS...] MESSAGE\n\n"
"%3$sQuery the user for a system passphrase, via the TTY or a UI agent.%4$s\n\n"
"%3$sQuery the user for a passphrase, via the TTY or a UI agent.%4$s\n\n"
" -h --help Show this help\n"
" --icon=NAME Icon name\n"
" --id=ID Query identifier (e.g. \"cryptsetup:/dev/sda5\")\n"
@@ -58,6 +58,8 @@ static int help(void) {
" --no-output Do not print password to standard output\n"
" -n Do not suffix password written to standard output with\n"
" newline\n"
" --user Ask only our own user's agents\n"
" --system Ask agents of the system and of all users\n"
"\nSee the %2$s for details.\n",
program_invocation_short_name,
link,
@@ -81,6 +83,8 @@ static int parse_argv(int argc, char *argv[]) {
ARG_NO_OUTPUT,
ARG_VERSION,
ARG_CREDENTIAL,
ARG_USER,
ARG_SYSTEM,
};
static const struct option options[] = {
@@ -97,6 +101,8 @@ static int parse_argv(int argc, char *argv[]) {
{ "keyname", required_argument, NULL, ARG_KEYNAME },
{ "no-output", no_argument, NULL, ARG_NO_OUTPUT },
{ "credential", required_argument, NULL, ARG_CREDENTIAL },
{ "user", no_argument, NULL, ARG_USER },
{ "system", no_argument, NULL, ARG_SYSTEM },
{}
};
@@ -183,6 +189,14 @@ static int parse_argv(int argc, char *argv[]) {
arg_credential_name = optarg;
break;
case ARG_USER:
arg_flags |= ASK_PASSWORD_USER;
break;
case ARG_SYSTEM:
arg_flags &= ~ASK_PASSWORD_USER;
break;
case 'n':
arg_newline = false;
break;
@@ -228,6 +242,9 @@ static int run(int argc, char *argv[]) {
log_setup();
/* Unprivileged? Then imply ASK_PASSWORD_USER by default */
SET_FLAG(arg_flags, ASK_PASSWORD_USER, geteuid() != 0);
r = parse_argv(argc, argv);
if (r <= 0)
return r;