Beefy Boxes and Bandwidth Generously Provided by pair Networks
go ahead... be a heretic

running an executable from a cgi script

by Angharad (Pilgrim)
on Feb 09, 2006 at 16:08 UTC ( [id://529119]=perlquestion: print w/replies, xml ) Need Help??

Angharad has asked for the wisdom of the Perl Monks concerning the following question:

Hi there
I'm trying to write a cgi script that will run a executable file (securely, with any luck). The executable itself is a bit tricky, because it needs a file (which I have uploaded onto the server) .. but I can't feed the program the file from the command line, I can only give it the name of the file once the program is running .. so normally, if I run the program from the command line i have to use a pipe.
This is what I have come up with so far. Any suggestions much appreciated.
#!/usr/bin/perl use CGI; # eventually the text file will be sent to this excutable via the uplo +ad script $file = 'http://www.mywebpage/uploaded_files/file.txt'; # path to program my $prog = 'http://www.mywebpage/cgi-bin/executableprog'; my $q = new CGI; my $pid = open PIPE, "-|"; die "Cannot fork $!" unless defined $pid; unless($pid) { exec PROG or die "Cannot open pipe to executableprog: $!"; print PROG "$file\n"; close PROG; }
This code should result in a text file being created. I guess I have to determine where that will be placed on the server too? I have only just started playing with cgi and would appreciate any advice thrown my way. Thanks a lot.

Replies are listed 'Best First'.
Re: running an executable from a cgi script
by serf (Chaplain) on Feb 09, 2006 at 16:18 UTC
    Could you perhaps show us how you run it from the command line?

    This piece of code doesn't seem to do much yet (is it meant to be pseudo code?)

    Things to think about:

    • Are you trying to run the executable remotely from another machine via CGI? and also pick up the file from off the web? (because this is what your file starting with "http://" makes it look like. If you want to do that I'd probably look at something like LWP::Simple - which makes it very easy to slurp in a file off the web.

      (Or were you meaning to tell the CGI the path to a file sitting on the same server as itself? - which is what your question seems to indicate. If so you would only need to give it the local path to the file as far as the CGI program was concerned (or more securely the name of a file sitting in a predetermined directory on the server where the program *always* looked for its files.)

    • Your script starts off with use CGI; indicating that it is intended to be run as a CGI program itself - is that what you really mean? to run one CGI which calls another CGI? Perhaps you actually intend to run one CGI which executes a file locally (i.e. on the same server as the CGI script) instead? - if so, you wouldn't need to call it with "http://" - but would probably want to run it locally using open and a pipe like this:
    • # path to program my $prog = '/local/path/to/cgi-bin/executableprog'; open(PROG, "| $prog") || die "Can't run '$prog': $!\n"; print PROG "$file\n"; close(PROG);
    • Presumably where you have:
      my $pid = open PIPE, "-|";
      and then:
      exec PROG or die "Cannot open pipe to executableprog: $!";
      PIPE and PROG were meant to be talking about the same process?
    • What's the stuff for a fork for? you're probably better off not worrying about forking (which is a little complex) until you get the basics of reading and writing files and running programs mastered.
      Yes, PIPE and prog are meant to be talking about the same process. oh dear .. i have a lot to learn here.
      OK ... well eventually I would like this program to be run as a cgi itself yes. But I'm not going to be running another cgi from this script, its a C program. Everything is on the same server, so perhaps I could run them locally then.
      Thanks for the tips so far.
      As for how I would run the program on the command line normally .. well I would type in the name of the program to start .. and then a prompt comes up asking me for the text file to process.
Re: running an executable from a cgi script
by swkronenfeld (Hermit) on Feb 09, 2006 at 16:32 UTC
    I don't know how many other things that your executable asks for on standard input, but if it's only this one file name, the following command will do what you need.

    `echo "$file" | $prog`;

    You can get rid of that fork, pipe, and pid stuff.

    Update: Since I got downvoted, maybe I wasn't being clear enough here? I still think this is a valid answer to the OP's original question.

    If a script expects input (in this case, a file name), you can pipe the input into the script. Take the following script as an example:

    #!/usr/bin/perl -w use strict; my $in = <STDIN>; print $in; # END # Now test it > echo "Hello, world!" | ./ Hello, world! >

    I think this is what the OP is looking for instead of his opening on pipes, etc.
Re: running an executable from a cgi script
by Angharad (Pilgrim) on Feb 09, 2006 at 16:35 UTC
    Thanks for the comments so far. I'm slightly confused though because I thought that cgi was rather 'insecure' and that forking was a safer way of running a executable via cgi even if it is a simple one
      CGI is insecure if you use input from the user to pass into a program. For example:

      Insecure CGI example: print "Enter a command to execute:" my $command = <STDIN>; system($command); # BAD! User enters 'rm -fR *' !!!

      However, in your code above, you are not taking any input. You are simply executing a program and supplying it with a file. Based on your snippet, you would do this exact same thing at a command line. You aren't giving the user any choice of what to do.

      CGI can also be dangerous is you allow someone to job off processes on your machines, like you are doing above. Is this a heavy duty process? If a user bounces on the refresh button, can they start a whole lot of these jobs, and eat up system resources causing poor performance and possibly a crash? That's a problem too. Have you dealt with that in your script?
        OK ... I don't think the 'refresh' problem will arise.
        The steps will be as follows:
        A script that uploads the text file to a named directory on the server. This has already been written. This cgi script will then (hopefully) point to this script which will then call the external program.
        The results of the external program will come though as a text file also.

Log In?

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://529119]
Approved by Mutant
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others cooling their heels in the Monastery: (6)
As of 2024-05-30 16:10 GMT
Find Nodes?
    Voting Booth?

    No recent polls found