From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on dcvr.yhbt.net X-Spam-Level: X-Spam-ASN: X-Spam-Status: No, score=-4.2 required=3.0 tests=ALL_TRUSTED,AWL,BAYES_00, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF, T_SCC_BODY_TEXT_LINE shortcircuit=no autolearn=ham autolearn_force=no version=3.4.6 Received: from localhost (dcvr.yhbt.net [127.0.0.1]) by dcvr.yhbt.net (Postfix) with ESMTP id 1CDFB1F406 for ; Thu, 30 Nov 2023 19:33:54 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=80x24.org; s=selector1; t=1701372834; bh=NxNC4QAIv805M9StjSPIU4XPL5JQVljAZExbcNX4xss=; h=From:To:Subject:Date:From; b=gQKqHloAloNPQ6+EqTDUmJQQP4SRiXr/9J+l2rbD4o1Op4XD40yMzUkLSgHPzY+5p suXbul+tSmFFZaa2iBz6PPTh+pTCAApuwsduOLWtb950GTYTZb1HWTWQkH9LvTdbk9 HVJCU1HBZLK4xjg5SjVaqKhydgzaTrvJGX8+2vfU= From: Eric Wong To: spew@80x24.org Subject: [PATCH] WIP-limiter-rlimit Date: Thu, 30 Nov 2023 19:33:53 +0000 Message-ID: <20231130193353.1105570-1-e@80x24.org> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit List-Id: --- lib/PublicInbox/Limiter.pm | 15 +++++++++------ lib/PublicInbox/Spawn.pm | 31 ++++++++++++++++++++++++------- t/spawn.t | 7 +++++++ 3 files changed, 40 insertions(+), 13 deletions(-) diff --git a/lib/PublicInbox/Limiter.pm b/lib/PublicInbox/Limiter.pm index 48a2b6a3..a8d08fc3 100644 --- a/lib/PublicInbox/Limiter.pm +++ b/lib/PublicInbox/Limiter.pm @@ -31,14 +31,17 @@ sub setup_rlimit { } elsif (scalar(@rlimit) != 2) { warn "could not parse $k: $v\n"; } - eval { require BSD::Resource }; - if ($@) { - warn "BSD::Resource missing for $rlim"; - next; - } + my $inf = $v =~ /\binfinity\b/i ? + $PublicInbox::Spawn::RLIMITS{RLIM_INFINITY} // eval { + require BSD::Resource; + BSD::Resource::RLIM_INFINITY(); + } // do { + warn "BSD::Resource missing for $rlim"; + next; + } : undef; for my $i (0..$#rlimit) { next if $rlimit[$i] ne 'INFINITY'; - $rlimit[$i] = BSD::Resource::RLIM_INFINITY(); + $rlimit[$i] = $inf; } $self->{$rlim} = \@rlimit; } diff --git a/lib/PublicInbox/Spawn.pm b/lib/PublicInbox/Spawn.pm index b09bb536..aed993db 100644 --- a/lib/PublicInbox/Spawn.pm +++ b/lib/PublicInbox/Spawn.pm @@ -21,10 +21,11 @@ use IO::Handle (); use Carp qw(croak); use PublicInbox::IO; our @EXPORT_OK = qw(which spawn popen_rd popen_wr run_die run_wait run_qx); -our @RLIMITS = qw(RLIMIT_CPU RLIMIT_CORE RLIMIT_DATA); +our (@RLIMITS, %RLIMITS); use autodie qw(close open pipe seek sysseek truncate); BEGIN { + @RLIMITS = qw(RLIMIT_CPU RLIMIT_CORE RLIMIT_DATA RLIMIT_FSIZE); my $all_libc = <<'ALL_LIBC'; # all *nix systems we support #include #include @@ -292,14 +293,28 @@ void recv_cmd4(PerlIO *s, SV *buf, STRLEN n) Inline_Stack_Done; } #endif /* defined(CMSG_SPACE) && defined(CMSG_LEN) */ -ALL_LIBC +void rlimit_map() +{ + Inline_Stack_Vars; + Inline_Stack_Reset; +ALL_LIBC my $inline_dir = $ENV{PERL_INLINE_DIRECTORY} // ( $ENV{XDG_CACHE_HOME} // ( ($ENV{HOME} // '/nonexistent').'/.cache' ) ).'/public-inbox/inline-c'; undef $all_libc unless -d $inline_dir; if (defined $all_libc) { + for (@RLIMITS, 'RLIM_INFINITY') { + $all_libc .= <new($inline_dir. @@ -325,6 +340,7 @@ ALL_LIBC } if (defined $all_libc) { # set for Gcf2 $ENV{PERL_INLINE_DIRECTORY} = $inline_dir; + %RLIMITS = rlimit_map(); } else { require PublicInbox::SpawnPP; *pi_fork_exec = \&PublicInbox::SpawnPP::pi_fork_exec @@ -370,11 +386,12 @@ sub spawn ($;$$) { my $rlim = []; foreach my $l (@RLIMITS) { my $v = $opt->{$l} // next; - my $r = eval "require BSD::Resource; BSD::Resource::$l();"; - unless (defined $r) { - warn "$l undefined by BSD::Resource: $@\n"; - next; - } + my $r = $RLIMITS{$l} // + eval "require BSD::Resource; BSD::Resource::$l();" // + do { + warn "$l undefined by BSD::Resource: $@\n"; + next; + }; push @$rlim, $r, @$v; } my $cd = $opt->{'-C'} // ''; # undef => NULL mapping doesn't work? diff --git a/t/spawn.t b/t/spawn.t index 48f541b8..344957af 100644 --- a/t/spawn.t +++ b/t/spawn.t @@ -260,4 +260,11 @@ SKIP: { is(readline($fh), "hihi\n", 'env+chdir SpawnPP under (faked) MOD_PERL'); } +my $rlimit_map = PublicInbox::Spawn->can('rlimit_map'); +diag $rlimit_map; +if ($rlimit_map) { + my %rlim = $rlimit_map->(); + diag explain(\%rlim); +} + done_testing();