Description: Consistantly writing programs that either act as daemons or take a long time to run depending on the input, I find it necessary to track weather or not they are still running. Lots of programs do this and its generally called state or status tracking. One of the most common ways to do this is to use a pid file.
The most common method is to create a file with the naming scheme program_name.pid. The contents of the file is the pid of the program. Then at the conclusion of the program, the file is removed. The pid file is generally stored in the OS’s state directory (in linux). Generally being a Debian or Ubuntu, the state information is stored in the /var/run/ directory. I also frequently use EnGarde Secure Linux which also has a state directory of /var/run/.
CPAN: File::Pid
Note: In the spirit of TIMTOWTDI, the process itself isn’t overly complex. To illustrate that, I will show one method of accomplishing this goal without using a Perl module. I will also be using the Perl special variable $$. To quote the Perl Special Variables page:
$PROCESS_ID $PID $$ The process number of the Perl running this script. You should consider this variable read-only, although it will be altered across fork() calls. (Mnemonic: same as shells.)
Note for Linux users: on Linux, the C functions getpid and getppid() return different values from different threads. In order to be portable, this behavior is not reflected by $$, whose value remains consistent across threads. If you want to call the underlying getpid, you may use the CPAN module Linux::Pid.
As you will likely note, although potentially less portable across OS’s, using File::Pid is much cleaner and easier.
# Declare your variables my $pid_file = "/var/run/myprog.pid"; local *PIDFILE; # Check for the PID file's existance if (-e $pid_file) { die ("Program already running or ended prematurely\\n"); } # Create the PID file # Use the 3 argument form of open for safety open PIDFILE, ">", $pid_file; print PIDFILE "$$\\n"; close PIDFILE; # XXX - Program here # Remove PID file unlink $pid_file or die "Error unlinking $pid_file: $!";
Example 1:
Using the basic example of just creating the PID file, checking if the program is already running, and removing the PID file, let’s take a look at the OO (Object Oriented) example:
# Always be safe & strict use strict; use warnings; # Use the module use File::Pid; # Create the PID object # Ensure you put a name that won't clobber # another program's PID file my $PID = File::Pid->new({ file => '/var/run/myprog.pid', }); # Write the PID file $PID->write; # Check for the previous instance # and die if PID file already exists if (my $oldPID = $PID->running()) { die "myprog already running: $oldPID\n"; } # XXX - Program here # Remove the PID file $PID->remove;