Article 4820 of comp.lang.perl:
Xref: feenix.metronet.com comp.lang.perl:4820
Newsgroups: comp.lang.perl
Path: feenix.metronet.com!news.ecn.bgu.edu!usenet.ins.cwru.edu!magnus.acs.ohio-state.edu!math.ohio-state.edu!cs.utexas.edu!usc!elroy.jpl.nasa.gov!decwrl!news.kpc.com!kpc!chrnlgc!themis!mac
From: mac@rhea.chronologic.com (Michael T.Y. McNamara)
Subject: Re: perl's equiv of csh 'limit'?
In-Reply-To: lqiao@watdragon.uwaterloo.ca's message of Tue, 3 Aug 1993 16:07:02 GMT
Message-ID: <MAC.93Aug5145638@rhea.chronologic.com>
Sender: usenet@chronologic.com
Nntp-Posting-Host: rhea
Reply-To: mac@chronologic.com
Organization: Chronologic Simulation
References: <CB6y3r.5ot@watdragon.uwaterloo.ca>
Date: Thu, 5 Aug 1993 21:56:38 GMT
Lines: 86


>>>>> On Tue, 3 Aug 1993 16:07:02 GMT, lqiao@watdragon.uwaterloo.ca (Lee Qiao ~{GG@hT*~}) said:
> Is there a Perl equivalent of csh's 'limit' command 
> (or the 'vlimit' call in C)?  Currently I am using the
> following,
> open(STUFF, "/bin/csh -f -c 'limit cputime 150; <some process>|'");
> which seems a little inefficient to me.
> If you have any ideas please reply by e-mail.  Thank you!
	Did so, but for the rest of you:

Snipped out of my verilog compiler regression perl driver, which wants
to arrange so that children generate no corefiles, don't run into
"arbitrarily small" stack limits, and don't infinate loop:

To get a file handle from which you could read the output, you will
need to much about in the spawnntime to have the parent open a pipe
before the fork and have the child hook it's stdout to the write piece
of the pipe... Left as an exercise...


require 'syscall.ph';
require 'sys/resource.ph'; # note h2ph doesn't always win on this one
                           # -- hand editing may be necessary 

# Arrange so no core files are generated
$coresize = pack("i2",0,0);
syscall(&SYS_setrlimit, &RLIMIT_CORE, $coresize);

# Make stack size large
$stacksize = pack("i2",1024*1024*4,1024*1024*4);
syscall(&SYS_setrlimit, &RLIMIT_STACK, $stacksize);

...

foreach (test...)
    @cmpl_time = &spawnntime("$compile_cmd > $output 2>&1",3000);
    printf "cmpl: %.2f ",$cmpl_time[2];
	...
    @run_time = &spawnntime("$run_cmd > $output 2>&1",3000);
    printf "run: %.2f ",$run_time[2];

}

sub spawnntime {
    local($cmd,$limittime) = @_;
    local(@start,@end,@diff);
    @start = times;
  FORK: {
      if ($child_pid = fork ) {
	  waitpid($child_pid,0);	# Parent -  wait for child to finish
	  &report_err($cmd) if ( $? );
	  @end = times;
	  $diff[0] = $end[0] - $start[0];
	  $diff[1] = $end[1] - $start[1];
	  $diff[2] = $end[2] - $start[2];
	  $diff[3] = $end[3] - $start[3];
	  $child_pid = 0;
	  return @diff;

      } elsif (defined $child_pid) {
	# Child  -  run argument
	  if( $limittime) {
	      @so_far = times();
	      $timelimit = pack("i2", $limittime+$so_far[0], $limittime*2+$so_far[0]);
	      syscall(&SYS_setrlimit, &RLIMIT_CPU, $timelimit);
	  }
	  exec("$cmd");
	  &report_err($cmd) if ( $? );
	  exit;

      } elsif ( $! =~ /No more process/ ) {
	  # EAGAIN, presumably recoverable...
	  sleep 5;
	  redo FORK;
      } else {
	  die "Can not fork: $!\n";
      }
  }
}      


--
Michael T.Y. McNamara                          1+(415) 965-3312
,------.                                       1+(415) 965-2705 FAX
|CHRONO|LOGIC SIMULATION                       mac@chronologic.com
`------'       {yes, company has new logo..  *sigh*}


