From: Eric Wong <e@80x24.org> To: meta@public-inbox.org Subject: [PATCH 4/9] lei: set PWD correctly for path expansion Date: Wed, 27 Jan 2021 03:42:25 -0600 [thread overview] Message-ID: <20210127094230.31174-5-e@80x24.org> (raw) In-Reply-To: <20210127094230.31174-1-e@80x24.org> While commit d1b9582872d1824f166a038dcf32b6ae8c6dc735 ("lei: pass FD to CWD via cmsg, use fchdir on server") ensured things work properly to get the daemon in the right directory, it forgot to deal with places where we expand relative paths based on the current working directory. --- lib/PublicInbox/LEI.pm | 56 ++++++++++++++++++++++++++++-------------- 1 file changed, 37 insertions(+), 19 deletions(-) diff --git a/lib/PublicInbox/LEI.pm b/lib/PublicInbox/LEI.pm index c017fd4e..0ce6a00b 100644 --- a/lib/PublicInbox/LEI.pm +++ b/lib/PublicInbox/LEI.pm @@ -13,6 +13,7 @@ use parent qw(PublicInbox::DS PublicInbox::LeiExternal use Getopt::Long (); use Socket qw(AF_UNIX SOCK_SEQPACKET MSG_EOR pack_sockaddr_un); use Errno qw(EAGAIN EINTR ECONNREFUSED ENOENT ECONNRESET); +use Cwd qw(getcwd); use POSIX (); use IO::Handle (); use Fcntl qw(SEEK_SET); @@ -65,18 +66,37 @@ sub opt_dash ($$) { ($spec, '<>' => $cb, $GLP_PASS) # for Getopt::Long } +sub rel2abs ($$) { + my ($self, $p) = @_; + return $p if index($p, '/') == 0; # already absolute + my $pwd = $self->{env}->{PWD}; + if (defined $pwd) { + my $cwd = $self->{3} // getcwd() // die "getcwd(PWD=$pwd): $!"; + if (my @st_pwd = stat($pwd)) { + my @st_cwd = stat($cwd) or die "stat($cwd): $!"; + "@st_pwd[1,0]" eq "@st_cwd[1,0]" or + $self->{env}->{PWD} = $pwd = $cwd; + } else { # PWD was invalid + delete $self->{env}->{PWD}; + undef $pwd; + } + } + $pwd //= $self->{env}->{PWD} = getcwd() // die "getcwd(PWD=$pwd): $!"; + File::Spec->rel2abs($p, $pwd); +} + sub _store_path ($) { - my ($env) = @_; - File::Spec->rel2abs(($env->{XDG_DATA_HOME} // - ($env->{HOME} // '/nonexistent').'/.local/share') - .'/lei/store', $env->{PWD}); + my ($self) = @_; + rel2abs($self, ($self->{env}->{XDG_DATA_HOME} // + ($self->{env}->{HOME} // '/nonexistent').'/.local/share') + .'/lei/store'); } sub _config_path ($) { - my ($env) = @_; - File::Spec->rel2abs(($env->{XDG_CONFIG_HOME} // - ($env->{HOME} // '/nonexistent').'/.config') - .'/lei/config', $env->{PWD}); + my ($self) = @_; + rel2abs($self, ($self->{env}->{XDG_CONFIG_HOME} // + ($self->{env}->{HOME} // '/nonexistent').'/.config') + .'/lei/config'); } # TODO: generate shell completion + help using %CMD and %OPTDESC @@ -295,7 +315,7 @@ sub atfork_prepare_wq { my ($self, $wq) = @_; my $tcafc = $wq->{-ipc_atfork_child_close} //= [ $listener // () ]; if (my $sock = $self->{sock}) { - push @$tcafc, @$self{qw(0 1 2)}, $sock; + push @$tcafc, @$self{qw(0 1 2 3)}, $sock; } if (my $pgr = $self->{pgr}) { push @$tcafc, @$pgr[1,2]; @@ -345,7 +365,7 @@ sub atfork_parent_wq { $ret->{dedupe} = $wq->deep_clone($dedupe); } $self->{env} = $env; - delete @$ret{qw(-lei_store cfg old_1 pgr lxs)}; # keep l2m + delete @$ret{qw(3 -lei_store cfg old_1 pgr lxs)}; # keep l2m my @io = delete @$ret{0..2}; $io[3] = delete($ret->{sock}) // $io[2]; my $l2m = $ret->{l2m}; @@ -362,7 +382,7 @@ sub _help ($;$) { my @info = @{$CMD{$cmd} // [ '...', '...' ]}; my @top = ($cmd, shift(@info) // ()); my $cmd_desc = shift(@info); - $cmd_desc = $cmd_desc->($self->{env}) if ref($cmd_desc) eq 'CODE'; + $cmd_desc = $cmd_desc->($self) if ref($cmd_desc) eq 'CODE'; my @opt_desc; my $lpad = 2; for my $sw (grep { !ref } @info) { # ("prio=s", "z", $GLP_PASS) @@ -520,7 +540,7 @@ sub dispatch { sub _lei_cfg ($;$) { my ($self, $creat) = @_; - my $f = _config_path($self->{env}); + my $f = _config_path($self); my @st = stat($f); my $cur_st = @st ? pack('dd', $st[10], $st[7]) : ''; # 10:ctime, 7:size if (my $cfg = $PATH2CFG{$f}) { # reuse existing object in common case @@ -550,8 +570,7 @@ sub _lei_store ($;$) { $cfg->{-lei_store} //= do { require PublicInbox::LeiStore; my $dir = $cfg->{'leistore.dir'}; - $dir //= _store_path($self->{env}) if $creat; - return unless $dir; + $dir //= $creat ? _store_path($self) : return; PublicInbox::LeiStore->new($dir, { creat => $creat }); }; } @@ -587,9 +606,8 @@ sub lei_init { my ($self, $dir) = @_; my $cfg = _lei_cfg($self, 1); my $cur = $cfg->{'leistore.dir'}; - my $env = $self->{env}; - $dir //= _store_path($env); - $dir = File::Spec->rel2abs($dir, $env->{PWD}); # PWD is symlink-aware + $dir //= _store_path($self); + $dir = rel2abs($self, $dir); my @cur = stat($cur) if defined($cur); $cur = File::Spec->canonpath($cur // $dir); my @dir = stat($dir); @@ -601,7 +619,7 @@ sub lei_init { } # some folks like symlinks and bind mounts :P - if (@dir && "$cur[0] $cur[1]" eq "$dir[0] $dir[1]") { + if (@dir && "@cur[1,0]" eq "@dir[1,0]") { lei_config($self, 'leistore.dir', $dir); _lei_store($self, 1)->done; return qerr($self, "$exists (as $cur)"); @@ -771,7 +789,7 @@ sub accept_dispatch { # Listener {post_accept} callback my ($argc, @argv) = split(/\0/, $buf, -1); undef $buf; my %env = map { split(/=/, $_, 2) } splice(@argv, $argc); - if (chdir(delete($self->{3}))) { + if (chdir($self->{3})) { local %ENV = %env; $self->{env} = \%env; eval { dispatch($self, @argv) };
next prev parent reply other threads:[~2021-01-27 9:42 UTC|newest] Thread overview: 10+ messages / expand[flat|nested] mbox.gz Atom feed top 2021-01-27 9:42 [PATCH 0/9] lei completion, some small updates Eric Wong 2021-01-27 9:42 ` [PATCH 1/9] eml: favor index() over regexp match Eric Wong 2021-01-27 9:42 ` [PATCH 2/9] lei: drop "git" command forwarding Eric Wong 2021-01-27 9:42 ` [PATCH 3/9] lei: fix comment regarding client payload Eric Wong 2021-01-27 9:42 ` Eric Wong [this message] 2021-01-27 9:42 ` [PATCH 5/9] gcf2: rely on Perl 5.10 to avoid needless ++ Eric Wong 2021-01-27 9:42 ` [PATCH 6/9] lei: complete option switch args Eric Wong 2021-01-27 9:42 ` [PATCH 7/9] lei_overview: clear redundant ovv_buf definition Eric Wong 2021-01-27 9:42 ` [PATCH 8/9] v2writable: nproc: use sysconf() on Linux and FreeBSD Eric Wong 2021-01-27 9:42 ` [PATCH 9/9] lei: dclose: fix typo Eric Wong
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style List information: https://public-inbox.org/README * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=20210127094230.31174-5-e@80x24.org \ --to=e@80x24.org \ --cc=meta@public-inbox.org \ --subject='Re: [PATCH 4/9] lei: set PWD correctly for path expansion' \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: link
Code repositories for project(s) associated with this inbox: https://80x24.org/public-inbox.git This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).