This may sound trivial, but I'm pretty sure this question hasn't been asked, or at least I can't find it.
I'm looking for a way to construct an infinite wait (not necessarily a loop) with shell scripting so that it waits forever and can be killed (or technically, to receive a SIGTERM
). The following are known possible constructs and arguments against them:
while true; do sleep 1; done
This almost gets it, but since sleep
is an external command, when I send a SIGTERM
to the running script, it has to wait for the sleep
to finish first and then process the signal. Change sleep 1
to something like sleep 10
and the lag will be obvious. Also the solution wakes up the CPU every 1 second, which is not ideal.while true; do read; done
This is perfect when stdin
is tty. read
is a shell builtin and SIGTERM
arrives at the script instantly. But, when stdin
is /dev/null
, the script eats up all the CPU by helplessly running read
forever on /dev/null
.Thus a shell builtin construct that waits forever is required. Skimming through man dash
I didn't find such one - the only blocking builtins are read
and wait
, and I don't have idea how I can construct an ideal one using wait
.
The answer should be applicable to POSIX shell (effectively dash
), or less preferably, Bash.
Additional notes.
The situation where the first example doesn't work perfectly is more complex than I thought. With the following shell script:
#!/bin/sh echo $$ while true; do sleep 100 done
if you kill it at another tty, it terminates immediately. The funny thing begins when you attempt to do trapping. With this script:
#!/bin/sh at_term() { echo 'Terminated.' exit 0 } trap at_term TERM echo $$ while true; do sleep 20 done
What happens is exactly described in example 1. This happens with bash, dash and zsh. And it's under this condition that I'm seeking a "perfect" infinite look construct.
The following syntax is used for create infinite while loop in a shell script. echo "Press [CTRL+C] to exit this loop..." You can also Unix true command with while loop to run it endlessly. The while loop syntax with true command will look like below example.
To set an infinite while loop use: true command - do nothing, successfully (always returns exit code 0) false command - do nothing, unsuccessfully (always returns exit code 1) : command - no effect; the command does nothing (always returns exit code 0)
1) Syntax:Syntax of for loop using in and list of values is shown below. This for loop contains a number of variables in the list and will execute for each item in the list. For example, if there are 10 variables in the list, then loop will execute ten times and value will be stored in varname.
wait is an inbuilt command in the Linux shell. It waits for the process to change its state i.e. it waits for any running process to complete and returns the exit status. Syntax: wait [ID] Here, ID is a PID (Process Identifier) which is unique for each running process.
you can use a named pipe for your read:
mkfifo /tmp/mypipe #or mknode /tmp/mypipe p
if you later want to send different arbitrary "signals" to the pipe, the read can be use in combination with a case statement to take appropriate actions (even useful ones)
while read SIGNAL; do case "$SIGNAL" in *EXIT*)break;; *)echo "signal $SIGNAL is unsupported" >/dev/stderr;; esac done < /tmp/mypipe
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With