bi-directional fifo help

B

BrettNem

Hi All,
I need some help with a fifo. Basically I'm trying to write a daemon
process that will sit on a fifo, looking for input data.. when it gets
the data, it processes it and returns a response (as STDOUT from
whoever manipulated the FIFO).

Essentially, I could use something like echo to test it like:
echo "Hello World" > /tmp/signalfifo
and it would reply with whatever I gave it:
Hello World

But I can't for the life of me figure out how to get the fifo to reply.
I'm using a code snippit I found in the group someitme last year:
http://groups-beta.google.com/group...13?q=signalfifo&rnum=1&hl=en#c61f5e5e1b56d613

I'm providing the code below for reference.. I added a print to the
fifo thought it might be as easy as that (nope).

btw, I tried the below with syswrite as well.

Any ideas??

Thanks,
Brett

#!/usr/bin/perl -Tw
#
# Example of using a named pipe and 4-way signal()
# to both manage a periodic task and an asynchronous
# task.
#

use strict;

# Parameters
my $interval=10; # seconds
my $signal_fifo="/tmp/signalfifo" ; # create with "mkfifo
/path/to/fifo"

# Verify the named pipe
if (!(-p $signal_fifo && -w _ && -r _))
{
print STDERR "Problem with fifo $signal_fifo!\n";
exit(1);
}
# Open the fifo read/write, not just read. This is necessary because
# of the POSIX rules about using select() on named pipes when no
writers
# are present


#open(FIFOFH,"+<",$signal_fifo) || die $!;
open(FIFOFH,"+<",$signal_fifo) || die $!;
# Now go into a select()-loop on the fifo.
my $rin='';
my $rout='';
vec($rin,fileno(FIFOFH),1)=1;
while(1)
{
my $nfound=select($rout=$rin,undef,undef,$interval);

# We got to this point because the blocking select()
# returned. It happened because 1) data came into the
# fifo, or 2) the timeout occurred.

# print "===== select() returned at ",scalar(localtime),"\n";

if($nfound) # data is in the fifo
{
# Completely drain the fifo, since we don't really
# care what the message is -- only that it exists.
print "fifo contains this data:\n";
my $fifodata;
while(select($rout=$rin,undef, undef,0)) # non-blocking select
{
sysread FIFOFH,$fifodata,1024;
print FIFOFH "$fifodata\n";
}
}

# For safety, just go ahead and perform the periodic and the
# async task any time we get here. A particular application
# may want to alter this strategy.
periodic_task();
async_task();

}

# Infinite loop above... we'll never get here.
# Something that needs to be done at least every n minutes
sub periodic_task
{
# print "Periodic task...\n";
return;

}

# Something to do only when signalled
sub async_task
{
# print "Asynchronous task...\n";
return;
}
 
B

Brian McCauley

BrettNem said:
I need some help with a fifo. Basically I'm trying to write a daemon
process that will sit on a fifo, looking for input data.. when it gets
the data, it processes it and returns a response (as STDOUT from
whoever manipulated the FIFO).

What do you mean by that? I suspect that you've got the wrong mental
model of what a FIFO is. This has nothing to do with Perl.
Essentially, I could use something like echo to test it like:
echo "Hello World" > /tmp/signalfifo

Note here the STDOUT of the echo command is the FIFO. The process at
the other end of the FIFO can know nothing about the session in which
echo is executing.
and it would reply with whatever I gave it:
Hello World

But I can't for the life of me figure out how to get the fifo to reply.

A FIFO cannot "reply".

You probably want a filter process...

echo "Hello World" | myfilter

The filter process could connect to a daemon using a socket.
 
B

BrettNem

Ok, so perhaps a FIFO isn't what I want??

What I want is a persistant DB connection on the daemon that always
runs.. Then I was to somehow (pipe, FIFO, ??) get data into the daemon
and it will give me a reply.. However the daemon needs to continuously
be running and be capable of serving multiple simultanious request..

Part of what I'm trying to do here is to take a funciton that requires
very fast database lookups that doesn't support the db query natively
(can execute an external script and use result data) and I'm trying to
eliminate the delay you get from connecting and disconnectiing to the
DB.. However I might just be replacing it with delay connecting and
disconnecting the socket..

As a side note, my daemon also caches the DB data and checks to see if
a local cache is available before it performs the query.. So all that
being said, the daemon needs to keep running and I need to throw data
at it.

Any ideas?
Thanks!
-Brett
 
J

Joe Smith

BrettNem said:
What I want is a persistant DB connection on the daemon that always
runs.. Then I was to somehow (pipe, FIFO, ??) get data into the daemon
and it will give me a reply.. However the daemon needs to continuously
be running and be capable of serving multiple simultanious request..

What you're describing is conceptually the same as a web server.

1) Daemon opens a socket and listens for incoming connections.
2) Daemon receives incoming connection.
3) Daemon either forks (for simultaneous requests) or handles
the request itself (serialized requests).
4) Client sends request all at once.
5) Daemon reads the request, performs some work, sends single response.
6) Both daemon and client disconnect.
7) Daemon loops back to step 2.

If you can make your daemon operate under mod_perl, then you could
use Apache to implement the framework.
-Joe
 

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

Forum statistics

Threads
473,770
Messages
2,569,586
Members
45,089
Latest member
Ketologenic

Latest Threads

Top