Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl-Sensitive Sunglasses
 
PerlMonks  

perl scripts executor on Win32

by Courage (Parson)
on May 29, 2002 at 09:30 UTC ( #170010=snippet: print w/replies, xml ) Need Help??
Description: I've stole that simple idea from Borland JBuilder, and implemented it as a simple C program. Idea is following

This program searches for a file with same name as its name (but with .exe stripped) in current directory, then in 'modules' subdirectory, then in 'perl' subdirectory and calls perl to execute it if found.
If not found, then 'script-resolver.pl' is searched in a same way

This allows us to copy compiled executable as some name, and have convenient way to call that script.

This is similar to 'pl2bat' in spirit, but proved to be more comfortable to use in my practice, because script to be called is always up-to-date, and in 'pl2bat' case one should re-run pl2bat after some modifications are done. Compilable with at least with BC++ and MSVC++.

// a simple program which executes a perl script at
// one of following locations, whichever comes first:
//  modules/[name].pl
//  perl/[name].pl
//  ./[name].pl
//  modules/executor-resolver.pl
//  perl/executor-resolver.pl
//  ./executor-resolver.pl
//?  modules/[name]
//?  perl/[name]
//?  ./[name]

#include <windows.h>
#include <stdio.h>
#include <io.h>

#include "EXTERN.h"
#include "perl.h"

int main(int argc, char *argv[], char **env)
{
    char bufstr[2048];
    char fullpath[2048];
    char name[2048];
    char **xargv = (char**)malloc(sizeof(char*)*(argc+2));
    char *script[] = // how to search for script to run
    {
      "modules\\",
      "perl\\",
      "",
      0
    };
    char history[2048];
    int i=0, j, k, rc;
    bufstr[0]=0;
    strcpy(history,"tried:\n ");
    GetModuleFileName(NULL,fullpath,2048);
    j = strlen(fullpath);
    while (j && fullpath[j]!='\\')
      j--;
    j++;
    strcpy(name,fullpath+j);
    k = strlen(name);
    if (stricmp(name+k-4,".exe")==0) {
      //okay
      name[k-4] = 0;
    }
    else {
      MessageBox(0,name,"bad: not able to parse",0);
      return 1;
    }
    //MessageBox(0,name,"good:",0);
    fullpath[j] = 0;

    strcpy(bufstr,fullpath);
    // try with 'name' first
    for (k=0;script[k];k++) {
      strcpy(bufstr+j,script[k]);
      strcat(bufstr+j,name);
      strcat(bufstr+j,".pl");
      strcat(history,bufstr);
      strcat(history,"\n ");
#undef access
      if (!access(bufstr,0)) {
        //found it!
        goto found;
      }
    }

    // try with "executor-resolver.pl" at second set of tries
    for (k=0;script[k];k++) {
      strcpy(bufstr+j,script[k]);
      strcat(bufstr+j,"executor-resolver.pl");
      strcat(history,bufstr);
      strcat(history,"\n ");
#undef access
      if (!access(bufstr,0)) {
        //found it!
    //but here script name should be inserted
        xargv = (char**)malloc(sizeof(char*)*(argc+4));
        for (k=0; k<argc; k++)
          xargv[k+2] = argv[k];
        xargv[2] = name;
        xargv[1] = bufstr;
        xargv[0] = "perl";
        argc += 2;
        goto run;
      }
    }
    MessageBox(0,history,"Did not found.",0);
    return -1;
found:;
    //MessageBox(0,name,"!found!",0);
    xargv = (char**)malloc(sizeof(char*)*(argc+3));
    for (k=0; k<argc; k++)
      xargv[k+1] = argv[k];
    xargv[1] = bufstr;
    xargv[0] = "perl";
    argc += 1;
run:;
    rc = RunPerl(argc, xargv, env);
    free(xargv);
 
    return rc;
}
Replies are listed 'Best First'.
Re: perl scripts executor on Win32
by osfameron (Hermit) on May 29, 2002 at 10:15 UTC
    Hmmm, interesting, but I think that a C program is overkill (and it's no good to me as I don't have a C compiler...)
    Using just the Win32 console you could also just do SET pathext=%pathext%;.PL and put all the directories you want to be able to execute from in your PATH environment variable.

    Or you could use a simple batch file (this is just an example, very noddy, no error checking etc.etc.)

    @echo off echo %0 if exist %0.pl perl %0.pl else goto :modules goto :EOF :modules if exist modules\%0.pl perl modules\%0.pl else goto :perl goto :EOF :perl if exist perl\%0.pl perl perl\%0.pl else goto :perl goto :EOF
    If you saved this batch file as test.bat it would try to run test.pl in current, perl and modules directories, as per the C code above.

    Cheerio!
    Osfameron
    http://osfameron.perlmonk.org/chickenman/

      May be I tried not enough, I did not succeed doing properly using your way.

      I tried using ASSOC, ftype in a different ways, but succeeded much less than 100%, mostly because I was not able to teach system about STDIN/STDERR/STDOUT redirections. (because something is going fishy on Win32 platforms:)

      Additionally, in my case I am not OS-specific (I think win95 will behave differently in respect of 'ftype' and 'assoc'), but, most importantly, I now able to use my script everywhere in our room at work, I do not need to remember whether this is set up properly on user's systems.

      As one more argument, after I compiled that program using both console and windows mode (two executables, one of them GUI, one console), I am free to choose appropriate mode, just copy appropriate executable and all is done.
      via associations I associate with perl.exe or wperl.exe, but not some this way and some - another way.

      BTW C is not that bad, you'll benefit when using both Perl and C :)

      Good luck and best wishes to you!

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: snippet [id://170010]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others pondering the Monastery: (3)
As of 2021-10-26 02:31 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    My first memorable Perl project was:







    Results (90 votes). Check out past polls.

    Notices?