home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 18 REXX / 18-REXX.zip / rximc175.zip / main.c < prev    next >
Text File  |  2002-08-06  |  5KB  |  159 lines

  1. /* The main() function of REXX/imc             (C) Ian Collier 1994 */
  2.  
  3. #include<stdio.h>
  4. #include<stdlib.h>
  5. #include<unistd.h>
  6. #include<memory.h>
  7. #include<string.h>
  8. #include<signal.h>
  9. #include<setjmp.h>
  10. #include<sys/types.h>
  11. #include<sys/time.h>
  12. #include<sys/stat.h>
  13. #include<sys/file.h>
  14. #if defined(HAS_MALLOPT) && !defined(M_MXFAST) || defined(MALLOC_DEBUG)
  15. #include<malloc.h>
  16. #endif
  17. #include "const.h"
  18. #include "globals.h"
  19. #include "functions.h"
  20. #include "rexxsaa.h"
  21.  
  22. static RXSTRING arglist;       /* argument list to main program */
  23. static RXSTRING instore[2];    /* "instore" argument for RexxStart */
  24. static RXSTRING answer;
  25.  
  26. main(argc,argv)  /* This function gives an interface between the command */
  27. int argc;        /* line and the API function RexxStart(). */
  28. char *argv[];
  29. {
  30.    int c,l;
  31.    int optionx=0;     /* set if "-x" option present */
  32.    int minus=0;       /* set if "-" present (take from stdin) */
  33.    int opt;           /* argument counter */
  34.    unsigned arglen;   /* amount of space allocated to arg string */
  35.    unsigned argtot=0; /* length of arg string so far */
  36.    char *input=0;     /* The source code from disk or wherever */
  37.    int ilen;          /* The length of the source code */
  38.    int callflags=RXMAIN; /* Flags to pass to RexxStartProgram */
  39.    char *args;
  40.    char *name=0;
  41.    short rc;
  42.    RXSTRING *progrm;
  43.    jmp_buf exbuf;
  44.  
  45. #ifdef MALLOC_DEBUG
  46.    malloc_debug(2);
  47. #endif
  48. #if defined(HAS_MALLOPT) && defined(M_MXFAST)
  49.    mallopt(M_MXFAST,1024);
  50. #endif
  51.  
  52. #ifdef STUFF_STACK
  53.    callflags|=RXSTUFF;
  54. #endif
  55.  
  56.    exitbuf=addressof(exbuf);
  57.    if(setjmp(*exitbuf))exit(1); /* catch error during arg interpretation */
  58.  
  59. /* Argument processing */
  60.    /* Flags are all arguments starting with "-" until a "-x" or "-" found */
  61.    traceout=stderr;
  62.    for(opt=1;!optionx && !minus && opt<argc && argv[opt][0]=='-';opt++)
  63.       if(!setoption(argv[opt]+1,strlen(argv[opt]+1)))
  64.          switch(argv[opt][1]&0xdf){
  65.          case 'X':
  66.             optionx=1; break;
  67.          case 0:
  68.             minus=1; break;
  69.          case 'C':
  70.          case 'S':
  71.             if(++opt==argc)
  72.                errordata=": no program supplied",die(Einit);
  73.             input=allocm(ilen=1+strlen(argv[opt]));
  74.             memcpy(input,argv[opt],ilen);
  75.             input[ilen-1]='\n';
  76.             break;
  77.          case 'T':
  78.             if(!argv[opt][2])
  79.                if(++opt==argc)die(Etrace);
  80.                else settrace(argv[opt]);
  81.             else settrace(argv[opt]+2);
  82.             break;
  83.          case 'I':
  84.             input=allocm(32);
  85.             strcpy(input,"do forever;nop;end\n");
  86.             ilen=strlen(input);
  87.             name="<trace>";
  88.             settrace("?a");
  89.             break;
  90.          case 'V':              /* "rexx -v" prints version and exits */
  91.             callflags|=RXVERSION;/* but "rexx -v something" prints version */
  92.             if(argc==2)         /* and behaves like "rexx something". */
  93.                callflags=RXVERSION;
  94.             break;
  95.          default:
  96.             workptr=allocm(worklen=32+strlen(argv[opt]));
  97.             sprintf(workptr,": invalid option '%s'",argv[opt]);
  98.             errordata=workptr;
  99.             die(Einit);
  100.       }
  101.    if(opt==argc || input)
  102.       minus=1; /* minus==0 if and only if there is a program name */
  103.    /* get argument list in string form */
  104.    /* estimate length and get mem for arg list */
  105.    for(arglen=0,c=opt+!minus;c<argc;++c)arglen+=strlen(argv[c])+1;
  106.    if(arglen)args=allocm(arglen);
  107.    else args=0;     /* this makes arg()=0. */
  108.    /* form list by concatenating all the arguments separated by spaces */
  109.    for(c=opt+!minus;c<argc;++c){
  110.       l=strlen(argv[c]);
  111.       memcpy(args+argtot,argv[c],l);
  112.       argtot+=l;
  113.       if(c<argc-1)args[argtot++]=' ';
  114.    }
  115.    if(input){
  116.       optionx=0;
  117.       if(!name)name="string";
  118.    }
  119.    else if(minus && callflags!=RXVERSION){
  120.       name="<stdin>";
  121.       input=allocm(ilen=256);
  122.       l=0;
  123.       while(1){
  124.          l+=fread(input+l,1,256,stdin);
  125.          if(feof(stdin))break;
  126.          else mtest(input,ilen,l+256,256);
  127.       }
  128.       if(!l || input[l-1]!='\n')input[l++]='\n';
  129.       input=realloc(input,ilen=l);
  130.       if(ttyout=fopen("/dev/tty","w"))
  131.          fputs("  \b\b",ttyout),
  132.          fclose(ttyout);
  133.    }
  134.    else name=argv[opt];
  135.    if(optionx)callflags|=RXOPTIONX;
  136. /* call the interpreter */
  137.    arglist.strptr=args;             /* there is one argument - "args" */
  138.    arglist.strlength=argtot;
  139.    if(input){
  140.       progrm=instore;
  141.       instore[0].strptr=input;
  142.       instore[0].strlength=ilen;
  143.       instore[1].strptr=0;
  144.       instore[1].strlength=0;
  145.    }
  146.    else progrm=0;
  147.    l=RexxStartProgram(argv[0],args!=0,&arglist,name,(char*)0,
  148.           progrm,"UNIX",RXCOMMAND,callflags,(PRXSYSEXIT)0,&rc,&answer);
  149.    if(l)exit(-l);
  150.    if(rc!=(short)(1<<15))exit(rc);
  151.    if(!answer.strptr)exit(0);
  152. /* Error has already been raised.  This code is not reached.
  153.    fputs("REXX: exit value of '",stderr);
  154.    for(l=0;l<answer.strlength;l++)putc(answer.strptr[l],stderr);
  155.    fputs("' is an invalid return code.\n",stderr);
  156. */
  157.    exit(1); /*NOTREACHED*/
  158. }
  159.