Run a time-constrained shell command [duplicate] - linux

This question already has answers here:
Command line command to auto-kill a command after a certain amount of time
(15 answers)
Closed 9 years ago.
I'm looking for the simplest way to run a command in a shell and kill it if it doesn't end in less than a second of CPU time. Something like:
$ deadline -- slow-foo
Started fooing...
[deadline] 1 sec deadline hit, killing and returning -1!
$ deadline -- quick-foo
Started fooing...
Finished fooing!
A linux-based solution is more than enough, but more portable ones are welcome.

Coreutils has a timeout utility that does just that, should be available on most Linux distributions:
timeout - run a command with a time limit
Has options for what signal to use and a few other things.

In addition of timeout(1) given in Mat's answer, and if you want to limit CPU time (not idle time or real time), you could use the setrlimit(2) syscall with RLIMIT_CPU (if the CPU time limit is exceeded, your process gets first a SIG_XCPU signal -which it could catch and handle-, and later a SIG_KILL -uncatchable- signal). This syscall is available in bash(1) with the ulimit builtin.
So to limit CPU time to 90 seconds (i.e. 1 minute and 30 seconds) type
ulimit -t 90
in your terminal (assuming your shell is bash; with zsh use limit cputime 90, etc...) - then all further commands are constrained by that limit
Read also the instructive time(7) and signal(7) man pages, and Advanced Linux Programming

This is quick and dirty and doesn't require any software packages to be installed, so is portable:
TIMEOUT=1
YOURPROGRAM & PID=$! ; (sleep $TIMEOUT && kill $PID 2> /dev/null & ) ; wait $PID

Related

How to kill a process after a given real running time in Bash?

For killing a process after a given timeout in Bash, there is a nice command called timeout. However, I'm running my program on a multi-user server, and I don't want the performance of my program to be influenced by others. Is there a way to kill a process in Bash, after a given time that the program is really running?
On Bash+Linux, you can use ulimit -t. Here's from help ulimit:
-t the maximum amount of cpu time in seconds
Here's an example:
$ time bash -c 'ulimit -t 5; while true; do true; done'
Killed
real 0m8.549s
user 0m4.983s
sys 0m0.008s
The infinite loop process was scheduled (i.e. actually ran) for a total of 5 seconds before it was killed. Due to other processes competing for the CPU at the same time, this took 8.5 seconds of wall time.
A command like sleep 3600 would never be killed, since it doesn't use any CPU time.

Briefly run / Restart sublime text from terminal

I don't want to run an external program (subl - sublime text) at a certain point of time, I want to run it for a certain amount of time. I basically need to boot up the program for 10 seconds then kill it - multiple times - because of its install and update process.
How can I do this?
You may have a timeout command on your system, which uses a standard alarm signal to terminate a process. I've never quite understood why no shell provides access to this feature as a builtin. If you don't have timeout on your system, you can simulate it with
my_program & pid=$!
sleep 10
kill "$pid"
Use timeout:
timeout 5s <program>
You can also specify the signal which need to be passed to terminating the process.
timeout -s9 5s <program>
(OR)
timeout --signal=KILL 5s <program>
Test:
$ time timeout 5s sleep 40
real 0m5.002s
user 0m0.001s
sys 0m0.001s
I ended up using this in my script
/usr/bin/subl
SPID="$(ps -A | grep sublime_text | awk '{print $1}')"
sleep 5
kill "$SPID"
unset "$SPID"

Bash script: CPU stress test while watching clock speed

I am totally new to this forum and also new to bash, so please bear with me :).
I would like to write a bash script to conduct a CPU stress test while observing the clock speed. Therefore, I have done the following:
1.) For the CPU stress test, I have created a script named "bernoulli" with the following code:
#!/bin/bash
# argument 1: n
function bernoulli()
{
if (( $1 < 3 ))
then
echo 1
else
echo $(( $(bernoulli $(( $1 - 1 ))) + $(bernoulli $(( $1 - 2 ))) ))
fi
}
bernoulli $1
2.) I have figured out that by using the "timeout" command I can kill a task after a specified time. For example,
timeout 30s ./bernoulli 35
starts a task calculating the 35th bernoulli number and the task is killed after 30 seconds.
3.) I also found out that by typing
timeout 30s watch grep \"cpu MHz\" /proc/cpuinfo
I can watch the clock speed of my cores (updated every 2 seconds) for 30 seconds (at which point "timeout 30s" kills this task).
What I want: I would like to do the above stress test and simultaneously observe the clock speed. In other words, I would somehow run the two commands
timeout 30s ./bernoulli 35
timeout 30s watch grep \"cpu MHz\" /proc/cpuinfo
"at the same time". I hope I could make it clear what I would like to achieve. Can anyone help with my issue? Thanks a lot for every comment!
How about
timeout 30s ./bernoulli 35 &
timeout 30s watch grep \"cpu MHz\" /proc/cpuinfo
& at the end will make command to run at background, so that second timeout will be executed almost instantly after the first one.
PS: this is rather poor way to test modern CPU. You will be exercising only single core and most likely only limited part of your CPU (no sse, etc). It is not trivial to write CPU benchmark, so you might want to use one of already available. For example, you can take a look at sysbench with something like sysbench --test=cpu --cpu-max-prime=20000 run.
You can run them in a dedicated shell:
timeout 30s bash -c './bernoulli 35 & watch grep \"cpu MHz\" /proc/cpuinfo'
Note that the single & is not a typo. It is not a logical and, it runs the bernoulli script in background.

Is it possible to set time out from bash script? [duplicate]

This question already has answers here:
How do I limit the running time of a BASH script
(5 answers)
Closed 7 years ago.
Sometimes my bash scripts are hanging and hold without clear reason
So they actually can hang for ever ( script process will run until I kill it )
Is it possible to combine in the bash script time out mechanism in order to exit from the program after for example ½ hour?
This Bash-only approach encapsulates all the timeout code inside your script by running a function as a background job to enforce the timeout:
#!/bin/bash
Timeout=1800 # 30 minutes
function timeout_monitor() {
sleep "$Timeout"
kill "$1"
}
# start the timeout monitor in
# background and pass the PID:
timeout_monitor "$$" &
Timeout_monitor_pid=$!
# <your script here>
# kill timeout monitor when terminating:
kill "$Timeout_monitor_pid"
Note that the function will be executed in a separate process. Therefore the PID of the monitored process ($$) must be passed. I left out the usual parameter checking for the sake of brevity.
If you have Gnu coreutils, you can use the timeout command:
timeout 1800s ./myscript
To check if the timeout occurred check the status code:
timeout 1800s ./myscript
if (($? == 124)); then
echo "./myscript timed out after 30 minutes" >>/path/to/logfile
exit 124
fi

Scons command with time limit

I want to limit the execution time of a program I am running under Linux. I put in my scons script a line like:
Command("com​","",​"ulimit -t 1; myprogram")
and tested it with an infinite loop program: it did not work and the program ran forever.
Am I missing something?
-- tsf
ulimit -t 1 means that the limit is set to 1 second of CPU time. If your infinite loop program uses any sort of sleep in its inner loop then it will use practically no CPU time. This means it will not get killed in 1 second of real, on the clock time. In fact it may take minutes or hours to use up its 1 second allocation.
What happens if you run the command outside of SCons? Perhaps you don't have permission to change the limit at all...
ulimit -t 1; ./myprogram
For example, it may say the following if the limit is already set to 0:
bash: ulimit: cpu time: cannot modify limit: Operation not permitted
Edit: it seems that the -t option is broken on Ubuntu 9.04. A fix has been committed 05 June 2009, but it may take a while to trickle into the updates - it may not be fixed until 9.10.
As an historical note, this problem no longer exists in Ubuntu 10.04.
You can also use this script:
(taken from http://newsgroups.derkeiler.com/Archive/Comp/comp.sys.mac.system/2005-12/msg00247.html)
#!/bin/sh
# timeout script
#
usage()
{
echo "usage: timeout seconds command args ..."
exit 1
}
[[ $# -lt 2 ]] && usage
seconds=$1; shift
timeout()
{
sleep $seconds
kill -9 $pid >/dev/null 2>/dev/null
}
eval "$#" &
pid=$!
timeout &
wait $pid
.

Resources