$ IF P1.NES."HELP" THEN GOTO SKIP_HELP $ SET VER $! $!------------------------------------------------------------------------------ $! $! (c) Yezerski Roper LTD. 1993-7 $! http://www.yrl.co.uk/ $! $! Please note: You are free to distribute this file provided you don't pretend $! it's yours, and give YRL the credit they deserve. $! $! Yezerski Roper will not accept any responsibility for any $! problems arising from the use of these commands. However, we $! welcome any suggestions and feedback you may have. $! $!------------------------------------------------------------------------------ $! $! Command file name : DCLWILD.COM $! $! Author(s) : John A Fotheringham $! $! Command file description $! ------------------------ $! DCLWILD performs wildcard DCL file operations $! $! Parameters $! ---------- $! p1 - DCL command or "HELP" (e.g. BACKUP, COPY, RENAME) $! p2 - Input wildcard filespec $! p3 - [Output wildcard filespec] $! p4,5... - [Other DCL command qualifiers] $! $! $! Comments $! -------- $! - To debug, set global symbol JDBG == "Y" $! - make sure your qualifiers are separated by white space from $! your wildcards $! - You may get unexpected results if the wildcards don't exactly match $! - be careful when wildcarding the version numbers. RENAME and COPY $! may fail if there are existing output files $! $! Examples: $! $! DCLWILD RENAME *919*NI*.dat *920*YR*.tmp /conf $! DCLWILD RENAME *1*2*3*4*.dat *4*3*2*1.dat /conf $! DCLWILD COPY *GOOD*.*lb *BAD*.* /LOG/CONF $! $! HISTORY $! ------- $! $! Version Name/description Date $! ------- ---------------- ---- $! V01-001 John A Fotheringham 26-JUL-93 $! V01-002 John A Fotheringham 21-Nov-97 $! Tarted up for release on comp.os.vms $! $!------------------------------------------------------------------------------ $! $ SET NOVER $ EXIT $ $ SKIP_HELP: $ $ ! Check all three args present $ If p3.eqs."" $ THEN $ WRITE SYS$OUTPUT "%DCLWILD-W-DCLWILD, Insufficient arguments" $ INQUIRE/NOPUNC GOON "Continue [N] > " $ if .not. goon .or. goon.eqs."" then exit $ ENDIF $ $ Filespec = p2 $ $ IF F$locate ("%",filespec).ne.f$len(filespec) $ THEN $ WRITE SYS$OUTPUT "%DCLWILD-W-DCLWILD, Sorry! We don't do ""%"" wildcards!" $ EXIT $ ENDIF $ $ ! See which bits of the filespec we need to match $ $ in_spec = f$parse (p2,,,"DEVICE") - + f$parse (p2,,,"DIRECTORY") - + f$parse (p2,,,"NAME") $ $ IF f$parse (p2,,,"TYPE").eqs."." $ THEN $ in_spec = in_spec + ".*" $ ELSE $ in_spec = in_spec + f$parse (p2,,,"TYPE") $ ENDIF $ $ VTEXT = f$parse (p2,,,"VERSION") $ IF VTEXT.nes.";" $ THEN $ ! use "." to make subsequent parsing easier $ in_spec = in_spec + "." + VTEXT - ";" $ ENDIF $ $ out_spec = f$parse (p3,,,"DEVICE") - + f$parse (p3,,,"DIRECTORY") - + f$parse (p3,,,"NAME") $ $ IF f$parse (p3,,,"TYPE").eqs."." $ THEN $ out_spec = out_spec + ".*" ! use "." to make parsing easier $ ELSE $ out_spec = out_spec + f$parse (p3,,,"TYPE") $ ENDIF $ $ VTEXT = f$parse (p3,,,"VERSION") $ IF VTEXT.nes.";" $ THEN $ ! use "." to make subsequent parsing easier $ out_spec = out_spec + "." + VTEXT - ";" $ ENDIF $ $ WRITE SYS$OUTPUT "" $ WRITE SYS$OUTPUT "Input spec = ", in_spec $ WRITE SYS$OUTPUT "Output spec = ", out_spec $ WRITE SYS$OUTPUT "" $ $!----- process files in loop ------------------------------------------------- $ $ file_count = 0 $ $ FILE_LOOP: $ $ next_file = f$search (filespec) $ IF next_file.eqs."" $ THEN $ if file_count.eq.0 THEN WRITE SYS$OUTPUT "No files matched spec ",in_spec $ EXIT $ ENDIF $ $ file_count = file_count + 1 $ $ ! convert the wildcard $ conv_file == "" $ if p3.nes."" $ then $ $ CALL CHANGE_WILD 'in_spec' 'out_spec' 'next_file' conv_file $ $ IF conv_file.eqs."" $ THEN $ WRITE SYS$OUTPUT "" $ WRITE SYS$OUTPUT "Unable to convert file ''next_file' using wildcards" $ WRITE SYS$OUTPUT "" $ GOTO FILE_LOOP $ ENDIF $ $ ENDIF $ $ ! File converted, construct command $ def/user sys$input sys$command $ DCL_Command = p1 + " " + next_file + " " + conv_file + " " + p4 - + " " + p5 + " " + p6 + " " + p7 + " " + p8 $ $ ! execute the command $ 'DCL_COmmand' $ $ GOTO FILE_LOOP $ $ EXIT $ CHANGE_WILD: $ SUBROUTINE ! CHANGE_WILD : changes filespecs using wild cards $ $ IF P1.NES."HELP" THEN GOTO SKIP_HELP $ SET VER $!------------------------------------------------------------------------------ $! $! (c) Yezerski Roper LTD. 1993 $! $!------------------------------------------------------------------------------ $! $! Command file name : CHANGE_WILD.COM $! $! Author(s) : John A Fotheringham $! $! Command file description $! ------------------------ $! CHANGE_WILD changes a string meeting one wild card, to those matching $! a second. If no match is made, the result is set blank. These strings $! are nominally file names, and substitution of wildcards in the $! directory part of the file name is not (yet) supported. Nor is the $! use of "%" wildcards $! $! Parameters $! ---------- $! p1 - (R) First wild card $! p2 - (R) Second wild card $! p3 - (R) input string $! p4 - (W) symbol to recieve output string, if missing MATCH will be $! used $! $! HISTORY $! ------- $! $! Version Name/description Date $! ------- ---------------- ---- $! V01-001 John A Fotheringham 26-JUL-93 $! $!------------------------------------------------------------------------------ $! $ SET NOVER $ EXIT $ $ SKIP_HELP: $ $ out_dir = "" $ Out_sym = P4 $ IF out_sym.eqs."" THEN out_sym = "MATCH" $ $ ! replace any ";" in P3 to simplify testing $ IF F$loc (";", p3).ne.f$len(p3) THEN - P3 = f$element (0,";",p3) + "." + f$element (1,";",p3) $ $ IF F$locate ("]",p1).ne.f$len(p1) $ THEN $ in_dir = f$element (0,"]",p1) + "]" $ out_dir = in_dir $ p1 = p1 - in_dir $ ENDIF $ $ IF F$locate ("]",p2).ne.f$len(p2) $ THEN $ out_dir = f$element (0,"]",p2) + "]" $ p2 = p2 - out_dir $ ELSE $ IF out_dir.eqs."" THEN out_dir = "[]" $ ENDIF $ $ IF F$locate ("]",p3).ne.f$len(p3) $ THEN $ out_dir2 = f$element (0,"]",p3) $ p3 = p3 - out_dir2 - "]" $ ENDIF $ $ ! set output symbol to blank $ 'Out_sym' == "" $ $ ! Test if test string matches $ CALL MATCH_WILD 'p1' 'p3' match $ $ ! if no match, give up. $ IF .NOT. match $ THEN $ WRITE SYS$OUTPUT "%DCLWILD-W-CHANGE_WILD, No match between ""''p1'"" and ""''p3'""" $ EXIT $ ENDIF $ $ ! now the tricky bit, process input wild card, output file card, and $ ! input string in parallel. $ ! $ ! process each "word" (separated by "."s) This is to allow independent $ ! wild card on extensions etc. $ $ WORD_COUNT = 0 $ $ total_string = "" $ $ WORD_LOOP: $ $ wild1 = f$element (word_count, ".", p1) $ wild2 = f$element (word_count, ".", p2) $ in_string = f$element (word_count, ".", p3) $ out_string = "" $ $ IF wild1.eqs."." .or. wild2.eqs."." THEN GOTO ALL_DONE $ $ WILD_LOOP: $ $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: wild1 =",wild1 $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: wild2 =",wild2 $ $ ! get position of next wild bit in Wild 1 $ w1_pos = f$locate ("*", wild1) $ $ IF w1_pos.eq.0 $ THEN $ $!------- next part is wild, copy up to next fixed bit $ $ ! remove wildcard $ wild1 = f$extract (1, f$len(wild1), wild1) $ $ ! get input fixed bit $ In_fixed_bit = f$ext ( w1_pos, f$locate ("*", wild1), wild1) $ in_pos = f$locate ("''In_fixed_bit'", In_string) $ If In_fixed_bit.eqs."" THEN in_pos = f$len (in_string) $ $ ! If next part of wild2 also wild, copy across, otherwise replace $ ! with blank $ $ IF f$locate ("*", wild2).EQ.0 .AND. wild2.nes."" $ THEN $ $ ! wild2 is wild, copy everything across up to fixed bit, if no $ ! remaining fixed bit, copy everything $ $ ! remove wildcard $ wild2 = f$extract (1, f$len(wild2), wild2) $ $ Out_fixed_bit = f$ext ( 0, f$locate ("*", wild2), wild2) $ IF out_fixed_bit.eqs."" THEN in_pos = f$length (in_string) $ $ out_string = out_string + f$ext (0, in_pos, in_string) $ $ in_string = f$ext (in_pos, f$len(in_string), in_string) $ $ ELSE $ $ ! wild2 is fixed, copy nothing across, unless no further input $ ! fixed bit, in which case substitue output fixed bit $ $ Out_fixed_bit = f$ext ( 0, f$locate ("*", wild2), wild2) $ $ IF in_pos.eq.f$len(in_string) THEN - out_string = out_string + out_fixed_bit $ $ in_string = f$ext (in_pos, f$len(in_string), in_string) $ $ ENDIF $ $ ELSE $ $!------ next part is fixed, replace up to next "wild" $ $ ! get input fixed bit $ $ In_fixed_bit = f$ext ( 0, f$locate ("*", wild1), wild1) $ $ ! If next part of wild2 of wild, blank out, otherwise replace with $ ! alternative fixed bit $ $ IF f$locate ("*", wild2).EQ.0 .AND. wild2.nes."" $ THEN $ $ ! wild2 is wild, replace by blanks $ $ Out_fixed_bit = "" $ $ out_string = out_string + "" ! No change $ $ in_string = in_string ! also no change $ $ ELSE $ $ ! wild2 is fixed, substitute this bit for input bit $ $ Out_fixed_bit = f$ext ( 0, f$locate ("*", wild2), wild2) $ $ in_pos = f$locate ("''In_fixed_bit'", In_string) $ out_string = out_string + "" + out_fixed_bit $ $ in_string = f$ext (in_pos+F$len(in_fixed_bit), - f$len(in_string), in_string) $ $ ENDIF $ $ ! take fixed bits from wildcards $ $ wild1 = wild1 - in_fixed_bit $ wild2 = wild2 - out_fixed_bit $ $ ENDIF $ $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: Out_fixed_bit = ", out_fixed_bit $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: In_fixed_bit = ", in_fixed_bit $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: Out_string = ", Out_string $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: In_string = ", In_string $ $ IF wild1.nes."" .AND. wild2.nes."" THEN GOTO WILD_LOOP $ $ END_WILD: $ $ IF word_count.gt.0 THEN out_string = "." + out_string $ total_string = total_string + out_string $ IF JDBG THEN WRITE SYS$OUTPUT "CHANGE_WILD: Total =",total_string $ $ ! Go do next word $ $ word_count = word_count + 1 $ goto word_loop $ $ ALL_DONE: $ 'out_sym' == "''out_dir'''total_string'" $ IF JDBG THEN SH SYM 'out_sym' $ $ EXIT ! End of CHANGE_WILD $ ENDSUBROUTINE $ MATCH_WILD: $ SUBROUTINE ! MATCH_WILD : tests strings against wild cards $ $ IF p1.eqs. "HELP" THEN SET VER $!------------------------------------------------------------------------------ $! $! Command file name : MATCH_WILD.COM $! $! Author(s) : John A Fotheringham $! $! Command file description $! ------------------------ $! MATCH_WILD tests whether a string matches a supplied wildcard $! $! Parameters $! ---------- $! p1 - Wildcard $! P2 - test string $! P3 - global symbol result ("TRUE" or "FALSE") is to be placed in $! $!------------------------------------------------------------------------------ $! $ IF p1.eqs. "HELP" $ THEN $ SET NOVER $ EXIT $ ENDIF $ $ wild = p1 $ test = p2 $ $ matched = "TRUE" $ $ first_ast = "T" $ $ ! Input spec is a sequence of fixed text, wildcard, fixed text, wildcard $ ! etc. Process each wildcard in turn, checking for the matching fixed $ ! text. Wildcards are processed differently according to whether they $ ! are on the left, right or middle of the string $ $ LOOP: $ $ ! determine position of next wildcard $ $ ast_pos = f$locate ("*",wild) $ !! per_pos = f$locate ("%",wild) $ per_pos = ast_pos + 1 ! Don't yet support "%" $ $ IF ast_pos.lE.per_pos $ THEN $ $ ! If leading wildcard, test if any more follow. If they don't, then $ ! we are testing a right wild, instead of a left wild $ $ temp_wild = f$ext (ast_pos+1,f$len(wild),wild) $ next_ast_pos = f$loc("*",temp_wild) $ $ ! if another wildcard later, do a left-wild comparison $ $ IF ast_pos.ne.0 .OR. next_ast_pos.ne.f$len(temp_wild) $ THEN $ $ ! testing a left or middle wildcard $ $ IF first_ast $ THEN $ $ ! testing a left wildcard $ $ first_ast = "F" ! reset first time flag $ $ wild_match = f$ext (0,ast_pos,wild) $ wild = f$ext (ast_pos, F$len(wild), wild) $ $ wild_test = f$ext (0, ast_pos, test) $ test = f$ext (ast_pos, f$len(test), test) $ $ IF wild_test.nes.wild_match $ THEN $ !! WRITE SYS$OUTPUT "match failed comparing ""''wild_test'"" with ""''wild_match'""" $ matched = "FALSE" $ GOTO END_TEST $ ENDIF $ $ ELSE $ $ ! Testing a middle wildcard $ wild_match = f$ext (1,next_ast_pos,wild) $ $ ! oh bother, this could be ANYWHERE...try sliding window until $ ! find a match (success) or reach end of test string failure $ $ Tind = 0 ! index position $ $ MID_LOOP: $ wild_test = f$ext (tind, next_ast_pos, test) $ $ ! if matched, exit loop $ IF wild_test.eqs.wild_match THEN GOTO END_MID_LOOP $ $ tind=tind + 1 $ IF tind+next_ast_pos-1.lt.f$len(test) THEN GOTO MID_LOOP $ $ ! Failure! - reached end without a match $ matched = "FALSE" $ GOTO END_TEST $ $ END_MID_LOOP: $ $ ! success!! $ wild = f$ext (next_ast_pos+1, F$len(wild), wild) $ test = f$ext (tind + next_ast_pos, f$len(test), test) $ $ ENDIF ! if testing a middle wildcard $ $ ELSE $ $ ! testing a right wildcard $ $ wild_match = f$ext (1,f$len(wild)-1,wild) $ wild_test = f$ext (f$len(test)-f$len(wild)+1, f$len(wild)-1, test) $ $ wild = "" ! force exit from loop $ $ IF wild_test.nes.wild_match $ THEN $ !WRITE SYS$OUTPUT "match failed comparing ""''wild_test'"" with ""''wild_match'""" $ matched = "FALSE" $ GOTO END_TEST $ ENDIF $ $ ENDIF ! if testing right wildcard $ $ ENDIF ! if found an asterisk $ $ IF wild.nes."" THEN GOTO LOOP $ $ END_TEST: $ $ IF P3.eqs."" $ THEN $ IF matched $ THEN $ WRITE SYS$OUTPUT "''p2' matched wildcard ''p1'" $ ELSE $ WRITE SYS$OUTPUT "''p2' failed to match wildcard ''p1'" $ ENDIF $ ELSE $ 'P3' == "''matched'" $ ENDIF $ $ EXIT ! End of MATCH_WILD $ ENDSUBROUTINE $