How do I sleep for a millisecond in bash or ksh
Solution 1
Bash has a "loadable" sleep which supports fractional seconds, and eliminates overheads of an external command:
$ cd bash-3.2.48/examples/loadables
$ make sleep && mv sleep sleep.so
$ enable -f sleep.so sleep
Then:
$ which sleep
/usr/bin/sleep
$ builtin sleep
sleep: usage: sleep seconds[.fraction]
$ time (for f in `seq 1 10`; do builtin sleep 0.1; done)
real 0m1.000s
user 0m0.004s
sys 0m0.004s
The downside is that the loadables may not be provided with your bash
binary, so you would need to compile them yourself as shown (though on Solaris it would not necessarily be as simple as above).
As of bash-4.4
(September 2016) all the loadables are now built and installed by default on platforms that support it, though they are built as separate shared-object files, and without a .so
suffix. Unless your distro/OS has done something creative (sadly RHEL/CentOS 8 build bash-4.4
with loadable extensions deliberately removed), you should be able to do instead:
[ -z "$BASH_LOADABLES_PATH" ] &&
BASH_LOADABLES_PATH=$(pkg-config bash --variable=loadablesdir 2>/dev/null)
enable -f sleep sleep
(The man page implies BASH_LOADABLES_PATH
is set automatically, I find this is not the case in the official distribution as of 4.4.12. If and when it is set correctly you need only enable -f filename commandname
as required.)
If that's not suitable, the next easiest thing to do is build or obtain sleep
from GNU coreutils, this supports the required feature. The POSIX sleep
command is minimal, older Solaris versions implemented only that. Solaris 11 sleep
does support fractional seconds.
As a last resort you could use perl
(or any other scripting that you have to hand) with the caveat that initialising the interpreter may be comparable to the intended sleep time:
$ perl -e "select(undef,undef,undef,0.1);"
$ echo "after 100" | tclsh
Solution 2
The documentation for the sleep
command from coreutils says:
Historical implementations of sleep have required that number be an integer, and only accepted a single argument without a suffix. However, GNU sleep accepts arbitrary floating point numbers. See Floating point.
Hence you can use sleep 0.1
, sleep 1.0e-1
and similar arguments.
Solution 3
Sleep accepts decimal numbers so you can break it down this like:
1/2 of a second
sleep 0.5
1/100 of a second
sleep 0.01
So for a millisecond you would want
sleep 0.001
Solution 4
Try this to determine accuracy:
time sleep 0.5 # 500 milliseconds (1/2 of a second)
time sleep 0.001 # 1 millisecond (1/1000 of a second)
time sleep 1.0 # 1 second (1000 milliseconds)
Combination of mr.spuratic's solution and coles's solution.
Solution 5
You may simply use usleep
. It takes microseconds (= 1e-6 seconds) as parameter, so to sleep 1 millisecond you would enter:
usleep 1000
Related videos on Youtube
yael
Updated on September 18, 2022Comments
-
yael over 1 year
sleep is a very popular command and we can start sleep from 1 second:
# wait one second please sleep 1
but what the alternative if I need to wait only 0.1 second or between 0.1 to 1 second ?
- remark: on linux or OS X
sleep 0.XXX
works fine , but on solarissleep 0.1
orsleep 0.01
- illegal syntax
-
Tom O'Connor over 11 yearsCan I ask why you want to sleep for 1ms?
-
yael over 11 yearsYes of course , in my bash script I add "sleep 1" , in some lines , but script run very slowly , so after some conclusion I calculate that sleep 0.1 also bring good results and more faster About the delay , I need delay in order to solve the ssh problem in my bash script , I perform paralel ssh login to some machines by expect and without delay its will not work , As you know from my question the delay should fit both Linux and Solaris
-
scai over 11 yearsWhatever solution you choose, keep in mind that a shell script won't be very accurate in terms of timing.
-
Tom O'Connor over 11 yearsHow about doing something that takes a very short time to execute, but does nothing.. like
echo "" >/dev/null
-
yael over 11 yearsGood idea but how msec this command take? , I need 0.1 msec , not less then that -:)
-
alanc over 11 yearsSupport for decimal arguments in Solaris sleep was added in Solaris 11. For older OS'es try installing GNU coreutils.
-
Perette over 7 yearsBeware! In macOS Sierra (at least the initial 10.12 release), ksh's built-in sleep does not work correctly for values ≤ 30. $ time sleep 5 real 0m0.00s user 0m0.00s sys 0m0.00s $ time sleep 30 real 0m0.00s user 0m0.00s sys 0m0.00s $ time sleep 31 real 0m31.01s user 0m0.00s sys 0m0.00s
-
Alexander Mills over 5 yearsthese solutions seem overly complex, is that not a simpler way to do this?
sleep -ms 50
?
- remark: on linux or OS X
-
yael over 11 yearssee my remark about SOLARIS OS
-
scai over 11 yearsDid you mix up is and isn't?
-
yael over 11 yearsfor example - I run on solaris 10 this: # sleep 0.1 sleep: bad character in argument , about linux sleep 0.1 works fine
-
mr.spuratic over 11 yearsAh, since you're using
expect
you can probably just use "after N
", where N is milliseconds, directly in your script. -
Mike Causer almost 10 yearsYou can also drop the leading zero before the decimal point. eg.
sleep .5
-
kevinarpe about 9 yearsNote: The built-in Bash command
sleep
is different from the external / separate binarysleep
, which is usually installed in/bin/sleep
or/usr/bin/sleep
. By default, Bash will use the built-in, so use"$(which sleep)"
to be very clear about using external binary. -
Ilan.K about 8 yearsuse
usleep
like @Luis Vazquez and @sebix write -
user over 7 yearsYou could at least change that bare
usleep()
call toif(argc == 1) { usleep(atoi(argv[1])); }
to avoid indexing outside of the bounds of the array, which can lead to any number of unexpected behaviors. -
Luis Vazquez almost 7 yearsNo, i mean
usleep
part of theinitscripts
package which is standard at least in all the Red Hat derived distributions; including at least RHEL, CentOS, Fedora, Mageia/Mandriva and SuSE. Here an example: `` `` -
Luis Vazquez almost 7 yearsHere is a sample ilustration running in CentOS 7: ``` $ which usleep /usr/bin/usleep $ rpm -qf /usr/bin/usleep initscripts-9.49.37-1.el7_3.1.x86_64 ``` To summarize: -
sleep
(from coreutils) works with seconds -usleep
(from initscripts) works with micro-seconds -
stark over 6 yearsExcept for mathforum.org/library/drmath/view/52352.html
-
Martin over 5 yearsTalk about everyone else overcomplicating it...
-
Alexander Mills over 5 years@MikeCauser leading zeros much more readable and signal intent to the reader of the code later. also better when you actually do math.
-
Déjà vu about 5 yearsAlso note that
usleep
unit is μs, so to wait 1 second, you need to provide a 1000000 argument. -
user about 5 years@RingØ Right. Stupid mistake, good catch.
-
Andrew Henle about 5 years
atoi()
is a horrible choice to convert a string to anint
. What doesatoi( "STRING" )
return?atoi()
has no way to return any error. -
roblogic over 4 yearsApple MacOS has BSD sleep, which also supports fractional seconds
-
Ray Foss over 2 yearsMy Debian/Ubuntu based NodeJs image in CodeSandbox has
sleep (GNU coreutils) 8.30
and supports this use of fractional seconds.