8

我有一个 Perl 脚本,它执行各种安装步骤来为我们公司设置一个开发框。它运行各种 shell 脚本,其中一些由于低于所需的 s (特别是在我的情况下ulimit的堆栈大小)而崩溃。-s

因此,我想设置一个ulimit适用于children从我的主要 Perl 脚本开始的所有脚本(子shell,它立即退出。

我知道我可以ulimit在运行 Perl 脚本或使用之前调用,/etc/security/limits.conf但我不希望用户知道这些 - 他们应该只知道如何运行脚本,这应该为他们处理所有这些。

我也可以在ulimit每次运行命令时运行,就像这样,ulimit -s BLA; ./cmd但我不想每次都重复这个,我觉得那里有一个更好、更清洁的解决方案。

另一个疯狂的“解决方法”是制作一个名为 BLA.sh 的包装脚本,该脚本将设置 ulimit 并调用 BLA.pl,但同样,我认为这是一个 hack,现在我有 2 个脚本(我什至可以制作 BLA.pl用“ulimit -s BLA; ./BLA.pl --foo”调用自己,并根据它是否看到 --foo 采取不同的行动,但这比以前更难了)。

最后,显然我可以安装 BSD::Resource 但我想避免使用外部依赖项。

那么从 Perl 脚本中设置 ulimit 并使其适用于所有子级的方法是什么?

谢谢你。

4

4 回答 4

12

您已经回答了您的问题:使用BSD::Resource

Perl 核心中没有任何与setrlimit. 如果您不能(或不会)使用标准方法,那么您必须使用 hack。您已经描述的任何方法都可以使用。(请注意,您可以创建一个子程序来添加ulimit -s BLA;到每个命令,然后使用该子程序而不是system.)

于 2010-02-09T03:14:41.507 回答
4

你总是可以将你的 perl 包装在一个小的 shell 脚本中:

#!/bin/sh -- # --*-Perl-*--
ulimit -n 2048
exec /usr/bin/perl -x -S $0 ${1+"$@"}
#!/usr/bin/perl
#line 6

use strict;

# etc, etc....

这很难看,而且很明显,脚本启动时间会稍微长一些。

于 2010-03-30T02:14:36.650 回答
4

这是一个如何在不使用 BSD::Resource 的情况下设置 cpu 限制的示例(但假设 perl 系统头文件在那里)。为了适应其他资源,做出明显的改变。

require 'syscall.ph';
require 'sys/resource.ph';

# set the soft cpu limit to 1 (second), and the hard limit to 10.
$rstruct = pack "L!L!",1,10; # L! means native long unsigned int.
syscall(&SYS_setrlimit,&RLIMIT_CPU,$rstruct);

这假设知道 rlim_t 实际上是无符号长的;我不知道是否有办法从 Perl 标头中提取此信息。

于 2011-11-25T17:06:38.520 回答
1

我最终在ulimit -s BLA需要它的命令之前添加了它。我特别不想使用 BSD::Resource,因为它不是默认的 Perl 包,并且在大约一半的现有开发机器上缺失。没有用户交互是特定要求。

于 2010-02-09T22:38:02.647 回答