home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 18 REXX / 18-REXX.zip / rdx200.zip / RDX.CMD next >
OS/2 REXX Batch file  |  1994-01-19  |  23KB  |  678 lines

  1. /*************************************************************************
  2.  RDX V2.00 (C) 1994 James Brombergs
  3.  
  4.    RDX /L
  5.         Edit lookup table
  6.  
  7.    RDX [/+] [/B] [/T] [[-]drivelist:]dirname
  8.  
  9.         /+ = Include drives A: and B: in search (excluded by default)
  10.         /B = Accept first matching directory without prompting
  11.         /T = Search lookup table only
  12.  
  13.         drivelist = drives to search
  14.             *: search all drives starting at C:
  15.           ddd: search only drives ddd
  16.          -ddd: search all drives except ddd, starting at C:
  17.  
  18.         dirname = directory name (with optional wildcards) to search for
  19.  
  20.    <SPACE> continue search
  21.    <ESC>   cancel search, revert to original directory
  22.    any other key to accept directory
  23.  *************************************************************************/
  24. /* The text above is displayed as the help screen */
  25.  
  26. '@ECHO OFF'
  27. SAY "RDX v2.00"
  28. SAY
  29.  
  30. /* -----------------------------------------------------------------------
  31.    Load REXXUTIL
  32.    ----------------------------------------------------------------------- */
  33. IF( RxFuncQuery( "SysLoadFuncs" ) <> 0 ) THEN
  34.      IF( RxFuncAdd( "SysLoadFuncs", "RexxUtil", "SysLoadFuncs" ) <>0 ) THEN
  35.           CALL Error "Unable to load REXX Utility functions.";
  36. CALL SysLoadFuncs
  37.  
  38. /* -----------------------------------------------------------------------
  39.    Set exception handlers
  40.    ----------------------------------------------------------------------- */
  41. SIGNAL ON FAILURE NAME Terminate
  42. SIGNAL ON HALT NAME Terminate
  43. SIGNAL ON SYNTAX NAME SyntaxTrap
  44. SIGNAL ON ERROR NAME ErrorTrap
  45. SIGNAL ON NOVALUE NAME NoValueTrap
  46.  
  47. /* -----------------------------------------------------------------------
  48.    Lookup Table
  49.    Entries are of form eg
  50.     lookUp.1.key = "WIN"
  51.     lookUp.1.dir = "E:\OS2\MDOS\WINOS2"
  52.     lookUp.0 contains the number of entries in the table and is put at the 
  53.              end of the table.
  54.  
  55.    Use quotation marks around key and dir entries. 
  56.    Entries are not case-sensitive
  57.    ----------------------------------------------------------------------- */
  58. /* !!! DO NOT CHANGE THE NEXT LINE !!! */
  59. /*LOOKUP*/
  60. lookUp.0 = 0
  61. /*ENDLOOKUP*/
  62. /* !!! DO NOT CHANGE THE LAST LINE EITHER !!! */
  63.  
  64. /* -----------------------------------------------------------------------
  65.    save environment to allow restoring cwd in case of errors
  66.    ----------------------------------------------------------------------- */
  67. n = SETLOCAL();           
  68.  
  69. /* -----------------------------------------------------------------------
  70.    check command line arguments
  71.    ----------------------------------------------------------------------- */
  72. ARG arg.1 arg.2 arg.3 arg.4 .
  73.  
  74. IF( arg.1 = "" ) THEN SIGNAL Help;
  75. IF( arg.1 = "/L" ) THEN DO
  76.     CALL EditLookupTable;
  77.     EXIT;
  78. END
  79.  
  80. searchParam = ""; /* set to string containing <drivelist>:<dirname> if found */
  81. acceptFirst = 0;  /* set to 1 if /B switch found */
  82. includeAB = 0;    /* set to 1 if /+ switch found */
  83. lookupOnly = 0;   /* set to 1 if /Q switch found */
  84.  
  85. DO i = 1 TO 4
  86.     SELECT
  87.         WHEN( arg.i = "" ) THEN NOP;
  88.         WHEN( ( arg.i = "/?" ) | ( arg.i = "/H" ) ) THEN SIGNAL Help;
  89.         WHEN( arg.i = "/B" ) THEN acceptFirst = 1;
  90.         WHEN( arg.i = "/+" ) THEN includeAB = 1;
  91.         WHEN( arg.i = "/T" ) THEN lookupOnly = 1;
  92.         OTHERWISE IF( searchParam = "" ) THEN searchParam = arg.i;
  93.     END
  94. END
  95. DROP i
  96.  
  97. IF( searchParam = "" ) THEN SIGNAL Help; /* no target specified */
  98.  
  99. /* -----------------------------------------------------------------------
  100.    Main procedure                                           
  101.    ----------------------------------------------------------------------- */
  102. PARSE UPPER VAR searchParam drivelist ":" pathTemplate .
  103.  
  104. IF( pathTemplate = "" ) THEN DO  /* if there wasn't a colon we have */
  105.     pathTemplate = drivelist;    /* to swap the variables and */
  106.     drivelist = "";              /* just search current drive */
  107. END
  108. ELSE
  109.     drivelist = MakeDriveList( drivelist, includeAB );
  110.  
  111. DROP searchParam
  112.  
  113. /* search the lookup table first */
  114. newPath  = SearchIt( "LOOKUP", pathTemplate, (acceptFirst*2) );
  115.  
  116. IF( ( newPath = 0 ) & ( lookupOnly = 0 ) ) THEN DO
  117.     /* check for illegal chars, note * and ? are legal as wildcards */
  118.     IF( VERIFY( pathTemplate, '/\":|', "MATCH" ) \= 0 ) THEN 
  119.         CALL Error( "Invalid path" );
  120.  
  121.     /* add wildcard, no problem if theres already one so dont need to check */
  122.     pathTemplate = pathTemplate || '*';
  123.     numDrives = LENGTH( driveList );
  124.  
  125.     IF( numDrives = 0 ) THEN DO     /* search current drive only */
  126.         newPath = SearchIt( "CURRENT", pathTemplate, (acceptFirst+1) );
  127.     END
  128.     ELSE DO
  129.         flag = acceptFirst * 2;
  130.  
  131.         DO i = 1 TO numDrives
  132.             IF( flag = 0 ) THEN flag = ( i = numDrives );
  133.             newPath = SearchIt( SUBSTR( driveList, i, 1 ), pathTemplate, flag );
  134.             IF( newPath \= 0 ) THEN LEAVE;
  135.         END
  136.  
  137.     END
  138.  
  139. END
  140.  
  141. /* restore environment before changing path or original directory will be 
  142.    restored on termination */
  143. n = ENDLOCAL();
  144.  
  145. IF( newPath \= 0 ) THEN 
  146.     IF( DIRECTORY( newPath ) \= newPath ) THEN
  147.         SAY "Cannot locate the directory " newPath;
  148.  
  149. DROP driveList numDrives newPath pathTemplate
  150. EXIT
  151.  
  152. /* ----------------------------------------------------------------------------------- 
  153.    MakeDriveList
  154.     Puts letters of drives to search in a string, and returns the string. Drives not 
  155.     recognised by the system or not responding (eg empty floppy drives) are ignored. 
  156.     If <addAB> is 1 and <drvlist> is * or -ddd then drives A: and B: are added to the 
  157.     list.
  158.    <drvlist> = drive list from command line, one or more letters, no spaces.
  159.     If * or - are given, they must be the first character.
  160.    ----------------------------------------------------------------------- */
  161. MakeDriveList: PROCEDURE
  162. ARG drvlist, addAB
  163.  
  164. if( drvlist = "" ) THEN RETURN drvlist;
  165.  
  166. firstchar = SUBSTR( drvlist, 1, 1 );
  167.  
  168. /* get drives recognised by system */
  169. if( firstchar = '*' | firstchar = '-' ) THEN 
  170.     IF( addAB = 1 ) THEN
  171.         /* include A: and B: according to command line option */
  172.         drvmap = SysDriveMap( "A:" );   
  173.     ELSE
  174.         /* omit A: and B: by default when searching multiple drives */
  175.         drvmap = SysDriveMap();         
  176. ELSE
  177.     drvmap = SysDriveMap( "A:", "USED" );
  178.  
  179. maplen = LENGTH( drvmap );
  180.  
  181. validlist = "";  /* string to put valid drive letters in */
  182. pchar = 1;       /* pointer to drive letter in drvmap */
  183.  
  184. DO WHILE( pchar < maplen )
  185.     drvletter = SUBSTR( drvmap, pchar, 1 );  /* get the drive letter */
  186.     pchar = pchar + 3;                       /* point to next drvmap entry */
  187.  
  188.     IF( firstchar = '-' ) THEN DO            /* ignoring listed drives */
  189.         IF( POS( drvletter, drvlist ) \= 0  ) THEN 
  190.             ITERATE;                         /* skip it if its on list */
  191.     END
  192.     ELSE                                     /* searching listed drives only */
  193.         IF( ( firstchar \= '*' ) & ( POS( drvletter, drvlist ) = 0 ) ) THEN 
  194.             ITERATE;                         /* skip if its not on list */
  195.  
  196.     /* check that drive is responding by trying to open a file called "*" in root directory
  197.        NOTREADY:2 means file not found as we would expect, anything else would indicate
  198.        a hard fail eg CD-ROM or floppy drive with no disk, etc */
  199.     IF( STREAM( drvletter || ":*", 'C', "OPEN" ) \= "NOTREADY:2" ) THEN ITERATE;
  200.  
  201.     IF( POS( drvletter, validlist ) = 0 ) THEN  /* check drive is not already listed */
  202.         validlist = validlist || drvletter;     /* add drive to the string if its all OK */
  203. END
  204.  
  205. DROP drvlist firstchar drvmap maplen pchar drvletter
  206. RETURN validlist
  207.  
  208. /* ----------------------------------------------------------------------- 
  209.    SearchIt
  210.      Searches <what> for directory names matching <template>.
  211.      <what> may be a drive letter, "CURRENT" to search the current
  212.      drive or "LOOKUP" to search the lookup table.
  213.      Returns selected path or 0 if none is found.
  214.      If <firstmatch> = 1 and only one matching path is found, it is
  215.      automatically selected. User is asked to select if there is a
  216.      choice. 
  217.      if <firstmatch> = 2 the first matching path is accepted without
  218.      asking, even if there is a choice.
  219.    ----------------------------------------------------------------------- */
  220. SearchIt: PROCEDURE EXPOSE lookUp.
  221. Arg what, template, firstmatch
  222.  
  223. count = 0;
  224. IF( what = "LOOKUP" ) THEN DO
  225.     nChars = LENGTH( template );
  226.  
  227.     DO index = 1 TO lookUp.0
  228.         PARSE UPPER VAR lookUp.index.key lookupKey .
  229.  
  230.         IF( template = SUBSTR( lookupKey, 1, nChars ) ) THEN DO
  231.             count = count + 1;
  232.             path.count = lookUp.index.dir;
  233.         END
  234.     END
  235.  
  236.     path.0 = count;
  237.     DROP nChars count lookupKey
  238. END
  239. ELSE DO
  240.     /* set cwd to root dir of drive depending on <what>, search for files
  241.        matching template, put matches into array 'path', scan recursively, 
  242.        directories only, report paths only */
  243.     IF( what = "CURRENT" ) THEN DO
  244.         CALL DIRECTORY( "/" );
  245.         CALL SysFileTree template, "path", "SDO"
  246.     END
  247.     ELSE DO
  248.         curDir = DIRECTORY( what || ":" );   /* save cwd */
  249.         CALL DIRECTORY( what || ":/" );      /* switch to root */
  250.         CALL SysFileTree template, "path", "SDO"
  251.         CALL DIRECTORY( curDir );            /* restore cwd */
  252.     END
  253. END
  254.  
  255. IF( path.0 = 0 ) THEN RETURN 0;          /* no matching paths */
  256.  
  257. IF( firstmatch = 2 ) THEN RETURN path.1; /* take first without asking */
  258.  
  259. /* if theres only 1 match and firstmatch = 1 then dont bother asking */
  260. IF( ( path.0 = 1 ) & ( firstmatch = 1 ) ) THEN 
  261.     found = path.1;
  262. ELSE DO
  263.     found = 0   /* init success flag */ 
  264.     index = 1   /* init index to path array */
  265.  
  266.     DO WHILE( ( index <= path.0 ) & ( found = 0 ) )
  267.         IF( SuggestPath( path.index ) = 0 ) THEN
  268.             index = index + 1;
  269.         ELSE
  270.             found = path.index;
  271.     END
  272.  
  273.     DROP index
  274. END
  275.  
  276. DROP what template firstmatch path.
  277.  
  278. RETURN found;
  279.  
  280. /* -------------------------------------------------------------------------------- 
  281.    SuggestPath
  282.     Displays a path name followed by a question mark and waits for a key. 
  283.     Exits directly on <ESCAPE>. Returns 0 for <SPACE> or 1 otherwise.
  284.    ----------------------------------------------------------------------- */
  285. SuggestPath: PROCEDURE
  286. PARSE ARG pathname
  287.  
  288. SAY pathname"?"
  289.  
  290. accept = C2X( SysGetKey( "NOECHO" ) );
  291.  
  292. IF( accept = '1B' ) THEN CALL Error( "Search cancelled" ); /* ESCAPE */
  293. IF( accept = '20' ) THEN                                   /* SPACE  */
  294.     pathOK = 0;
  295. ELSE
  296.     pathOK = 1;
  297.  
  298. DROP accept pathname
  299.  
  300. RETURN pathOK;
  301.  
  302. /* -----------------------------------------------------------------------
  303.    Help
  304.     Displays command line syntax. Since this is not speed-
  305.     critical, the text is read from the top of the source
  306.     file, which saves updating it in two places. Not a 
  307.     procedure because it is called using SIGNAL and needs
  308.     access to SOURCE variable.
  309.    ----------------------------------------------------------------------- */
  310. Help: 
  311.     PARSE SOURCE . . self
  312.     SAY self
  313.     CALL STREAM self, 'C', "OPEN READ";
  314.     CALL LINEIN self;   /* first line is a comment */
  315.  
  316.     helpLine = "";
  317.     DO WHILE( POS( "*/", helpLine ) = 0 )
  318.         SAY helpLine;
  319.         helpLine = LINEIN( self );
  320.     END
  321.  
  322.     CALL STREAM self, 'C', "CLOSE";
  323. EXIT
  324.  
  325. /************************************************************
  326.                     ERROR  HANDLERS
  327.  ************************************************************/
  328.  
  329. /* -----------------------------------------------------------------------
  330.    Error
  331.      Called by the program to terminate precipitately.
  332.      Displays <errormsg> string, then exits.
  333.    ----------------------------------------------------------------------- */
  334. Error: PROCEDURE
  335. PARSE ARG errormsg
  336. SAY errormsg;
  337. EXIT
  338.  
  339. /* -----------------------------------------------------------------------
  340.    ErrorTrap
  341.      Traps errors in library functions, displays return code.
  342.    ----------------------------------------------------------------------- */
  343. ErrorTrap:
  344. SAY ERRORTEXT( rc );
  345. EXIT
  346.  
  347. /* -----------------------------------------------------------------------
  348.    NoValueTrap
  349.     Traps uninitialised variables and reports line number.
  350.     Shouldn't be any now of course.
  351.    ----------------------------------------------------------------------- */
  352. NoValueTrap:
  353. SAY "Uninitialised variable in line "SIGL;
  354. EXIT
  355.  
  356. /* -----------------------------------------------------------------------
  357.    SyntaxTrap
  358.     Traps syntax error and reports line number. The interpreter
  359.     will trap syntax errors but won't restore the environment 
  360.     which could leave the wrong drive or directory.
  361.    ----------------------------------------------------------------------- */
  362. NoValueTrap:
  363. SAY "Syntax error in line "SIGL;
  364. EXIT
  365.  
  366. /* -----------------------------------------------------------------------
  367.    Terminate : General exit and error trap
  368.    ----------------------------------------------------------------------- */
  369. Terminate:
  370. EXIT;
  371.  
  372. /************************************************************
  373.        LOOKUP TABLE EDITING ROUTINES
  374.  
  375.   If you don't intend to use the lookup table facilities,
  376.   you can delete the rest of the file.
  377.  ************************************************************/
  378.  
  379. /* -----------------------------------------------------------------------
  380.    EditLookupTable :
  381.    ----------------------------------------------------------------------- */
  382. EditLookupTable: PROCEDURE EXPOSE lookUp.
  383.  
  384. /* useful ASCII formatting chars */
  385. CRLF = X2C( '0D' ) || X2C( '0A' );  /* carriage return / line feed */
  386. TAB = X2C( 9 );                     /* tab char */
  387.  
  388. cancelled = 0;
  389. finished = 0;
  390. modified = 0;
  391.  
  392. DO WHILE( ( cancelled = 0 ) & ( finished = 0 ) )
  393.     legal = 0;
  394.  
  395.     DO WHILE( legal = 0 )
  396.         CALL SysCls;
  397.         SAY " (A)dd Entry" CRLF" (D)elete Entry" CRLF" (V)iew Entries" 
  398.         SAY CRLF" (C)ancel and Exit" CRLF" (S)ave and Exit" CRLF;
  399.         PARSE UPPER VALUE SysGetKey( "NOECHO" ) WITH choice
  400.  
  401.         legal = 1;
  402.         SELECT
  403.             WHEN( choice = 'A' ) THEN 
  404.                 IF( AddLookupEntry() \= 0 ) THEN modified = 1;
  405.  
  406.             WHEN( choice = 'D' ) THEN DO
  407.                 delIndex = DisplayLookupTable( 1 );
  408.                 IF( delIndex \= 0 ) THEN DO
  409.                     CALL DeleteLookupEntry delIndex;
  410.                     modified = 1;
  411.                 END
  412.             END
  413.  
  414.             WHEN( choice = 'V' ) THEN CALL DisplayLookupTable( 0 );
  415.             WHEN( choice = 'C' ) THEN cancelled = 1;
  416.             WHEN( choice = 'S' ) THEN finished = 1;
  417.             OTHERWISE legal = 0;
  418.         END
  419.  
  420.     END
  421.  
  422. END
  423.  
  424. IF( ( cancelled = 0 ) & ( modified = 1 ) ) THEN 
  425.     CALL RewriteLookupTable;
  426. ELSE
  427.     SAY "No changes were recorded.";
  428.  
  429. DROP cancelled finished modified legal
  430. RETURN;
  431.  
  432. /* -----------------------------------------------------------------------
  433.    GetNumber
  434.    ----------------------------------------------------------------------- */
  435. GetNumber: PROCEDURE
  436. ARG upper
  437.  
  438. inputOK = 0;
  439. number = "";
  440.  
  441. DO WHILE( inputOK = 0 )
  442.     ch = C2X( SysGetKey( "NOECHO" ) );
  443.  
  444.     SELECT
  445.         WHEN( ch = '1B' ) THEN DO              /* ESCAPE */
  446.             inputOK = 1;
  447.             number = 0;
  448.         END
  449.         WHEN( ch = '0D' ) THEN inputOK = 1;    /* ENTER */
  450.         WHEN( ( ch < '30' ) | ( ch > '39' ) ) THEN CALL BEEP 2500, 200;
  451.         OTHERWISE DO
  452.             ch = X2C( ch );
  453.             IF( ( number || ch ) <= upper ) THEN DO
  454.                 CALL CHAROUT "STDOUT:", ch;
  455.                 number = number || ch;
  456.             END
  457.             ELSE
  458.                 CALL BEEP 2500, 200;
  459.         END
  460.     END
  461.  
  462. END
  463.  
  464. DROP inputOK ch
  465. RETURN number
  466.  
  467. /* -----------------------------------------------------------------------
  468.    DisplayLookupTable
  469.    ----------------------------------------------------------------------- */
  470. DisplayLookupTable: PROCEDURE EXPOSE lookUp. TAB CRLF
  471. ARG active
  472.  
  473. IF( lookUp.0 = 0 ) THEN DO
  474.     SAY "No entries in table. Press a key."
  475.     CALL SysGetKey( "NOECHO" );
  476.     RETURN "";
  477. END
  478.  
  479. PARSE VALUE SysTextScreenSize() WITH screenRows screenCols
  480.  
  481. IF( active = 1 ) THEN
  482.     screenRows = screenRows - 8;   /* leave room for menu */
  483. ELSE
  484.     screenRows = screenRows - 2;   /* or just for <Press a key> message */
  485.  
  486. indexLU = 0;
  487. choice = "";
  488.  
  489. DO WHILE( (choice = "" ) & ( indexLU < lookUp.0 ) )
  490.     CALL SysCls;
  491.     row = 0;
  492.  
  493.     DO WHILE( ( row < screenRows ) & ( indexLU < lookUp.0 ) )
  494.         indexLU = indexLU + 1;
  495.         row = row + 1;
  496.         outstr = indexLU TAB lookUp.indexLU.key " = " lookUp.indexLU.dir;
  497.         SAY outstr
  498.     END
  499.  
  500.     SAY;
  501.     IF( active = 0 ) THEN DO
  502.         SAY " <Press a key>";
  503.         CALL SysGetKey( "NOECHO" );
  504.     END
  505.     ELSE DO
  506.         SAY "Choose a number" CRLF"<ENTER> for next screen" CRLF"<ESC> to quit";
  507.         choice = GetNumber( lookUp.0 );
  508.     END
  509.  
  510. END
  511.  
  512. DROP active screenCols screenRows indexLU outstr row
  513. RETURN choice;
  514.  
  515. /* -----------------------------------------------------------------------
  516.    AddLookupEntry
  517.     Prompts for a new lookup key and checks that it doesn't
  518.     include any spaces, then prompts for a path name, checks
  519.     for illegal characters then tries to CD to it. Note that
  520.     it is not an error if the path does not exist - the user
  521.     may intend to create it later or it may be on a drive that
  522.     is currently inaccessible.
  523.    ----------------------------------------------------------------------- */
  524. AddLookupEntry: PROCEDURE EXPOSE lookUp.
  525.  
  526. inputOK = 0;
  527. DO WHILE( inputOK = 0 )
  528.     SAY "Enter a lookup key :";
  529.     PULL newKey junk .       
  530.     IF( junk \= "" ) THEN 
  531.         SAY "Do not embed spaces!";
  532.     ELSE
  533.         inputOK = 1;
  534. END
  535. DROP junk
  536.  
  537. inputOK = 0;
  538. DO WHILE( inputOK = 0 )
  539.     SAY "Enter the fully-qualified pathname :";
  540.     PULL newPath .
  541.     PARSE VAR newPath drive ":" path 
  542.  
  543.     /* check for illegal chars in <path>, and that <drive> is a single letter */
  544.     IF( ( VERIFY( path, '":*?|', "MATCH" ) \= 0 ) | ( LENGTH( drive ) > 1 ) | ( DATATYPE( drive, 'M' ) = 0 ) ) THEN
  545.         SAY " The path is illegal";
  546.     ELSE DO
  547.         /* first check that the drive responds, then try to change to the directory */
  548.         IF( STREAM( drive || ":*", 'C', "OPEN" ) = "NOTREADY:2" ) THEN DO
  549.             curDir = DIRECTORY( drive || ":" ); /* save cwd for this drive */
  550.             IF( DIRECTORY( newPath ) = newPath ) THEN inputOK = 1;
  551.             CALL DIRECTORY( curDir );           /* restore the cwd */
  552.             DROP curDir
  553.         END
  554.  
  555.         IF( inputOK = 0 ) THEN DO
  556.             SAY " Cannot locate the directory. Is that OK (Y/N)?";
  557.             PARSE UPPER VALUE SysGetKey( "NOECHO" ) WITH response
  558.             IF( response = 'Y' ) THEN inputOK = 1;
  559.         DROP response
  560.         END
  561.  
  562.     END
  563. DROP drive path
  564. END
  565.  
  566. last = lookUp.0 + 1;          /* add the new entry to the table */
  567. lookUp.last.key = newKey;
  568. lookUp.last.dir = newPath;
  569. lookUp.0 = last;
  570.  
  571. DROP newKey newPath last
  572. RETURN inputOK
  573.  
  574. /* -----------------------------------------------------------------------
  575.    DeleteLookupEntry
  576.     Removes entry <deleteAt> and packs the remaining entries
  577.     then adjusts lookUp.0 to reflect the new size.
  578.    ----------------------------------------------------------------------- */
  579. DeleteLookupEntry: PROCEDURE EXPOSE lookUp.
  580. ARG deleteAt
  581.  
  582. DO index = deleteAt TO ( lookUp.0 - 1 )
  583.     nIndex = index + 1;
  584.     lookUp.index.key = lookUp.nIndex.key;
  585.     lookUp.index.dir = lookUp.nIndex.dir;
  586. END
  587.  
  588. lookUp.0 = lookUp.0 - 1;
  589.  
  590. DROP index nIndex deleteAt
  591. RETURN;
  592.  
  593. /* -----------------------------------------------------------------------
  594.    RewriteLookupTable
  595.     Copies the entire file to a temp file, filling in the
  596.     lookup table section with the new entries, then deletes
  597.     the old file and renames the temp file.
  598.     "source directory" refers to the one where RDX.CMD resides.
  599.    ----------------------------------------------------------------------- */
  600. RewriteLookupTable: PROCEDURE EXPOSE lookUp.
  601.  
  602. PARSE SOURCE . . rdxFile;
  603.  
  604. /* locate the directory containing the source file */
  605. srcDrive = FILESPEC( "DRIVE", rdxFile );
  606. srcPath = FILESPEC( "PATH", rdxFile );
  607. sourceDir = srcDrive || srcPath;
  608.  
  609. /* if source dir is a root we need terminating backslash, otherwise it must go */
  610. IF( srcPath \= "\" ) THEN srcPath = SUBSTR( srcPath, 1, LENGTH( srcPath )-1 );
  611.  
  612. curDir = DIRECTORY( srcDrive );         /* find and save the cwd for the drive */
  613. CALL DIRECTORY( srcDrive || srcPath );  /* then change to the source directory */
  614. DROP srcDrive srcPath
  615.  
  616. /* drop the path from source file name for convenience */
  617. rdxFile = FILESPEC( "NAME", rdxFile );
  618. CALL STREAM rdxFile, 'C', "OPEN READ";
  619.  
  620. /* create the temporary file in the source directory so it can be renamed */
  621. tempFile = SysTempFileName( "RDX?????.CMD" );
  622. IF( STREAM( tempFile, 'C', "OPEN WRITE" ) \= "READY:" ) THEN
  623.     CALL Error( "Cannot create temporary file" );
  624.  
  625. /* Copy lines from source file to temp file until we find the start
  626.    of the lookup table */
  627. fline = "";
  628. DO WHILE( ( LINES( rdxFile ) = 1 ) & ( fline \= "/*LOOKUP*/" ) )
  629.     fline = LINEIN( rdxFile );
  630.     CALL LINEOUT tempFile, fline;
  631. END
  632.  
  633. /* Write new lookup table to the temp file */
  634. DO index = 1 TO lookUp.0
  635.     CALL LINEOUT tempFile, "lookUp." || index || ".key = '" || lookUp.index.key || "'";
  636.     fline = "lookUp." || index || ".dir = '" || lookUp.index.dir || "'";
  637.     CALL LINEOUT tempFile, fline;
  638. END
  639.  
  640. /* Write size of lookup table to temp file */
  641. fline = "lookUp.0 = " || lookUp.0;
  642. CALL LINEOUT tempFile, fline;
  643.  
  644. /* Search source file for the end of the lookup table */
  645. fline = "";
  646. DO WHILE( ( LINES( rdxFile ) = 1 ) & ( fline \= "/*ENDLOOKUP*/" ) )
  647.     fline = LINEIN( rdxFile );
  648. END
  649.  
  650. /* Write the ENDLOOKUP flag to the temp file */
  651. CALL LINEOUT tempFile, fline;
  652.  
  653. /* Copy the rest of the source to the temp file */
  654. DO WHILE( LINES( rdxFile ) = 1 )
  655.     CALL LINEOUT tempFile, LINEIN( rdxFile );
  656. END
  657.  
  658. CALL STREAM tempFile, 'C', "CLOSE";
  659. CALL STREAM rdxFile, 'C', "CLOSE";
  660.  
  661. /* Delete the source file and rename the temp file */
  662. IF( SysFileDelete( rdxFile ) \= 0 ) THEN DO
  663.     SAY "Cannot replace original file " rdxFile;
  664.     SAY "New file was saved as " sourceDir tempFile;
  665.     SIGNAL Terminate;
  666. END
  667.  
  668. "REN" tempFile rdxFile;
  669.  
  670. CALL DIRECTORY( curDIr );
  671. DROP curDir sourceDir index fline rdxFile tempFile
  672. RETURN
  673.  
  674. /************************************************************
  675.    end
  676.   ************************************************************/
  677.  
  678.