Finding Background processes?

P

pankaj_wolfhunter

Greetings,
I want to check whether a particular script (say
test.txt) is already running in background or not?
If it exists then I want to exit the code else proceed further.

I am new to perl and have done this in shell scripting but not able to
find the equivalent in perl

-- unix shell script
if [[ `ps -ef | grep $script_name | grep -vcE "grep|vi|cat|more|tail|
head" ` > 1 ]]; then
echo " $script_name script is currently running on `hostname`"
exit
fi

Any help would be appreciated?

TIA
 
B

Brian McCauley

Greetings,
I want to check whether a particular script (say
test.txt) is already running in background or not?
If it exists then I want to exit the code else proceed further.

I am new to perl and have done this in shell scripting but not able to
find the equivalent in perl

-- unix shell script
if [[ `ps -ef | grep $script_name | grep -vcE "grep|vi|cat|more|tail|
head" ` > 1 ]]; then
echo " $script_name script is currently running on `hostname`"
exit
fi

You can similarly parse the STDOUT /bin/ps executed with argument '-
ef' using Perl just as you do above in shell script.

if ( grep { /$script_name/ && !/grep|vi|cat|more|tail|head/ } `ps -
ef` )

Alternatively you could look on CPAN for a Perl module with similar
semantics to /bin/ps (Proc::processTable).

Be aware, of course, that the approach you have above is somewhat
prone to false readings.

I'd recommend you use some sort of resource lock to prevent multiple
instances of a program.
 
G

gf

Greetings,
I want to check whether a particular script (say
test.txt) is already running in background or not?
If it exists then I want to exit the code else proceed further.

Well, besides checking ps, you could do what a lot of apps do.

Define a flag file in your app's default directory.
Check to see if the file exists. Die if it does with a message saying
why you're dying.

If it doesn't exist then open the file and write the $$ variable to it
and continue on your way.
Delete the file when your app quits.

Something like this untested code.

#!/usr/bin/perl

use warnings;
use strict;

my $PID_FLAG = './_running_pid';
( -f $PID_FLAG ) and die "Another instance is running.\n";
open (my $pid_flag_file, '>', $PID_FLAG) or die "Can't create
$PID_FLAG ($!)\n";
print $pid_flag_file $$;
close $pid_flag_file;

# do stuff

END {
unlink $PID_FLAG;
}

I put the unlink in an END{} block so there's a pretty good chance the
file will be removed automatically as the app exists.

This sort of approach is nice because the flag file contains the
process ID of the last running instance of the app. If something is
weird, like the app is run away or a zombie, you can cat the file and
know which ID to look for or to kill. After killing it, or if the app
won't launch correctly, then you kill the flag file and you're good
for another launch. And/or, if you want to keep your app from
launching, say because it's on a cron and it'd be a pain to kill the
cron entry, then touch the flag file to temporarily disable the run of
the app. You'll get the normal die message as a reminder the app is
trying to do its job.
 
J

Jamie

In said:
Greetings,
I want to check whether a particular script (say
test.txt) is already running in background or not?
If it exists then I want to exit the code else proceed further.

I am new to perl and have done this in shell scripting but not able to
find the equivalent in perl

-- unix shell script
if [[ `ps -ef | grep $script_name | grep -vcE "grep|vi|cat|more|tail|
head" ` > 1 ]]; then
echo " $script_name script is currently running on `hostname`"
exit
fi

Depends on the platform, my personal favorite is to create a broken
symlink containing the process ID, something like this:

If you know the process ID, you can use kill() to determine if it's running.

If you use "ps | grep" you'll run the risk of accidently killing a process with
the same name.


# ------------- lock_process --------------------
#
# Attempt to create a symlink, will fail if such a symlink already exists.
# we use this failure.
#

while(! symlink($$,$FLAG)){
my $pid = readlink($FLAG);
#
# This is the "guts" of it, kill with a signal of 0 only reports
# whether or not a given process ID exists.
#
if(! kill(0,$pid)){
warn "Stale PID $pid";
unlink($FLAG); # There is a slight race condition here, however,
} # We should normally never be here anyway.
sleep(1); # Pause, count how many loops for a timeout, etc..
}

#
# At the end of our script, we need to do this. However, a kill -9 will blow us
# away and we'll end up with a stale lockfile. The above code (with the race condition..)
# is an attempt at recovering from a former "blown away" process.
#
END {
unlink($FLAG);
}
#------------------------------------------------

I don't know why I perfer to cram the info into a symlink, guess it's a habit. Most
people seem to use pid files. Far as I know, both are equally valid methods, symlinks
aren't portable though. You do need something that is "atomic" for the flag creation,
open(FH,">pidfile") is not a good choice since it'll happily clobber a brother who
managed to squeak in on a time slice.

Also, if this is to run on multiple machines (shared filesystem) there is a chance
that kill won't work. In that situation, you should put the current hostname into
the link and match it against the host that's trying to clear the lockfile.


Jamie
 
M

Martijn Lievaart

On Sat, 24 Feb 2007 12:40:31 +0000, Jamie wrote:

(snip)

Nice.
I don't know why I perfer to cram the info into a symlink, guess it's a
habit. Most people seem to use pid files. Far as I know, both are
equally valid methods, symlinks aren't portable though. You do need
something that is "atomic" for the flag creation, open(FH,">pidfile") is
not a good choice since it'll happily clobber a brother who managed to
squeak in on a time slice.

Well, a file can be flock()ed so the race can be avoided.

M4
 
D

Daniel Pfeiffer

la 24.02.2007 13:40 Jamie skribis:
Depends on the platform, my personal favorite is to create a broken
symlink containing the process ID, something like this:

while(! symlink($$,$FLAG)){

I don't know why I perfer to cram the info into a symlink, guess it's a habit. Most
people seem to use pid files. Far as I know, both are equally valid methods, symlinks
aren't portable though. You do need something that is "atomic" for the flag creation,
open(FH,">pidfile") is not a good choice since it'll happily clobber a brother who
managed to squeak in on a time slice.

I also prefer symlinks for pids. They're much less of a hassle than
open/flock/print/close and I can see them instantly with ls.

best regards
Daniel
 
J

Jamie

In said:
la 24.02.2007 13:40 Jamie skribis:


I also prefer symlinks for pids. They're much less of a hassle than
open/flock/print/close and I can see them instantly with ls.

I recall Matt Dillon from DragonFlyBSD claiming that, if you open a lock file with
the O_CREAT option, you don't need to lock it. (the subject at hand was NFS
and locking) But, I still like to use a symlink. :)

flock, even with perl, does not work when flocking NFS filesystems between linux
and dragonflybsd. (this took me by surprise, I had thought perl's flock implementation
had "magic" to get around this, it didn't when I tried it.)

Jamie
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,743
Messages
2,569,478
Members
44,898
Latest member
BlairH7607

Latest Threads

Top