mirror of
git://git.proxmox.com/git/pve-common.git
synced 2024-12-22 21:33:47 +03:00
tools: run fork: allow running code in parent after fork
Add an option parameter to the run_fork() run_fork_with_timeout() functions, where an 'afterfork' subroutine that is run in the parent process after the fork can be specified. It is made subject to the timeout too, because the fork already started running at that point and an error in the 'afterfork' subroutine will take priority over an error in the child. In preparation to add a helper to run a Perl subroutine in a user namespace, which, in turn, will be used for running the container backup subroutine for external providers inside a user namespace. That allows them to see the filesystem to back-up from the containers perspective and also improves security because of isolation. Signed-off-by: Fiona Ebner <f.ebner@proxmox.com>
This commit is contained in:
parent
de6ffbdebf
commit
fb96ee89f2
@ -1026,7 +1026,7 @@ sub must_stringify {
|
||||
# sigkill after $timeout a $sub running in a fork if it can't write a pipe
|
||||
# the $sub has to return a single scalar
|
||||
sub run_fork_with_timeout {
|
||||
my ($timeout, $sub) = @_;
|
||||
my ($timeout, $sub, $opts) = @_;
|
||||
|
||||
my $res;
|
||||
my $error;
|
||||
@ -1075,17 +1075,28 @@ sub run_fork_with_timeout {
|
||||
$error = $child_res->{error};
|
||||
};
|
||||
|
||||
my $handle_forked = sub {
|
||||
if (my $afterfork = $opts->{afterfork}) {
|
||||
eval { $afterfork->($child); };
|
||||
if (my $err = $@) {
|
||||
$error = $err; # propagate error
|
||||
die $err;
|
||||
}
|
||||
}
|
||||
$readvalues->();
|
||||
};
|
||||
|
||||
my $got_timeout = 0;
|
||||
my $wantarray = wantarray; # so it can be queried inside eval
|
||||
eval {
|
||||
if (defined($timeout)) {
|
||||
if ($wantarray) {
|
||||
(undef, $got_timeout) = run_with_timeout($timeout, $readvalues);
|
||||
(undef, $got_timeout) = run_with_timeout($timeout, $handle_forked);
|
||||
} else {
|
||||
run_with_timeout($timeout, $readvalues);
|
||||
run_with_timeout($timeout, $handle_forked);
|
||||
}
|
||||
} else {
|
||||
$readvalues->();
|
||||
$handle_forked->();
|
||||
}
|
||||
};
|
||||
warn $@ if $@;
|
||||
@ -1102,8 +1113,8 @@ sub run_fork_with_timeout {
|
||||
}
|
||||
|
||||
sub run_fork {
|
||||
my ($code) = @_;
|
||||
return run_fork_with_timeout(undef, $code);
|
||||
my ($code, $opts) = @_;
|
||||
return run_fork_with_timeout(undef, $code, $opts);
|
||||
}
|
||||
|
||||
# NOTE: NFS syscall can't be interrupted, so alarm does
|
||||
|
Loading…
Reference in New Issue
Block a user