Thursday, January 15, 2015

How to prevent starting another bash script copy?

Usually pidfile is used in order to check if bash script has been already started. If pidfile exists and its content is valid then it means that script has been already started and its second instance exits. If pidfile doesn't exist or it stores invalid PID file it means that script is stopped, so script instance continue to run. Looks like nothing complex, but there is one pitfall. 

If script has been started simultaneously (for example: ./script& ./script&) race condition can happen: both scripts will check that pidfile doesn't exist and then write its PID values to the pidfile. As the result, only last PID value will be stored in the pidfile and both instance will continue to run.

In order to prevent race condition file should be created atomically. 
Below is the example how to do it.


set -C - enable preventing redirection to already existing files;
set +C - disable preventing redirection to already existing files;

You also can notice that echo $$ > $g_sPathToPidFile is surrounded by brackets {}.
It is not the coincidence, these brackets prevent script from printing error "cannot overwrite existing file" to stdout in case if pidfile has been already created.

Pay attention I've tested set -C command behavior only for /bin/bash interpreter.

No comments:

Post a Comment