home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Fresh Fish 8
/
FreshFishVol8-CD2.bin
/
bbs
/
dev
/
oberon-a-1.4ß.lha
/
Oberon-A
/
source
/
amigautil
/
Args.mod
< prev
next >
Wrap
Text File
|
1994-08-08
|
5KB
|
185 lines
(***************************************************************************
$RCSfile: Args.mod $
Description: C-style command-line argument parsing
Created by: fjc (Frank Copeland)
$Revision: 2.3 $
$Author: fjc $
$Date: 1994/08/08 16:10:27 $
Copyright © 1994, Frank Copeland.
This file is part of the Oberon-A Library.
See Oberon-A.doc for conditions of use and distribution.
***************************************************************************)
MODULE Args;
(*
** $C- CaseChk $I- IndexChk $L- LongAdr $N- NilChk
** $P- PortableCode $R- RangeChk $S= StackChk $T- TypeChk
** $V- OvflChk $Z- ZeroVars
*)
IMPORT E := Exec, D := Dos, WB := Workbench, SYS := SYSTEM;
TYPE
ArgVPtr *= POINTER TO ARRAY OF E.STRPTR;
VAR
IsCLI * : BOOLEAN;
(*
* TRUE = program started from CLI, FALSE = program started from
* Workbench
*)
argc * : LONGINT;
(* Number of arguments passed by CLI *)
argv * : ArgVPtr;
(*
* Array of argument strings passed by CLI.
* argv [0] is always the name of the program.
*)
NumArgs * : LONGINT;
(* Number of arguments passed by Workbench *)
ArgList * : WB.WBArgumentsPtr;
(* Array of WBArg structures passed by Workbench *)
DosCmdLen * : LONGINT;
(* Length of the command string passed by the CLI *)
DosArgs * : E.STRPTR;
(* The actual command string passed by the CLI; !! DO NOT CHANGE !! *)
argCopy : E.STRPTR;
(* Copy of the command string passed by the CLI *)
startDir : D.FileLockPtr;
(*------------------------------------*)
PROCEDURE GetArgs ();
VAR argLen : LONGINT; args : E.APTR;
(*------------------------------------*)
PROCEDURE CliArgs ();
VAR index, index2 : LONGINT; nameLen : INTEGER;
process : D.ProcessPtr; prCLI : D.CommandLineInterfacePtr;
BEGIN (* CliArgs *)
IsCLI := TRUE; NumArgs := 0; ArgList := NIL;
argCopy := NIL; argc := 1; (* First arg is always program name *)
DosCmdLen := argLen; DosArgs := args;
IF DosCmdLen > 0 THEN
(* Make a copy of the command string *)
SYS.NEW (argCopy, SYS.STRLEN (DosArgs^) + 1);
COPY (DosArgs^, argCopy^);
(*
* Scan the copy, planting a NUL at the end of each argument and
* keeping a count of the arguments found;
*)
index := 0;
LOOP
IF index >= DosCmdLen THEN (* last argument found *) EXIT END;
(* Kill any leading spaces *)
WHILE argCopy [index] = " " DO
argCopy [index] := 0X; INC (index)
END;
IF argCopy [index] = 22X THEN (* a quoted argument *)
(* zap the quote *)
argCopy [index] := 0X; INC (index);
(* scan for the next quote *)
WHILE argCopy [index] # 22X DO INC (index) END;
(* zap it too *)
argCopy [index] := 0X; INC (index);
INC (argc)
ELSIF argCopy [index] > " " THEN (* an unquoted argument *)
(* scan for the end of the argument *)
WHILE argCopy [index] > " " DO INC (index) END;
(* mark it *)
argCopy [index] := 0X; INC (index);
INC (argc)
ELSE
(*
* This is probably a dummy "\n" at the end of an empty command
* line.
*)
argCopy [index] := 0X; INC (index)
END; (* IF *)
END; (* LOOP *)
(* Allocate the argv array *)
NEW (argv, argc + 1);
IF argc > 0 THEN (* Fill argv with pointers to arguments *)
index := 0; index2 := 1;
WHILE index2 < argc DO
WHILE argCopy [index] = 0X DO INC (index) END;
argv [index2] := SYS.ADR (argCopy [index]);
INC (index2);
WHILE argCopy [index] # 0X DO INC (index) END
END; (* WHILE *)
END; (* IF *)
(* Terminate it with a NIL *)
argv [argc] := NIL
ELSE
(* Create a dummy entry for argv *)
NEW (argv, 2);
argv [1] := NIL
END; (* ELSE *)
(* Get the command name *)
process := SYS.VAL (D.ProcessPtr, E.base.FindTask (NIL));
nameLen := ORD (process.cli.commandName [0]);
SYS.NEW (argv [0], nameLen + 1, {E.memClear});
SYS.MOVE (SYS.ADR (process.cli.commandName [1]), argv [0], nameLen);
(* argv [0, nameLen] := 0X; *)
startDir := NIL
END CliArgs;
(*------------------------------------*)
PROCEDURE WBArgs ();
VAR wbMsg : WB.WBStartupPtr;
BEGIN (* WBArgs *)
IsCLI := FALSE; argc := 0; argv := NIL;
DosCmdLen := 0; DosArgs := NIL; argCopy := NIL;
wbMsg := args;
NumArgs := wbMsg.numArgs; ArgList := wbMsg.argList;
IF NumArgs = 1 THEN
startDir := D.base.CurrentDir (ArgList [0].lock)
ELSE
startDir := D.base.CurrentDir (ArgList [1].lock)
END
END WBArgs;
BEGIN (* GetArgs *)
SYS.ARGLEN (argLen); SYS.ARGS (SYS.VAL (LONGINT, args));
IF argLen >= 0 THEN CliArgs ()
ELSE WBArgs ()
END
END GetArgs;
(*------------------------------------*)
PROCEDURE* Cleanup ();
BEGIN (* Cleanup *)
IF startDir # NIL THEN startDir := D.base.CurrentDir (startDir) END
END Cleanup;
BEGIN (* Args *)
GetArgs ();
SYS.SETCLEANUP (Cleanup)
END Args.