From: DeaDDooMER Date: Fri, 14 Feb 2020 19:55:59 +0000 (+0300) Subject: remove generic parser from DswOpts X-Git-Url: http://deadsoftware.ru/gitweb?a=commitdiff_plain;h=0c2f9751f947b917bb4cdf63da95d5cd79d1b8c2;p=cpc.git remove generic parser from DswOpts --- diff --git a/src/generic/Dsw/Mod/Opts.cp b/src/generic/Dsw/Mod/Opts.cp index 079bf61..f4fc7d1 100644 --- a/src/generic/Dsw/Mod/Opts.cp +++ b/src/generic/Dsw/Mod/Opts.cp @@ -1,17 +1,6 @@ MODULE DswOpts; - IMPORT Kernel, Log; - - CONST - (* symbol *) - null* = 0; opt* = 1; char* = 2; string* = 3; ident* = 4; eos* = 5; eof* = 6; - - (* scanner options *) - options* = 0; strings* = 1; identifiers* = 2; chars* = 3; terminators* = 4; - emptystr* = 5; emptyident* = 6; invalid* = 7; - - (* errors *) - ok* = 0; unkopt* = 1; missarg* = 2; + IMPORT Kernel; TYPE String* = POINTER TO ARRAY OF CHAR; @@ -21,134 +10,58 @@ MODULE DswOpts; args: POINTER TO ARRAY OF String; argn-, argi-: INTEGER; str-: String; - ch-: CHAR; - opts*: SET; - - PROCEDURE Skip (n: INTEGER); - BEGIN - ASSERT(n >= 0, 20); - ASSERT(argn < LEN(args), 21); - ASSERT(argi + n <= LEN(args[argn]$), 22); - INC(argi, n) - END Skip; PROCEDURE IsOpt (ch: CHAR): BOOLEAN; BEGIN - RETURN (CAP(ch) >= "A") & (CAP(ch) <= "Z") OR (ch >= "0") & (ch <= "9") OR (ch = "-") + RETURN (CAP(ch) >= "A") & (CAP(ch) <= "Z") OR (ch >= "0") & (ch <= "9") END IsOpt; - PROCEDURE IsIdentStart (ch: CHAR): BOOLEAN; - BEGIN - RETURN (CAP(ch) >= "A") & (CAP(ch) <= "Z") OR (ch = "_") - END IsIdentStart; - - PROCEDURE IsIdent (ch: CHAR): BOOLEAN; + PROCEDURE Reset*; BEGIN - RETURN (CAP(ch) >= "A") & (CAP(ch) <= "Z") OR (ch = "_") OR (ch >= "0") & (ch <= "9") - END IsIdent; + argn := 1; argi := 0; str := NIL; optMode := FALSE; + END Reset; - PROCEDURE Get* (VAR x: BYTE); - VAR i, j, len: INTEGER; sym: BYTE; c: CHAR; + PROCEDURE GetStr; + VAR ch: CHAR; i, beg, len: INTEGER; BEGIN - ch := 0X; str := NIL; - IF argn >= LEN(args) THEN - optMode := FALSE; sym := eof - ELSE - sym := null; - c := args[argn, argi]; - IF c = 0X THEN - optMode := FALSE; INC(argn); argi := 0; - IF terminators IN opts THEN sym := eos; (* !!! *) - ELSIF argn >= LEN(args) THEN sym := eof (* !!! *) - ELSE c := args[argn, argi] (* continue parsing *) - END + str := NIL; + IF argn < LEN(args) THEN + beg := argi; + REPEAT ch := args[argn, argi]; INC(argi) UNTIL ch = 0X; + len := argi - beg; + NEW(str, len + 1); + FOR i := 0 TO len - 1 DO + str[i] := args[argn, beg + i] (* zero not copied *) END; - IF sym = null THEN - IF (options IN opts) & (optMode & IsOpt(c) OR (c = "-") & IsOpt(args[argn, argi + 1])) THEN - sym := opt; - IF optMode THEN - ch := c; optMode := TRUE; Skip(1) - ELSE - ch := args[argn, argi + 1]; optMode := TRUE; Skip(2) - END - ELSIF (identifiers IN opts) OR (strings IN opts) THEN - len := 0; i := argi; sym := null; - (* --- get length of identifier --- *) - IF (identifiers IN opts) & (IsIdentStart(args[argn, i]) OR (emptyident IN opts)) THEN - WHILE IsIdent(args[argn, i]) DO - INC(len); - INC(i) - END; - sym := ident - END; - (* --- get length of string --- *) - IF strings IN opts THEN - WHILE args[argn, i] # 0X DO - INC(len); - INC(i) - END; - sym := string - ELSIF (identifiers IN opts) & (args[argn, i] # 0X) & ~(invalid IN opts) THEN - WHILE args[argn, i] # 0X DO INC(i) END; - sym := null - END; - (* --- copy string --- *) - IF (sym # null) & ((len > 0) OR (sym = string) & (emptystr IN opts) OR (sym = ident) & (emptyident IN opts)) THEN - NEW(str, len + 1); - FOR j := 0 TO len - 1 DO - str[j] := args[argn, argi + j] - END; - str[len] := 0X - END; - optMode := FALSE; - Skip(i - argi) - ELSIF chars IN opts THEN - ch := c; optMode := FALSE; Skip(1) - ELSE - optMode := FALSE; sym := null; Skip(1) - END - END - END; - x := sym - END Get; - - PROCEDURE Reset*; - BEGIN - argn := 1; argi := 0; ch := 0X; str := NIL; optMode := FALSE; - opts := {options, strings, emptystr} - END Reset; + INC(argn); argi := 0; optMode := FALSE + END + END GetStr; PROCEDURE GetOpt* (IN optstring: ARRAY OF CHAR): CHAR; - VAR save: SET; sym: BYTE; c: CHAR; i, mode: INTEGER; + VAR opt, ch: CHAR; i: INTEGER; BEGIN - save := opts; opts := {options, strings, emptystr}; c := 0X; - Get(sym); - IF sym = opt THEN - c := ch; i := 0; - WHILE (optstring[i] # 0X) & (optstring[i] # c) DO - INC(i); - WHILE optstring[i] = ":" DO - INC(i) - END - END; - IF optstring[i] = c THEN - opts := {strings, emptystr}; mode := 0; INC(i); - WHILE optstring[i] = ":" DO - INC(mode); - INC(i) - END; - IF mode # 0 THEN Get(sym); - IF (sym # string) & (mode = 1) THEN - NEW(str, 2); str[0] := c; c := ":" - END + IF argn >= LEN(args) THEN + opt := 0X; optMode := FALSE (* eof *) + ELSIF optMode & IsOpt(args[argn, argi]) OR (args[argn, argi] = "-") & IsOpt(args[argn, argi + 1]) THEN + IF ~optMode THEN optMode := TRUE; INC(argi) END; + opt := args[argn, argi]; INC(argi); i := 0; + IF args[argn, argi] = 0X THEN INC(argn); argi := 0; optMode := FALSE END; + REPEAT + ch := optstring[i]; INC(i); + IF ch = ":" THEN ch := optstring[i]; INC(i) END + UNTIL (ch = opt) OR (ch = 0X); + IF ch = opt THEN + IF optstring[i] = ":" THEN + GetStr; + IF str = NIL THEN + NEW(str, 2); str[0] := opt; opt := ":" (* missing param *) + END END - ELSE NEW(str, 2); str[0] := c; c := "?" + ELSE NEW(str, 2); str[0] := opt; opt := "?" (* unknown option *) END - ELSIF sym = eof THEN c := 0X (* eof *) - ELSE c := "$" (* string *) + ELSE GetStr; opt := "$" (* string *) END; - opts := save; - RETURN c + RETURN opt END GetOpt; PROCEDURE Init;