diff options
Diffstat (limited to 'lacme-accountd')
-rwxr-xr-x | lacme-accountd | 35 |
1 files changed, 27 insertions, 8 deletions
diff --git a/lacme-accountd b/lacme-accountd index b9a6e33..e170637 100755 --- a/lacme-accountd +++ b/lacme-accountd @@ -30,7 +30,6 @@ my $NAME = 'lacme-accountd'; use Errno 'EINTR'; use File::Basename 'dirname'; use Getopt::Long qw/:config posix_default no_ignore_case gnu_getopt auto_version/; -use List::Util 'first'; use MIME::Base64 'encode_base64url'; use Socket qw/PF_UNIX SOCK_STREAM SHUT_RDWR/; @@ -64,11 +63,32 @@ sub usage(;$$) { usage(1) unless GetOptions(\%OPTS, qw/config=s privkey=s socket=s stdio quiet|q debug help|h/); usage(0) if $OPTS{help}; +sub env_fallback($$) { + my $v = $ENV{ shift() }; + return (defined $v and $v ne "") ? $v : shift; +} +sub spec_expand($) { + my $str = shift; + $str =~ s#%(.)# my $x = + $1 eq "C" ? ($< == 0 ? "@@localstatedir@@/cache" : env_fallback(XDG_CACHE_HOME => "$ENV{HOME}/.cache")) + : $1 eq "E" ? ($< == 0 ? "@@sysconfdir@@" : env_fallback(XDG_CONFIG_HOME => "$ENV{HOME}/.config")) + : $1 eq "g" ? (getgrgid((split /\s/,$()[0]))[0] + : $1 eq "G" ? $( =~ s/\s.*//r + : $1 eq "h" ? (getpwuid($<))[7] + : $1 eq "u" ? (getpwuid($<))[0] + : $1 eq "U" ? $< + : $1 eq "t" ? ($< == 0 ? "@@runstatedir@@" : $ENV{XDG_RUNTIME_DIR}) + : $1 eq "T" ? env_fallback(TMPDIR => "/tmp") + : $1 eq "%" ? "%" + : die "Error: \"$str\" has unknown specifier %$1\n"; + die "Error: undefined expansion %$1 in \"$str\"\n" unless defined $x; + $x; + #ge; + return $str; +} + do { - my $conffile = $OPTS{config} // first { -f $_ } - ( ($ENV{XDG_CONFIG_HOME} // "$ENV{HOME}/.config") . "/lacme/$NAME.conf" - , "@@sysconfdir@@/lacme/$NAME.conf" - ); + my $conffile = spec_expand($OPTS{config} // "%E/lacme/$NAME.conf"); if (defined $OPTS{config} or -e $conffile) { print STDERR "Using configuration file: $conffile\n" if $OPTS{debug}; @@ -94,7 +114,7 @@ do { # my ($JWK, $SIGN); if ($OPTS{privkey} =~ /\A(file|gpg):(\p{Print}+)\z/) { - my ($method, $filename) = ($1,$2); + my ($method, $filename) = ($1, spec_expand($2)); my ($fh, @command); if ($method eq 'file') { # generate with `openssl genpkey -algorithm RSA` @@ -142,8 +162,7 @@ my $JWK_STR = JSON::->new->encode($JWK); # delete the file manually. # unless (defined $OPTS{stdio}) { - my $sockname = $OPTS{socket} // (defined $ENV{XDG_RUNTIME_DIR} ? "$ENV{XDG_RUNTIME_DIR}/S.lacme" : undef); - die "Missing socket option\n" unless defined $sockname; + my $sockname = spec_expand($OPTS{socket} // '%t/S.lacme'); $sockname = $sockname =~ /\A(\p{Print}+)\z/ ? $1 : die "Invalid socket name\n"; # untaint $sockname # ensure we're the only user with write access to the parent dir |