(*##########################################################################

              MagicAppl:    Basisfunktionen einer Applikation

  ##########################################################################
  V2.01  27.01.91  Jens Pirnay          ARGV wird untersttzt
  V2.00  17.10.90  Peter Hellinger      Anpassung an neues MagicSys
                                        Die Implementationen fr Megamax und
                                        TDI-Modula unterscheiden sich nur 
                                        noch durch Compilerswitches.
  V1.03  18.08.90  Peter Hellinger
  V1.02  14.08.90  Peter Hellinger
  V1.01  16.07.90  Peter Hellinger       
  V1.00  14.05.90  Peter Hellinger       Implementation TDI-Modula-2
  ##########################################################################*)

IMPLEMENTATION MODULE mtAppl;

(*------------------------------*)
(*       COMPILERSWITCHES       *)
(*------------------------------*)
(*  TDI-Version:   DEAKTIVIERT  *)
(*------------------------------*)
(* V-  Overflow-Checks          *)
(* R-  Range-Checks             *)
(* S-  Stack-Check              *)
(* N-  NIL-Checks               *)
(* T-  TDI-Compiler vor 3.01    *)
(* Q+  Branch statt Jumps       *)
(*                              *)
(*------------------------------*)
(*  MM2-Version:   DEAKTIVIERT  *)
(*------------------------------*)
(*$R-   Range-Checks            *)
(*$S-   Stack-Check             *)
(*                              *)
(*------------------------------*)


FROM SYSTEM     IMPORT  ADDRESS, ADR, LONGWORD, BYTE, TSIZE;
FROM Storage    IMPORT  ALLOCATE, DEALLOCATE;
FROM MagicVDI   IMPORT  UnloadFonts, SetTextface, SetCharpoints,
                        InqFacename, SetTexteffect, InqTextextent, InqText; 
FROM MagicSys   IMPORT  Nil, Null, Bit0, Bit1, Bit2, Bit3, Bit4, Bit5, Bit6, Bit7,
                        Bit8, Bit9, Bit10, Bit11, Bit12, Bit13, Bit14, Bit15,
                        LOC, Byte, ByteSet, sWORD, sINTEGER, sCARDINAL, sBITSET,
                        lWORD, lINTEGER, lCARDINAL, lBITSET,
                        CastToChar, CastToByte, CastToByteset, CastToInt,
                        CastToCard, CastToBitset, CastToWord, CastToLInt,
                        CastToLCard, CastToLBitset, CastToLWord, CastToAddr,
                        Terminate, Basepage;
FROM MagicStrings  IMPORT  Append, Assign, Length;
IMPORT  MagicTypes, MagicAES, MagicVDI, MagicDOS, MagicBIOS, MagicSys;

(*--------------------------------------------------------------------------*)

CONST   cFonts =        0;
        cOpen =         1;
        ABCGEM =        0210H;


TYPE    WsPtr =         POINTER TO WsInfo;
        WsInfo =        RECORD
                         handle: sINTEGER;
                         flags:  sBITSET;
                         next:   WsPtr;
                        END;


TYPE    TermPtr =       POINTER TO TermInfo;
        TermInfo =      RECORD
                         proc:  PROC;
                         next:  TermPtr;
                        END;


VAR     WorkInArray:    MagicVDI.tWorkIn;
        WorkOutArray:   MagicVDI.tWorkOut;
        applpath:       ARRAY [0..255] OF CHAR;

VAR     WorkStation:    WsPtr;
        TermProc:       TermPtr;

VAR     pCount:         sINTEGER;
        ProgReturn:     sINTEGER;
        stack:          ADDRESS;
        BasePage:       MagicBIOS.PtrPD;
        Maus:           BOOLEAN; 
        MausForm:       sINTEGER;
        Usermaus:       ADDRESS;
        GEMversion:     sINTEGER;
        gdos:           BOOLEAN;
        argv:           BOOLEAN;
        argpos:         sINTEGER;
        cmdline:        ARRAY [0..127] OF CHAR;


PROCEDURE ApplInit;
VAR i: sINTEGER;
BEGIN
 (* Applikation anmelden *)
 ApplIdent:= MagicAES.ApplInit ();
 IF ApplIdent < 0 THEN  HALT; END;
 (* Eine Workstation ”ffnen *)
 VDIHandle:= OpenWorkstation();
 (* Gesamtbreite und H”he des Bildschirms *)
 MaxWidth:= WorkOutArray[0] + 1;
 MaxHeight:= WorkOutArray[1] + 1;
 Bitplanes:= MagicAES.AESGlobal.apNplanes;
 GEMversion:= MagicAES.AESGlobal.apVersion;
 IF GEMversion # ABCGEM THEN  gdos:= MagicSys.VqGdos();
                        ELSE  gdos:= TRUE;
 END;
 Maus:= TRUE;  MausForm:= MagicAES.ARROW;  MouseOn;
END ApplInit;


PROCEDURE InstallTermproc (proc: PROC);
VAR p: TermPtr;

 PROCEDURE new (): TermPtr;
 VAR q: TermPtr;
 BEGIN
  NEW (q);
  IF q = NIL THEN  HALT;  END;
  q^.proc:= proc;
  q^.next:= NIL;
  RETURN q;
 END new;

BEGIN
 IF TermProc = NIL THEN
  TermProc:= new ();
 ELSE
  p:= TermProc;
  WHILE p^.next # NIL DO  p:= p^.next;  END;
  p^.next:= new ();
 END;
END InstallTermproc;


PROCEDURE ApplTerm (return: sINTEGER);
VAR  p: TermPtr;
     q: WsPtr;
     i: sINTEGER;
BEGIN
 (* Installierte TermProcedures abarbeiten *)
 p:= TermProc;
 WHILE (p # NIL) DO  p^.proc;  p:= p^.next;  END;
 (* Cursor wieder sichtbar machen *)
 MagicVDI.ShowCursor (VDIHandle, TRUE);
 q:= WorkStation;
 WHILE (q # NIL) DO
  IF cFonts IN q^.flags THEN  MagicVDI.UnloadFonts (q^.handle, 0);  END;
  MagicVDI.CloseVirtual (q^.handle);
  q:= q^.next;
 END; (* WHILE *)
 MagicAES.ApplExit;
 Terminate (return);
END ApplTerm;


PROCEDURE ApplPath (VAR pfad: ARRAY OF CHAR);
BEGIN
 Assign (applpath, pfad);
END ApplPath;


PROCEDURE OpenWorkstation (): sINTEGER;
VAR h, i: sINTEGER;
    p:    WsPtr;

 PROCEDURE new (handle: sINTEGER; flags: BITSET): WsPtr;
 VAR q: WsPtr;
 BEGIN
  NEW (q);
  IF q = NIL THEN  HALT;  END;
  q^.handle:= handle;
  q^.flags:=  flags;
  q^.next:=   NIL;
  RETURN q;
 END new;

BEGIN
 (* Handle der physikalischen Workstation ermitteln *)
 MagicAES.GrafHandle (h, i, i, i, i);
 IF h < 0 THEN  HALT;  END;
 WorkInArray[ 0]:= 1;  (* Aktuelle Aufl”sung                *)
 WorkInArray[ 1]:= 1;  (* Linientyp, durchgehender Strich   *)
 WorkInArray[ 2]:= 1;  (* Liniefarbe, schwarz               *)
 WorkInArray[ 3]:= 1;  (* Markertyp, Punkt                  *)
 WorkInArray[ 4]:= 1;  (* Markerfarbe, schwarz              *)
 WorkInArray[ 5]:= 1;  (* Textfont, Systemzeichensatz       *)
 WorkInArray[ 6]:= 1;  (* Textfarbe, schwarz                *)
 WorkInArray[ 7]:= 1;  (* Flltyp, voll                     *)
 WorkInArray[ 8]:= 1;  (* Musterindex,                      *)
 WorkInArray[ 9]:= 1;  (* Musterfarbe, schwarz              *)
 WorkInArray[10]:= 2;  (* RC-Koordinatensystem              *)
 (* Virtuelle Workstation ”ffnen *)
 MagicVDI.OpenVirtual (WorkInArray, h, WorkOutArray);
 IF h < 0 THEN  HALT;  END;
 IF WorkStation = NIL THEN
  WorkStation:= new (h, {cOpen});
 ELSE
  p:= WorkStation;
  WHILE p^.next # NIL DO  p:= p^.next;  END;
  p^.next:= new (h, {cOpen});
 END;
 RETURN h;
END OpenWorkstation;


PROCEDURE GetWS (handle: sINTEGER): WsPtr;
VAR p: WsPtr;
BEGIN
 p:= WorkStation;
 WHILE p # NIL DO
  IF p^.handle = handle THEN  RETURN p;  END;
  p:= p^.next;
 END;
 RETURN NIL;
END GetWS;


PROCEDURE CloseWorkstation (handle: sINTEGER);
VAR p, q: WsPtr;
BEGIN
 p:= GetWS (handle);
 IF p # NIL THEN
  IF cOpen IN p^.flags THEN
   IF cFonts IN p^.flags THEN  UnloadFonts (p^.handle, 0);  END;
   MagicVDI.CloseVirtual (p^.handle);
   EXCL (p^.flags, cOpen);
  END;
 END; (* IF *)
END CloseWorkstation;


(*----------------------------------------------------------------------*
 *                            M„usetreiberei                            *
 *----------------------------------------------------------------------*)

PROCEDURE MouseOn;
BEGIN
 IF NOT Maus THEN
  Maus:= TRUE;
  MagicVDI.ShowCursor (VDIHandle, FALSE);
 END;
 IF MausForm = MagicAES.USERDEF THEN
  MagicAES.GrafMouse (MausForm, Usermaus);
 ELSE
  MagicAES.GrafMouse (MausForm, Nil);
 END;
END MouseOn;


PROCEDURE MouseArrow;
BEGIN
 MausForm:= MagicAES.ARROW;  MouseOn;
END MouseArrow;


PROCEDURE MouseCursor;
BEGIN
 MausForm:= MagicAES.TEXTCRSR;  MouseOn;
END MouseCursor;


PROCEDURE MouseBusy;
BEGIN
 MausForm:= MagicAES.BUSYBEE;  MouseOn;
END MouseBusy;


PROCEDURE MouseFinger;
BEGIN
 MausForm:= MagicAES.POINTHAND;  MouseOn;
END MouseFinger;


PROCEDURE MouseHand;
BEGIN
 MausForm:= MagicAES.FLATHAND;  MouseOn;
END MouseHand;


PROCEDURE MouseThincross;
BEGIN
 MausForm:= MagicAES.THINCROSS;  MouseOn;
END MouseThincross;


PROCEDURE MouseThickcross;
BEGIN
 MausForm:= MagicAES.THICKCROSS;  MouseOn;
END MouseThickcross;


PROCEDURE MouseOutline;
BEGIN
 MausForm:= MagicAES.OUTLCROSS;  MouseOn;
END MouseOutline;


PROCEDURE MouseUser;
BEGIN
 MausForm:= MagicAES.USERDEF;  MouseOn;
END MouseUser;


PROCEDURE MouseOff;
BEGIN
 IF Maus THEN
  Maus:= FALSE;
  MagicVDI.HideCursor (VDIHandle);
 END;
END MouseOff;


PROCEDURE UserMouse (VAR form: MFORM);
BEGIN
 Usermaus:= ADR(form);
END UserMouse;



(*--------------------------------------------------------------------------*
 *                              Font-Handling                               *
 *--------------------------------------------------------------------------*)

CONST   MaxFont =       100;
        MaxSizes =       30;

TYPE    FONT =          RECORD
                         id:     sINTEGER;        (* Font-ID *)
                         name:   ARRAY [0..32] OF CHAR;  (* Name des Fonts *)
                         mono:   BOOLEAN;        (* Monospaced *)
                         min:    sINTEGER;        (* Minimale Gr”že *)
                         max:    sINTEGER;        (* Maximale Gr”že *)
                         fsize:  sINTEGER;        (* Aktuelle Gr”že *)
                         sTab: ARRAY [0..MaxSizes] OF sINTEGER;
                        END;

TYPE    Fontlist =      POINTER TO ARRAY [SystemFont..MaxFont] OF FONT;


VAR     Font:           Fontlist;
        NumFonts:       sINTEGER;
        init:           BOOLEAN;



PROCEDURE VqGdos (): BOOLEAN;
BEGIN 
 RETURN gdos;
END VqGdos;


PROCEDURE FontCode (id: sINTEGER): sINTEGER;
VAR i: sINTEGER;
BEGIN
 IF Font # NIL THEN
  FOR i:= 1 TO NumFonts DO
   IF Font^[i].id = id  THEN  RETURN i;  END;
  END;
 ELSE
  RETURN SystemFont;
 END;
END FontCode;


PROCEDURE LoadFonts (handle: sINTEGER): sINTEGER;
VAR f, i, j, d, c: sINTEGER;
    b:          sBITSET;
    e1, e2:     ARRAY [0..7] OF sINTEGER;
    p:          WsPtr;
BEGIN
 f:= 0;
 IF gdos THEN
  p:= GetWS (handle);
  IF p = NIL THEN  RETURN -4;  END;
  IF NOT (cFonts IN p^.flags) THEN
   NumFonts:= MagicVDI.LoadFonts (p^.handle, 0);
   IF NumFonts < 1 THEN  RETURN -2;  END;
   INCL (p^.flags, cFonts);
   ALLOCATE (Font, LONG(TSIZE(FONT) * NumFonts));
   IF Font = NIL THEN  UnloadFonts (handle, 0);  RETURN -3;  END;
   FOR i:= 1 TO NumFonts DO
    WITH Font^[i] DO
     IF i = 1 THEN  (* Sonderbehandlung fr Systemfont *)
      id:= 1;
      name:= 'Systemfont';
      mono:= TRUE;
      j:= SetTextface (p^.handle, id);
      sTab[0]:= SetCharpoints (p^.handle, 32656, c, c, c, c);
      j:= 1;  
      LOOP
       sTab[j]:= SetCharpoints (p^.handle, sTab[j-1]-1, c, c, c, c);
       IF sTab[j] = sTab[j-1] THEN  sTab[j]:= 0;  EXIT;  END;
       INC (j);
       IF j > (MaxSizes - 1) THEN sTab[MaxSizes]:= 0;  EXIT;  END;
      END;
      max:= 0;  min:= j - 1;
      IF Bitplanes > 1 THEN  fsize:= 9;  ELSE  fsize:= 10;  END;
     ELSE
      id:= InqFacename (p^.handle, i, name);
      j:=  SetTextface (p^.handle, id);
      b:=  SetTexteffect (p^.handle, {});
      InqTextextent (p^.handle, 'AzByCxDwEvFuGtHsIrJqKpLoMn01234', e1);
      InqTextextent (p^.handle, 'NmOlPkQjRiShTgUfVeWdXcYbZa56789', e2);
      mono:= (e1[0] = e2[0]) AND (e1[1] = e2[1]) AND
             (e1[2] = e2[2]) AND (e1[3] = e2[3]) AND
             (e1[4] = e2[4]) AND (e1[5] = e2[5]) AND
             (e1[6] = e2[6]) AND (e1[7] = e2[7]);
      sTab[0]:= SetCharpoints (p^.handle, 32656, c, c, c, c);
      j:= 1;  
      LOOP
       sTab[j]:= SetCharpoints (p^.handle, sTab[j-1]-1, c, c, c, c);
       IF sTab[j] = sTab[j-1] THEN  sTab[j]:= 0;  EXIT;  END;
       INC (j);
       IF j > (MaxSizes - 1) THEN sTab[MaxSizes]:= 0;  EXIT;  END;
      END;
      max:= 0;  min:= j - 1;  
      fsize:= SetCharpoints (p^.handle, sTab[min], c, c, c, c);
     END;  (* IF *)
    END;  (* WITH *)
   END;  (* FOR *)
   (* Systemfont wieder einstellen *)
   j:= SetTextface (p^.handle, 1);
   b:= SetTexteffect (p^.handle, {});
   IF Bitplanes > 1 THEN  d:= 9;  ELSE  d:= 10;  END;
   j:= SetCharpoints (p^.handle, d, c, c, c, c);
  END;
  RETURN  0;
 END;
 RETURN -1;
END LoadFonts;


PROCEDURE FreeFonts (handle: sINTEGER);
VAR p: WsPtr;
BEGIN
 p:= GetWS (handle);
 IF p # NIL THEN
  IF cFonts IN p^.flags THEN  UnloadFonts (handle, 0);  END;
 END;
END FreeFonts;


PROCEDURE FontNumber(): sINTEGER;
BEGIN
 RETURN NumFonts;
END FontNumber;


PROCEDURE SelectFont (handle, font: sINTEGER; VAR size: sINTEGER);
VAR i:   sINTEGER;
BEGIN
 IF (font < 0) OR (font > NumFonts)  THEN font:= 1;  END;
 IF Font # NIL THEN
  WITH Font^[font] DO
   i:= SetTextface (handle, id);
   fsize:= SetCharpoints (handle, fsize, i, i, i, i);
   size:= fsize;
  END;
 END;
END SelectFont;


PROCEDURE ScaleFont (handle, siz: sINTEGER; VAR width, height: sINTEGER): sINTEGER;
VAR i, j, f: sINTEGER;
    att:  ARRAY [0..9] OF sINTEGER;
    p:    WsPtr;
BEGIN
 p:= GetWS (handle);
 IF p = NIL THEN   RETURN -1;  END;
 InqText (handle, att);
 f:= FontCode (att[0]);
 i:= SetCharpoints (handle, siz, j, j, j, j);
 IF Font # NIL THEN  Font^[f].fsize:= i;  END;
 InqText (handle, att);
 width:= att[8];  height:= att[9];
 RETURN i;
END ScaleFont;


PROCEDURE Monospaced (font: sINTEGER): BOOLEAN;
BEGIN
 IF (font < 0) AND (font > NumFonts)  THEN font:= 1;  END;
 IF Font # NIL THEN
  RETURN Font^[font].mono;
 ELSE
  RETURN TRUE; (* Systemfont ist monospaced *)
 END;
END Monospaced;


PROCEDURE PossibleSize (font: sINTEGER; VAR sizearray: ARRAY OF sINTEGER);
VAR i, j, h, m: sINTEGER;
BEGIN
 IF (font < 0) AND (font > NumFonts)  THEN font:= 1;  END;
 IF Font # NIL THEN
  WITH Font^[font] DO
   h:= CastToInt (HIGH(sizearray));
   IF min > h THEN  m:= h - 1;  ELSE  m:= min + 1;  END;
   j:= max;
   FOR i:= max TO m DO  sizearray[i]:= sTab[i];  INC(j);  END;
   sizearray[j]:= 0;
  END;
 ELSE
  sizearray[0]:= 0;
 END;
END PossibleSize;


PROCEDURE FontInfo (handle, font: sINTEGER; VAR rname: ARRAY OF CHAR;
                    VAR rid, rsize, rmin, rmax: sINTEGER);
VAR p:   WsPtr;
BEGIN
 p:= GetWS (handle);
 IF p = NIL THEN   RETURN;  END;
 IF (font < 0) AND (font > NumFonts)  THEN font:= 1;  END;
 IF Font # NIL THEN
  WITH Font^[font] DO
   Assign (name, rname);
   rid:= id;  rmin:= sTab[min];  rmax:= sTab[max];  rsize:=  fsize;
  END;
 ELSE
  Assign ('Systemfont', rname);
  rid:= 1;  rmin:= 8;  rmax:= 20;
  IF Bitplanes > 1 THEN  rsize:= 9;  ELSE  rsize:= 10;  END;  
 END;
END FontInfo;


(*--------------------------------------------------------------------------*
 *                    fertig konfigurierte Alert-Messages                   *
 *--------------------------------------------------------------------------*)

VAR alert:  ARRAY [0..199] OF CHAR;
    i:      sINTEGER;


PROCEDURE DoAlert (vor, str, nach: ARRAY OF CHAR; wich: sINTEGER): sINTEGER;
BEGIN
 Assign(vor, alert);
 IF Length (str) < 90 THEN  Append(' | |', alert);  END;
 Append(str, alert);
 Append(nach, alert);
 MagicVDI.ShowCursor (VDIHandle, TRUE);
 i:= MagicAES.FormAlert (wich, alert);
 RETURN i;
END DoAlert;


PROCEDURE Message (m: ARRAY OF CHAR);
VAR i: sINTEGER;
BEGIN
 i:= DoAlert('[3][', m, '][ OK ]', 1);
END Message;


PROCEDURE Question (default: sCARDINAL; m: ARRAY OF CHAR): BOOLEAN;
BEGIN
 RETURN  DoAlert ('[1][', m, '][ JA | NEIN ]', default) = 1;
END Question;


PROCEDURE Select (default: sCARDINAL; m: ARRAY OF CHAR): CARDINAL;
BEGIN
 RETURN  DoAlert ('[1][', m, '][ JA | NEIN | ABBRUCH ]', default);
END Select;


PROCEDURE ParamCount (): sINTEGER;
BEGIN
 RETURN pCount;
END ParamCount;

 PROCEDURE ParamString (n: sINTEGER; VAR arg: ARRAY OF CHAR);
 VAR i, j, c, d, p, l: sINTEGER;
     cpointer : POINTER TO ARRAY [0..2047] OF CHAR;
     out      : ARRAY [0..255] OF CHAR;
     BP       : MagicBIOS.PtrPD;
 
  PROCEDURE pAssign;
  VAR d : INTEGER;
  BEGIN
   d:= 0;
   WHILE (cmdline[c] # 0C) AND (cmdline[c] # ' ') AND (c <= 126) DO
     arg[d]:= cmdline[c];  
     INC (c);  
     INC (d);
   END;
   arg[d]:= 0C;
 (**  
   RTD.Message(arg);
 **)  
  END pAssign;
 
 BEGIN
   BP := Basepage ();
   IF argv THEN
     cpointer := BP^.pEnv;
     arg[0] := 0C;
     IF (n<0) OR (n>pCount) THEN
       RETURN;
      ELSE
       i := argpos;
       FOR j:=0 TO n DO
         WHILE (cpointer^[i]<>0C) DO
           INC(i);
         END;
         INC(i);
       END;
       j := 0;
       REPEAT
         arg[j] := cpointer^[i];
         INC(j);
         arg[j] := 0C;
         INC(i);
       UNTIL cpointer^[i] = 0C;
     END;
    ELSE
     p:= 0;  c:= 0;  l:= Length(cmdline); arg[0]:= 0C;  DEC (n);
     IF n>=0 THEN
       WHILE (c<l) AND (cmdline[c] = ' ') DO
         INC(c);
       END;
       LOOP
         IF n = p THEN  pAssign;  RETURN  END;
         IF (cmdline[c] = 0C) OR (c > 126) OR (c=l) THEN  EXIT  END;
         IF (cmdline[c] = ' ') THEN
           INC (p);
           WHILE (cmdline[c+1] = ' ') DO
             INC(c);
           END;
         END;
         INC (c);
       END;
     END;
   END;
 
 END ParamString;
 
 PROCEDURE GetARGV;
 (* Suche im Environment nach ARGV *)
 VAR cpointer : POINTER TO ARRAY [0..1023] OF CHAR;
     BP       : MagicBIOS.PtrPD;
     found    : BOOLEAN;
     i, j     : INTEGER;
 BEGIN
   BP := Basepage ();
   cpointer := BP^.pEnv;
   i := 0;
   found := FALSE;
   pCount := -2; (* Da zwei 0C zu viel *)
   WHILE NOT found AND ((cpointer^[i]<>0C) OR (cpointer^[i+1]<>0C)) DO
     IF (cpointer^[i]   = 'A') AND
        (cpointer^[i+1] = 'R') AND
        (cpointer^[i+2] = 'G') AND
        (cpointer^[i+3] = 'V') AND
        (cpointer^[i+4] = '=') THEN
       argpos := i;
       REPEAT
         INC(i);
         IF cpointer^[i]=0C THEN
           INC(pCount);
         END;
       UNTIL (cpointer^[i]=0C) AND (cpointer^[i+1]=0C);
       found := TRUE;
     END;
     INC(i);
   END;
   IF pCount<0 THEN pCount := 0; END;
 END GetARGV;
 
 VAR c, l, len, drv:  CARDINAL;
     slash:      ARRAY [0..1] OF CHAR;
     p:          ARRAY [0..255] OF CHAR;
 
 
 BEGIN
  (* Applikation und Workstation initialisieren *)
  Font:= NIL;  NumFonts:= 1;  WorkStation:= NIL;  TermProc:= NIL;
  Maus:= FALSE;  MausForm:= MagicAES.ARROW;
  ApplInit;
 
  (* Basepage auslesen *)
  BasePage:= Basepage ();
  len := ORD(BasePage^.pCmdlin[0]);
  pCount := 0;
  argv := FALSE;
  IF (len>0) AND (len<127) THEN
    FOR l:=1 TO len DO
      cmdline[l-1] := BasePage^.pCmdlin[l];
    END;
    cmdline[len] := 0C;
    l := 1;
    WHILE (l<=len) AND (BasePage^.pCmdlin[l] = ' ') DO
      INC(l, 1);
    END;
    IF (l<=len) THEN
      pCount := 1;
    END;
    WHILE (l<=len) DO
      IF (BasePage^.pCmdlin[l] = ' ') THEN
        INC (pCount);
        (* So werden mehrere Leerzeichen hintereinander unterdrckt *)
        WHILE (l<=len) AND (BasePage^.pCmdlin[l+1] = ' ') DO
          INC(l, 1);
        END;
      END;
      INC(l, 1);
    END;
   ELSIF len=127 THEN
    (* ARGV-Methode *)
    argv := TRUE;
    GetARGV;
  END;
 (**
  RTD.SetDevice(RTD.printer);
  RTD.ShowVar('Len', len);
  RTD.ShowVar('pcount', pCount);
  RTD.ShowVar('argv', argv);
  RTD.Message(cmdline);
 **) 
 (* Programmpfad feststellen *)
 slash[0]:= '\';
 drv:= MagicDOS.Dgetdrv ();
 applpath[0]:= CHR (ORD ('A') + drv);
 applpath[1]:= ':';
 applpath[2]:= 0C;
 MagicDOS.Dgetpath (p, drv + 1);
 Append (p, applpath);
 Append (slash, applpath);
END mtAppl.
