diff --git a/doc/gpg-card.texi b/doc/gpg-card.texi index be19704cc..60107176b 100644 --- a/doc/gpg-card.texi +++ b/doc/gpg-card.texi @@ -125,6 +125,16 @@ Specify a non-default gpg binary to be used by certain commands. @opindex gpgsm-program Specify a non-default gpgsm binary to be used by certain commands. +@item --chuid @var{uid} +@opindex chuid +Change the current user to @var{uid} which may either be a number or a +name. This can be used from the root account to run gpg-card for +another user. If @var{uid} is not the current UID a standard PATH is +set and the envvar GNUPGHOME is unset. To override the latter the +option @option{--homedir} can be used. This option has only an effect +when used on the command line. This option has currently no effect at +all on Windows. + @end table @mansect notes (OpenPGP) diff --git a/doc/gpg.texi b/doc/gpg.texi index 970cbabb5..09e973f17 100644 --- a/doc/gpg.texi +++ b/doc/gpg.texi @@ -3617,6 +3617,16 @@ on the configuration file. @c OpenPGP card while several cards are available. This option might be @c removed if it turns out that nobody requires it. +@item --chuid @var{uid} +@opindex chuid +Change the current user to @var{uid} which may either be a number or a +name. This can be used from the root account to run gpg for +another user. If @var{uid} is not the current UID a standard PATH is +set and the envvar GNUPGHOME is unset. To override the latter the +option @option{--homedir} can be used. This option has only an effect +when used on the command line. This option has currently no effect at +all on Windows. + @end table @c ******************************* diff --git a/doc/tools.texi b/doc/tools.texi index 3ebec1a98..3bbddbcd3 100644 --- a/doc/tools.texi +++ b/doc/tools.texi @@ -1330,39 +1330,6 @@ gpg-connect-agent [options] [commands] The following options may be used: @table @gnupgtabopt -@item -v -@itemx --verbose -@opindex verbose -Output additional information while running. - -@item -q -@item --quiet -@opindex q -@opindex quiet -Try to be as quiet as possible. - -@include opt-homedir.texi - -@item --agent-program @var{file} -@opindex agent-program -Specify the agent program to be started if none is running. The -default value is determined by running @command{gpgconf} with the -option @option{--list-dirs}. Note that the pipe symbol (@code{|}) is -used for a regression test suite hack and may thus not be used in the -file name. - -@item --dirmngr-program @var{file} -@opindex dirmngr-program -Specify the directory manager (keyserver client) program to be started -if none is running. This has only an effect if used together with the -option @option{--dirmngr}. - -@item --keyboxd-program @var{file} -@opindex keyboxd-program -Specify the keybox daemon program to be started if none is running. -This has only an effect if used together with the option -@option{--keyboxd}. - @item --dirmngr @opindex dirmngr Connect to a running directory manager (keyserver client) instead of @@ -1390,6 +1357,29 @@ execute it as an Assuan server. Here is how you would run @command{gpgsm}: @end smallexample Note that you may not use options on the command line in this case. +@item -v +@itemx --verbose +@opindex verbose +Output additional information while running. + +@item -q +@item --quiet +@opindex q +@opindex quiet +Try to be as quiet as possible. + +@include opt-homedir.texi + +@item --chuid @var{uid} +@opindex chuid +Change the current user to @var{uid} which may either be a number or a +name. This can be used from the root account to run gpg-connect-agent +for another user. If @var{uid} is not the current UID a standard PATH +is set and the envvar GNUPGHOME is unset. To override the latter the +option @option{--homedir} can be used. This option has only an effect +when used on the command line. This option has currently no effect at +all on Windows. + @item --no-ext-connect @opindex no-ext-connect When using @option{-S} or @option{--exec}, @command{gpg-connect-agent} @@ -1407,6 +1397,26 @@ In interactive mode the command line history is usually saved and restored to and from a file below the GnuPG home directory. This option inhibits the use of that file. +@item --agent-program @var{file} +@opindex agent-program +Specify the agent program to be started if none is running. The +default value is determined by running @command{gpgconf} with the +option @option{--list-dirs}. Note that the pipe symbol (@code{|}) is +used for a regression test suite hack and may thus not be used in the +file name. + +@item --dirmngr-program @var{file} +@opindex dirmngr-program +Specify the directory manager (keyserver client) program to be started +if none is running. This has only an effect if used together with the +option @option{--dirmngr}. + +@item --keyboxd-program @var{file} +@opindex keyboxd-program +Specify the keybox daemon program to be started if none is running. +This has only an effect if used together with the option +@option{--keyboxd}. + @item -r @var{file} @itemx --run @var{file} @opindex run diff --git a/g10/gpg.c b/g10/gpg.c index 7f219e869..0e2a3b2dc 100644 --- a/g10/gpg.c +++ b/g10/gpg.c @@ -437,6 +437,7 @@ enum cmd_and_opt_values oFullTimestrings, oIncludeKeyBlock, oNoIncludeKeyBlock, + oChUid, oNoop }; @@ -897,6 +898,7 @@ static gpgrt_opt_t opts[] = { ARGPARSE_s_s (oLCctype, "lc-ctype", "@"), ARGPARSE_s_s (oLCmessages, "lc-messages","@"), ARGPARSE_s_s (oXauthority, "xauthority", "@"), + ARGPARSE_s_s (oChUid, "chuid", "@"), ARGPARSE_s_n (oNoAutostart, "no-autostart", "@"), ARGPARSE_s_n (oUseKeyboxd, "use-keyboxd", "@"), /* Options which can be used in special circumstances. They are not @@ -2328,6 +2330,8 @@ main (int argc, char **argv) static int print_dane_records; static int print_pka_records; static int allow_large_chunks; + static const char *homedirvalue; + static const char *changeuser; #ifdef __riscos__ @@ -2413,7 +2417,6 @@ main (int argc, char **argv) opt.keyid_format = KF_NONE; opt.def_sig_expire = "0"; opt.def_cert_expire = "0"; - gnupg_set_homedir (NULL); opt.passphrase_repeat = 1; opt.emit_version = 0; opt.weak_digests = NULL; @@ -2446,7 +2449,11 @@ main (int argc, char **argv) break; case oHomedir: - gnupg_set_homedir (pargs.r.ret_str); + homedirvalue = pargs.r.ret_str; + break; + + case oChUid: + changeuser = pargs.r.ret_str; break; case oNoPermissionWarn: @@ -2498,6 +2505,11 @@ main (int argc, char **argv) assuan_set_gpg_err_source (GPG_ERR_SOURCE_DEFAULT); setup_libassuan_logging (&opt.debug, NULL); + /* Change UID and then set the homedir. */ + if (changeuser && gnupg_chuid (changeuser, 0)) + log_inc_errorcount (); /* Force later termination. */ + gnupg_set_homedir (homedirvalue); + /* Set default options which require that malloc stuff is ready. */ additional_weak_digest ("MD5"); parse_auto_key_locate (DEFAULT_AKL_LIST); @@ -2872,6 +2884,7 @@ main (int argc, char **argv) opt.def_recipient_self = 0; break; case oHomedir: break; + case oChUid: break; /* Command line only (see above). */ case oNoBatch: opt.batch = 0; break; case oWithTofuInfo: opt.with_tofu_info = 1; break; diff --git a/sm/gpgsm.c b/sm/gpgsm.c index 3b41fe3b2..cbce15594 100644 --- a/sm/gpgsm.c +++ b/sm/gpgsm.c @@ -992,8 +992,10 @@ main ( int argc, char **argv) estream_t htmlauditfp = NULL; struct assuan_malloc_hooks malloc_hooks; int pwfd = -1; - const char *changeuser = NULL; - /*mtrace();*/ + + static const char *homedirvalue; + static const char *changeuser; + early_system_init (); gnupg_reopen_std (GPGSM_NAME); @@ -1062,7 +1064,7 @@ main ( int argc, char **argv) break; case oHomedir: - gnupg_set_homedir (pargs.r.ret_str); + homedirvalue = pargs.r.ret_str; break; case oChUid: @@ -1096,6 +1098,11 @@ main ( int argc, char **argv) assuan_set_gpg_err_source (GPG_ERR_SOURCE_DEFAULT); setup_libassuan_logging (&opt.debug, NULL); + /* Change UID and then set homedir. */ + if (changeuser && gnupg_chuid (changeuser, 0)) + log_inc_errorcount (); /* Force later termination. */ + gnupg_set_homedir (homedirvalue); + /* Setup a default control structure for command line mode */ memset (&ctrl, 0, sizeof ctrl); gpgsm_init_default_ctrl (&ctrl); @@ -1103,9 +1110,6 @@ main ( int argc, char **argv) ctrl.status_fd = -1; /* No status output. */ ctrl.autodetect_encoding = 1; - if (changeuser && gnupg_chuid (changeuser, 0)) - log_inc_errorcount (); /* Force later termination. */ - /* Set the default policy file */ opt.policy_file = make_filename (gnupg_homedir (), "policies.txt", NULL); diff --git a/tools/gpg-card.c b/tools/gpg-card.c index 7910a48fe..bf3663924 100644 --- a/tools/gpg-card.c +++ b/tools/gpg-card.c @@ -76,6 +76,7 @@ enum opt_values oNoKeyLookup, oNoHistory, + oChUid, oDummy }; @@ -104,6 +105,7 @@ static gpgrt_opt_t opts[] = { "use --no-key-lookup for \"list\""), ARGPARSE_s_n (oNoHistory,"no-history", "do not use the command history file"), + ARGPARSE_s_s (oChUid, "chuid", "@"), ARGPARSE_end () }; @@ -125,6 +127,8 @@ struct keyinfolabel_s }; typedef struct keyinfolabel_s *keyinfolabel_t; +/* Helper for --chuid. */ +static const char *changeuser; /* Limit of size of data we read from a file for certain commands. */ #define MAX_GET_DATA_FROM_FILE 16384 @@ -235,6 +239,8 @@ parse_arguments (gpgrt_argparse_t *pargs, gpgrt_opt_t *popts) case oNoKeyLookup: opt.no_key_lookup = 1; break; case oNoHistory: opt.no_history = 1; break; + case oChUid: changeuser = pargs->r.ret_str; break; + default: pargs->err = 2; break; } } @@ -279,6 +285,9 @@ main (int argc, char **argv) parse_arguments (&pargs, opts); gpgrt_argparse (NULL, &pargs, NULL); /* Release internal state. */ + if (changeuser && gnupg_chuid (changeuser, 0)) + log_inc_errorcount (); /* Force later termination. */ + if (log_get_errorcount (0)) exit (2); diff --git a/tools/gpg-connect-agent.c b/tools/gpg-connect-agent.c index cde086770..ac0bc89dc 100644 --- a/tools/gpg-connect-agent.c +++ b/tools/gpg-connect-agent.c @@ -71,8 +71,10 @@ enum cmd_and_opt_values oKeyboxd, oUIServer, oNoHistory, - oNoAutostart + oNoAutostart, + oChUid, + oNoop }; @@ -107,6 +109,7 @@ static gpgrt_opt_t opts[] = { ARGPARSE_s_s (oAgentProgram, "agent-program", "@"), ARGPARSE_s_s (oDirmngrProgram, "dirmngr-program", "@"), ARGPARSE_s_s (oKeyboxdProgram, "keyboxd-program", "@"), + ARGPARSE_s_s (oChUid, "chuid", "@"), ARGPARSE_end () }; @@ -1187,6 +1190,9 @@ main (int argc, char **argv) char **cmdline_commands = NULL; char *historyname = NULL; + static const char *changeuser; + + early_system_init (); gnupg_rl_initialize (); gpgrt_set_strusage (my_strusage); @@ -1233,12 +1239,16 @@ main (int argc, char **argv) opt.enable_varsubst = 1; opt.trim_leading_spaces = 1; break; + case oChUid: changeuser = pargs.r.ret_str; break; default: pargs.err = 2; break; } } gpgrt_argparse (NULL, &pargs, NULL); /* Release internal state. */ + if (changeuser && gnupg_chuid (changeuser, 0)) + log_inc_errorcount (); /* Force later termination. */ + if (log_get_errorcount (0)) exit (2);