Every tick of the event loop can change the working directory,
so we need to restore it for every client if they operate
in different directories.
This would be easier if we had openat(2) and friends in Perl;
but Inline::C is practically required for lei, now.
+sub fchdir {
+ my ($lei) = @_;
+ my $dh = $lei->{3} // die 'BUG: lei->{3} (CWD) gone';
+ chdir($dh) || $lei->fail("fchdir: $!");
+}
+
sub wq_eof { # EOF callback for main daemon
my ($lei) = @_;
my $wq1 = delete $lei->{wq1} // return $lei->fail; # already failed
sub wq_eof { # EOF callback for main daemon
my ($lei) = @_;
my $wq1 = delete $lei->{wq1} // return $lei->fail; # already failed
my ($lei) = @_; # $_[1] = $rbuf
if (defined($_[1])) {
$_[1] eq '' and return eval {
my ($lei) = @_; # $_[1] = $rbuf
if (defined($_[1])) {
$_[1] eq '' and return eval {
- if (my $dfd = $lei->{3}) {
- chdir($dfd) or return $lei->fail("fchdir: $!");
- }
+ $lei->fchdir or return;
my @argv = split(/\s+/, $lei->{mset_opt}->{qstr});
$lei->{mset_opt}->{qstr} = extract_all($lei, @argv)
or return;
my @argv = split(/\s+/, $lei->{mset_opt}->{qstr});
$lei->{mset_opt}->{qstr} = extract_all($lei, @argv)
or return;
my ($self) = @_; # $_[1] = $rbuf
if (defined($_[1])) {
$_[1] eq '' and return eval {
my ($self) = @_; # $_[1] = $rbuf
if (defined($_[1])) {
$_[1] eq '' and return eval {
- if (my $dfd = $self->{3}) {
- chdir($dfd) or return $self->fail("fchdir: $!");
- }
+ $self->fchdir or return;
$self->{mset_opt}->{q_raw} = $self->{mset_opt}->{qstr};
$self->{lse}->query_approxidate($self->{lse}->git,
$self->{mset_opt}->{qstr});
$self->{mset_opt}->{q_raw} = $self->{mset_opt}->{qstr};
$self->{lse}->query_approxidate($self->{lse}->git,
$self->{mset_opt}->{qstr});
sub do_post_augment {
my ($lei) = @_;
my $l2m = $lei->{l2m} or return; # client disconnected
sub do_post_augment {
my ($lei) = @_;
my $l2m = $lei->{l2m} or return; # client disconnected
+ $lei->fchdir or return;
my $err;
eval { $l2m->post_augment($lei) };
$err = $@;
my $err;
eval { $l2m->post_augment($lei) };
$err = $@;