{$S128}
PROGRAM disk_engineer ;

  CONST
    {$I GEMCONST.PAS}
    did        = ' DISK INSIDE DRIVE ';             { spart Platz }

  TYPE
    {$I GEMTYPE.PAS}
    fdescript  =  packed array [1..32] of char;     { einzelner DIR-Eintrag }
    dir_point  =  ^dir_buff;                        { Zeiger zu dir_buff }
    dir_buff   =  RECORD
                    parameter : array [1..16] of fdescript;
                  END;                              { einzelne DIR-Seite }
    tr_buff    =  packed array [0..10240] of byte;  { ganzer Track ppig }
    sector     =  packed array [0..511] of byte;    { einzelner Sektor }
    sc_point   =  ^sc_buff;                         { Zeiger zu sc_buff }
    sc_buff    =  RECORD
                    parameter : sector;
                  END;
                  { als RECORD angelegt um mit  -do with- arbeiten zu k”nnen }
    fat_type   =  packed array [0..5260] of byte;   { nur fr FAT }
    zeilenfeld =  array [1..18] of string[80];      { Arrays fr Schleifen- }
    kzfeld     =  array [1..18] of byte;            { bildung im Dialogtree }
    int40      =  array [1..40] of integer;
    intstr     =  string[5];

  VAR
    directory                    : array [1..512] of char;
    dirbuf                       : dir_point;
    scbuf                        : sc_point;
    errstr                       : string;
    fat                          : fat_type;      { Global fr FAT }
    ens                          : intstr;        { Hilfsvariable fr VAL }
    act_sd, act_tr, act_sc,
    act_fl, act_to, act_so,
    act_bs, act_cl, act_de,
    act_fc, act_fs, act_hd,
    act_rs, act_md, act_bf,                       { BPB fr Default-Drive }
    button, device, errnr, menu,                  { Global fr Responses  }
    ok_btn, cancel_btn           : integer;
    act_sr                       : long_integer;  { noch zu BPB }

    {$I GEMSUBS}

  PROCEDURE Cconout( x : char );
    GEMDOS($02);

  { graf_text gibt ber LineA-PutChar Textzeile aus }

  PROCEDURE graf_text(x,y,s,g:integer;zeile:string);
    VAR  ig,wg :integer;
    BEGIN
      wg:=10;
      if s=0 then wg:=6;
      if s=1 then wg:=8;
      for ig:=1 to length(zeile) do put_char(zeile[ig],x+ig*wg,y,s,g,0);
    END;

  { clrscr L”scht das Display ganz und schreibt einen copyright-Vermerk }

  PROCEDURE clrscr;
    BEGIN
      Hide_Mouse;
      Cconout( chr(27) );
      Cconout( chr(69) );
      graf_text(70,2,2,16,'DISK ENGINEER 3.01 int.    (c)1986 by A.Vollmer');
      graf_text(200,140,2,16,'     PLEASE WAIT');
      graf_text(200,160,2,16,'BACKGROUND EXECUTION');
      graf_text(200,180,2,16,'    NO DATA SHOWN');
      Show_Mouse;
    END;

  { str wandelt eine integer-Variable in einen 5-stelligen string um }

  PROCEDURE str( zahl : integer; VAR zs : intstr );
  VAR z      : array [1..5] of integer;
      x,i,zd : integer;
  BEGIN
    zahl:=abs(zahl); zs:=''; zd:=0;
    for i:=1 to 5 do
    begin
      x:=trunc(PwrOfTen(5-i));
      z[i]:=zahl div x;
      zd:=zd+z[i];
      zahl:=zahl-(z[i]*x);
      if zd>0 then
        zs:=concat(zs,chr(z[i]+48))
      else
        zs:=concat(zs,' ');
      end;
    END;

  { adr_sc rechnet einen logischen Sektor-Pointer in eine physikalische
    Adresse um, SS und DS werden bercksichtigt                         }

  PROCEDURE adr_sc( sc_abs : integer; VAR sd1,tr1,sc1 : integer );
  BEGIN
    sc_abs:=sc_abs+1;                 { min Sektor-Nr. ist 1 nicht 0 }
    if act_sd<1 then act_sd:=1;
    if act_sd>2 then act_sd:=2;       { Bl”dsinn eliminieren }
    tr1:=sc_abs div act_sc;           { Tracknr. isolieren }
    sc1:=sc_abs mod act_sc;           { 'Angebrochener' Track }
    if sc1=0 then tr1:=tr1-1;         { Sektor 0 gibts nicht }
    if sc1=0 then sc1:=act_sc;        { ist daher max Sektor im niedrigen Tr }
    CASE act_sd OF

      1  :  begin
              sd1:=0;                 { eine Seite alles klar }
            end;

      2  :  begin
              sd1:=(tr1+1) mod 2;     { ungerade Vorderseite }
              tr1:=(tr1-1) div 2;     { gerade R@ckseite }
            end;

      END; { of CASE }
    END;   { of adr_sc }

  { Error_Alert zeigt eine Fehlernummer in einer Alert-Box an }

  PROCEDURE Error_Alert( errnr: integer; VAR taste: integer );
    begin
      Set_Mouse( M_Arrow );
      str(errnr,ens);
      errstr:=concat('[1][DISKERROR No.  ',ens,   '][ CANCEL | OK ]');
      taste:=Do_Alert(errstr,0);
      Set_Mouse( M_Bee );
      clrscr;
    end; { of error_alert   reicht doch fr den Fall der F„lle ? }


  FUNCTION mediach( devno: integer ) : integer;
  BIOS(9);                                        { Disk gewechselt ? }


  FUNCTION drvmap : long_integer;
  BIOS(10);                                       { Welche Drives ?   }


  FUNCTION getRez : integer;
  XBIOS(4);                                       { Welche Aufl”sung ? }

  { Sector-Read mehrfach definiert mit unterschiedlichen Buffer-Types }

  FUNCTION rd_sec( buff   : sc_point;
                   free   : long_integer;
                   devno,sectno,trackno,sideno,count : integer):integer;
  XBIOS(8);


  FUNCTION rd_sec_c( buff   : dir_point;
                     free   : long_integer;
                     devno,sectno,trackno,sideno,count : integer): integer;
  XBIOS(8);


  FUNCTION fatrd(VAR buffer : fat_type;
                     f      : long_integer;
                     drvf, secf, trkf, sdf, ctf : integer):integer;
  XBIOS(8);


  FUNCTION wr_sec_c( buff   : dir_point;
                     free   : long_integer;
                     devno, sectno, trackno, sideno, count : integer): integer;
  XBIOS(9);



  FUNCTION flopfmt( VAR buf    : tr_buff;
                        free   : long_integer;
                        devno,spt,trackno,sideno,interlv : integer;
                        magic  : long_integer;
                        filler : integer ) : integer;
  XBIOS(10);


  FUNCTION rd_bot( VAR buff   : sector;
                       free   : long_integer;
                       devno,sectno,trackno,sideno,count : integer):integer;
  XBIOS(8);


  FUNCTION cr_bot( VAR buff   : sector;
                       serial : long_integer;
                       dtype, exfl : integer):integer;
  XBIOS(18);


  FUNCTION wr_sec( VAR buf    : sector;
                       free   : long_integer;
                       devno,sectno,trackno,sideno,count : integer): integer;
  XBIOS(9);


  FUNCTION setprt( conf : integer ) : integer;
  XBIOS(33);


  PROCEDURE fmtdisk( dev, sttr, endtr, side, filler, sctr : integer );
  VAR  i, btn,
       headl, erz, btn_st, btn_br,
       t1, t2, t3, terr, tmsg      : integer;
       anz         : string;
       trbuf       : tr_buff;
       dial_ftd    : Dialog_Ptr;
  BEGIN
    erz:=0;
    dial_ftd:= New_Dialog( 12, 0, 0, 40, 15) ;
    anz:=concat('FORMAT OF',did,chr(device+65));
    headl:= Add_DItem( dial_ftd, G_BoxText, None, 2, 1, 36, 2, 2, $11A1 );
    Set_DText(dial_ftd, headl, anz, System_Font, TE_Center);
    Obj_SetState( dial_ftd, headl, Shadowed, False );
    anz:=concat('START TRACK : ',chr(sttr div 10 + 48), chr(sttr mod 10 +48));
    t1:= Add_DItem( dial_ftd, G_Text, None, 8, 4, 16, 1, 0, $1180);
    Set_DText(dial_ftd, t1, anz, System_Font, TE_Left);
    anz:=concat('END TRACK : ',chr(endtr div 10 + 48), chr(endtr mod 10 +48));
    t2:= Add_DItem( dial_ftd, G_Text, None, 10, 5, 14, 1, 0, $1180);
    Set_DText(dial_ftd, t2, anz, System_Font, TE_Left);
    anz:=concat('SIDE : ',chr(side + 48));
    t3:= Add_DItem( dial_ftd, G_Text, None, 15, 6, 8, 1, 0, $1180);
    Set_DText(dial_ftd, t3, anz, System_Font, TE_Left);
    anz:=concat('ERRORS : ',chr(erz div 10 + 48), chr(erz mod 10 + 48));
    terr:= Add_DItem( dial_ftd, G_Text, None, 13, 8, 12, 1, 0, $1180);
    Set_DText(dial_ftd, terr, anz, System_Font, TE_Left);
    btn_st:= Add_DItem( dial_ftd, G_Button, Selectable|Touch_Exit|Exit_Btn,
                        2, 13, 16, 1, 1, $1180);
    Set_DText(dial_ftd, btn_st, 'S T A R T', System_Font, TE_Center);
    btn_br:= Add_DItem( dial_ftd, G_Button, Selectable|Touch_Exit|Exit_Btn,
                        22, 13, 16, 1, 1, $1180);
    Set_DText(dial_ftd, btn_br, 'B R E A K', System_Font, TE_Center);
    anz:='START FORMAT NOW                    ';
    tmsg:= Add_DItem( dial_ftd, G_String, None, 2, 10, 36, 1, 0, $1180);
    Set_DText(dial_ftd, tmsg, anz, System_Font, TE_Left);
    Center_Dialog( dial_ftd );
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_ftd, 0 );
    End_Dialog( dial_ftd );
    clrscr;
    Set_Mouse( M_Bee );
    if btn=btn_st then
    for i:=sttr to endtr do   { formatiere von/bis Track }
      begin
        errnr:= flopfmt( trbuf, 01, dev, sctr, i, side, 1, $87654321, filler);
        if errnr<>0
          then begin          { im Fehlerfall unterbrechen und OP-Info }
            erz:=erz+1;
            Set_DText( dial_ftd, btn_st, 'CONTINUE ', System_Font, TE_Center);
            Obj_SetState( dial_ftd, btn_st, Normal, False );
            anz:=concat('ERRORS : ',chr(erz div 10 + 48),chr(erz mod 10 + 48));
            Set_DText(dial_ftd, terr, anz, System_Font, TE_Left);
            errnr:=abs(errnr);
            anz:=concat('ERROR NO. ',chr(errnr div 10 + 48),
                         chr(errnr mod 10 + 48));
            anz:=concat(anz,' AT TRACK ',chr(i div 10 + 48),
                         chr(i mod 10 + 48),'            ');
            Set_DText( dial_ftd, tmsg, anz, System_Font, TE_Center );
            Set_Mouse( M_Point_Hand );
            btn:=Do_Dialog( dial_ftd, 0 );
            End_Dialog( dial_ftd );
            Set_Mouse( M_Bee );
            clrscr;
            if btn=btn_br then i:=endtr;
            end;
        end;
    errnr:=0;
    Delete_Dialog( dial_ftd );
    clrscr;
    END;

  PROCEDURE cr_boot_sc( dev : integer );
  VAR  i, btn, mxs,
       sd2, tr2, sc2,
       k1, k2, headl,
       btn_st, btn_br,
       btn_md, bexy, bexn : integer;
       tz          : zeilenfeld;
       tk          : kzfeld;
       buffer      : sector;
       anz         : string;
       dial_bot    : Dialog_Ptr;

  BEGIN
    act_fc:=2;
    mxs:=1;
    dial_bot:= New_Dialog( 30, 0, 0, 64, 15) ;
    anz:=concat('CREATE VOLUME INFORMATION FOR',did,chr(dev+65));
    headl:= Add_DItem( dial_bot, G_BoxText, Selectable|Exit_Btn,
                       2, 1, 60, 2, 2, $11A1 );
    Set_DText(dial_bot, headl, anz, System_Font, TE_Center);
    Obj_SetState( dial_bot, headl, Shadowed, False );
    tz[1]:=concat('               FATs :   ',chr(act_fc + 48),'   ');
    tz[2]:=concat('         SECTOR/FAT :   ',chr(act_fs + 48),'   ');
    mxs:=mxs+act_fc*act_fs;
    if act_de=128 then tz[3]:='  DIRECTORY/ENTRIES : 128';
    if act_de=128 then mxs:=mxs+8;
    if act_de=112 then tz[3]:='  DIRECTORY/ENTRIES : 112';
    if act_de=112 then mxs:=mxs+7;
    if act_de=64  then tz[3]:='  DIRECTORY/ENTRIES :  64';
    if act_de=64  then mxs:=mxs+4;
    tz[4]:='        BYTE/SECTOR : 512';
    tz[5]:=concat('       SECTOR/TRACK :  ',chr(act_sc div 10 +48),
                  chr(act_sc mod 10 +48) );
    tz[6]:=concat('     SECTOR/CLUSTER :   ',chr(act_cl + 48));
    tz[7]:=concat('         TRACK/SIDE :  ',chr(act_tr div 10 +48),
                  chr(act_tr mod 10 +48) );
    tz[8]:=concat('          SIDE/DISK :   ',chr(act_sd + 48));
    for i:=1 to 8 do
      begin
        tk[i]:= Add_DItem( dial_bot, G_Text, None, 2, (3+i), 30, 1, 0, $1180);
        Set_DText( dial_bot, tk[i], tz[i], System_Font, TE_Left);
        end;
    btn_st:= Add_DItem( dial_bot, G_Button, Exit_Btn|Selectable,
                        2, 13, 18, 1, 0, $1180);
    Set_DText( dial_bot, btn_st, 'C R E A T E', System_Font, TE_Center);
    btn_br:= Add_DItem( dial_bot, G_Button, Exit_Btn|Selectable,
                        23, 13, 18, 1, 0, $1180);
    Set_DText( dial_bot, btn_br, 'C A N C E L', System_Font, TE_Center);
    btn_md:= Add_DItem( dial_bot, G_Button, Exit_Btn|Selectable,
                        44, 13, 18, 1, 0, $1180);
    Set_DText( dial_bot, btn_md, 'M O D I F Y', System_Font, TE_Center);
    Center_Dialog( dial_bot );
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_bot, 0 );
    Set_Mouse( M_Bee );
    End_Dialog( dial_bot );
    Delete_Dialog( dial_bot );
    clrscr;
    if btn=btn_st then      { Bootsektor, FAT und Directory initialisieren }
    begin
      if act_tr>42 then act_md:=248 else act_md:=252;
      if act_sd=2 then act_md:=act_md+1;
      for i:=0 to 511 do buffer[i]:=0;
      for i:=1 to mxs do
      begin
        adr_sc( i, sd2, tr2, sc2 );
        errnr:=wr_sec( buffer, 01, dev, sc2, tr2, sd2, 1);
        end;
      buffer[8]:=$20;
      buffer[9]:=$02;   { Serien Nummer }
      buffer[10]:=$59;  { Geburtstag meiner Frau : 20. Februar 1959 }
      buffer[12]:=$02; buffer[13]:=act_cl; buffer[14]:=$01;
      buffer[16]:=act_fc; buffer[17]:=act_de;
      buffer[19]:=(act_to mod 256); buffer[20]:=(act_to div 256);
      buffer[21]:=act_md; buffer[22]:=act_fs; buffer[24]:=act_sc;
      buffer[26]:=act_sd;
      errnr:=wr_sec( buffer, 01, dev, 1, 0, 0, 1);
      for i:=0 to 511 do buffer[i]:=0;
      buffer[0]:=act_sd+$FB;
      if act_md<250 then buffer[0]:=$F7;
      buffer[1]:=$FF;
      buffer[2]:=$FF;
      errnr:=wr_sec( buffer, 01, dev, 2, 0, 0, 1);
      i:=act_fs+1;
      adr_sc( i, sd2, tr2, sc2 );
      errnr:=wr_sec( buffer, 01, dev, sc2, tr2, sd2, 1);
      end;
    if btn=btn_md then      { vorhandenen Bootsektor modifizieren }
    begin
      if act_tr>42 then act_md:=248 else act_md:=252;
      if act_sd=2 then act_md:=act_md+1;
      errnr:=rd_bot( buffer, 01, dev, 1, 0, 0, 1);
      buffer[8]:=$20; buffer[9]:=$02; buffer[10]:=$59;
      buffer[12]:=$02; buffer[13]:=act_cl; buffer[14]:=$01;
      buffer[16]:=$02; buffer[17]:=act_de;
      buffer[19]:=act_to & $FF; buffer[20]:=shr(act_to,8) & $FF;
      buffer[21]:=act_md; buffer[22]:=act_fs; buffer[24]:=act_sc;
      buffer[26]:=act_sd;
      if buffer[2]=$4C then errnr:=cr_bot( buffer, -1, -1, 1); { executable   }
      errnr:=Do_Alert('[1][WRITE NEW BOOTSECTOR][ OK ]',1);    { Disk change  }
      errnr:=wr_sec( buffer, 01, dev, 1, 0, 0, 1);             { write new sc }
      end;
    menu:=0;
    if btn=headl then menu:=9;                                 { BREAK ? }
    end;  { of create boot sector and volume information }


PROCEDURE start_dev ( VAR device:integer ) ;
VAR dial_anf  : Dialog_Ptr ;
    ct        : long_integer;
    anfz      : string[70];
    dvn       : string[1];
    devbtn    : array [1..10] of integer;
    dev_btn, i, cu,
    anfti_item, anfz1_item, anfz2_item, anfz3_item,
    anfz4_item, anfz5_item, anfz6_item, anfz7_item   : integer ;

BEGIN
  ct:=drvmap;
  dial_anf   := New_Dialog( 20, 0, 0, 60, 16 ) ;
  anfti_item:=Add_DItem(dial_anf,G_BoxText,Selectable|Exit_Btn,
                        6, 1, 48, 3, 2, $11A1 );
  Set_DText(dial_anf, anfti_item,'DISK ENGINEER 3.01', System_Font, TE_Center);
  Obj_SetState( dial_anf, anfti_item, Shadowed, False );
  anfz1_item := Add_DItem( dial_anf, G_Text, None, 5, 5, 55, 1, 0, $1180 );
  anfz:='copyright 1986 by A.Ph.Vollmer      not for resale or commercial use';
  Set_DText( dial_anf, anfz1_item, anfz , Small_Font, TE_Left ) ;
  anfz2_item := Add_DItem( dial_anf, G_Text, None, 5, 6, 55, 1, 0, $1180 );
  anfz:='Alle Rechte vorbehalten - all rights reserved - Tous droits reserves';
  Set_DText( dial_anf, anfz2_item, anfz , Small_Font, TE_Left ) ;
  anfz3_item := Add_DItem( dial_anf, G_Text, None, 5, 7, 55, 1, 0, $1180 );
  anfz:='ST Pascal plus        No printer required        Atari ST Monochrome';
  Set_DText( dial_anf, anfz3_item, anfz , Small_Font, TE_Left ) ;
  anfz4_item := Add_DItem( dial_anf, G_Text, None, 5, 9, 55, 1, 0, $1180 );
  anfz:='Deutsches Software Produkt   Internationale Version   Stand 02/09/86';
  Set_DText( dial_anf, anfz4_item, anfz , Small_Font, TE_Left ) ;
  anfz5_item := Add_DItem( dial_anf, G_Text, None, 5, 10, 55, 1, 0, $1180 );
  anfz:='Copy allowed - Shareware Payments through POSTGIRO Karlsruhe/Germany';
  Set_DText( dial_anf, anfz5_item, anfz , Small_Font, TE_Left ) ;
  anfz6_item := Add_DItem( dial_anf, G_Text, None, 5, 11, 55, 1, 0, $1180 );
  anfz:='               DM10/$5 for private user   BLZ 66010075 No.206025-758';
  Set_DText( dial_anf, anfz6_item, anfz , Small_Font, TE_Left ) ;
  anfz7_item := Add_DItem( dial_anf, G_Text, None, 6, 12, 15, 1, 0, $1180 );
  Set_DText( dial_anf, anfz7_item, 'Default Drive :', System_Font, TE_Left ) ;
  cu:=0;
  for i:=1 to 10 do
    begin
      dvn:=chr(64+i);
      devbtn[i]:= Add_DItem( dial_anf, G_Button, Selectable|Exit_Btn|Radio_Btn,
                             1+i*5, 14, 4, 1, 2, $1180 );
      Set_DText( dial_anf, devbtn[i], dvn, System_Font, TE_Center );
      cu:=cu*2; if cu=0 then cu:=1;
      if ct<>ct|cu then Obj_SetState( dial_anf, devbtn[i], Disabled, False );
      end;
  Center_Dialog( dial_anf );
  Set_Mouse( M_Point_Hand );
  dev_btn:=Do_Dialog( dial_anf, 0 );
  Set_Mouse( M_Bee );
  for i:=1 to 10 do
    if dev_btn=devbtn[i] then device:=i-1;
  if dev_btn=anfti_item then device:=99;
  End_Dialog( dial_anf );
  Delete_Dialog( dial_anf );
  clrscr;
  menu:=0;
  if device=99 then menu:=9;
END;                                 { Drive Auswahl und Copyright }



PROCEDURE anal_disk( devno : integer );  { Disk-Parameter ohne BPB ermitteln }

  VAR  ppmt  : sc_point;
       wahl  : integer;

  BEGIN
    new(ppmt);
    with ppmt^ do                        { geht auch so ber Zeiger in RECORD }
    begin
      REPEAT
        errnr:=rd_sec(ppmt,01,devno,1,0,0,1);     { 1. phys+log Sektor }
        if errnr=0 then
        begin
          act_sr:=parameter[8]+(parameter[9]+parameter[10]*256)*256; { serial }
          act_bs:=parameter[11]+parameter[12]*256;    { Bytes / Sektor }
          act_cl:=parameter[13];                      { Sektor / Cluster }
          act_rs:=parameter[14]+parameter[15]*256;    { reservierte Sektoren }
          act_fc:=parameter[16];                      { Anzahl FATs }
          act_de:=parameter[17]+parameter[18]*256;    { Eintr„ge in Directory }
          act_to:=parameter[19]+parameter[20]*256;    { Anzahl Sektoren/Disk }
          act_md:=parameter[21];                      { Disk Typ }
          act_fs:=parameter[22]+parameter[23]*256;    { Sektoren / FAT }
          act_sc:=parameter[24]+parameter[25]*256;    { Sektoren / Track }
          act_sd:=parameter[26]+parameter[27]*256;    { Seiten / Disk }
          act_hd:=parameter[28]+parameter[29]*256;    { Versteckte Sektoren }
          act_bf:=parameter[510]+parameter[511]*256;  { Bootflag }
          act_fl:=$E5E5;                              { Formatierungs-Blank }
          act_so:=act_rs+(act_fc*act_fs)+(act_de div 16);  { logischer Offset }
          if (act_de mod 16)>0 then act_so:=act_so+1;
          act_tr:=act_to div (act_sd*act_sc);         { Track / Seite }
          end
        else
        begin
          Error_Alert(errnr,wahl);                    { Laufwerk-Error }
          errnr:=wahl-1;
          end;
        until errnr=0;
      end;
    dispose(ppmt);
    END;


  PROCEDURE anal_fat( devno : integer );              { FAT einlesen }
  BEGIN
    begin
      if (act_fs < (act_sc-1))
        then
          errnr:=fatrd(fat,01,devno,2,0,0,act_fs)
        else                                       { nicht ber Trackgrenze }
          errnr:=fatrd(fat,01,devno,2,0,0,(act_sc-1));
      end;
    END;              { of anal_fat }


PROCEDURE show_anal( VAR cho_anal:integer );
  VAR dial_an : Dialog_Ptr ;
      btn,
      btn_a, btn_b, btn_c, btn_d, btn_e, btn_f,
      anti_item, anz1_item, anz2_item, anz3_item,
      anz4_item, anz5_item, anz6_item, anz7_item   : integer ;
      anz    : str255;
      wert   : intstr;

  BEGIN
    dial_an  := New_Dialog( 20, 0, 0, 40, 16 ) ;
    anz:=concat('PARAMETERS OF',did,chr(device+65));
    anti_item:= Add_DItem( dial_an, G_BoxText, None, 2, 1, 36, 2, 2, $11A1 );
    Set_DText(dial_an, anti_item, anz, System_Font, TE_Center);
    Obj_SetState( dial_an, anti_item, Shadowed, False );
    anz1_item := Add_DItem( dial_an, G_Text, None, 6, 4, 25, 1, 0, $1180 );
    str(act_sd,wert); anz:=concat('Sides/Disk        : ',wert);
    Set_DText( dial_an, anz1_item, anz , System_Font, TE_Left ) ;
    anz2_item := Add_DItem( dial_an, G_Text, None, 6, 5, 25, 1, 0, $1180 );
    str(act_tr,wert); anz:=concat('Tracks/Side       : ',wert);
    Set_DText( dial_an, anz2_item, anz , System_Font, TE_Left ) ;
    anz3_item := Add_DItem( dial_an, G_Text, None, 6, 6, 25, 1, 0, $1180 );
    str(act_sc,wert); anz:=concat('Sectors/Track     : ',wert);
    Set_DText( dial_an, anz3_item, anz , System_Font, TE_Left ) ;
    anz4_item := Add_DItem( dial_an, G_Text, None, 6, 7, 25, 1, 0, $1180 );
    str(act_bs,wert); anz:=concat('Bytes/Sector      : ',wert);
    Set_DText( dial_an, anz4_item, anz , System_Font, TE_Left ) ;
    anz5_item := Add_DItem( dial_an, G_Text, None, 6, 8, 25, 1, 0, $1180 );
    str(act_cl,wert); anz:=concat('Sector/Cluster    : ',wert);
    Set_DText( dial_an, anz5_item, anz , System_Font, TE_Left ) ;
    anz6_item := Add_DItem( dial_an, G_Text, None, 6, 9, 25, 1, 0, $1180 );
    str(act_de,wert); anz:=concat('Directory Entries : ',wert);
    Set_DText( dial_an, anz6_item, anz , System_Font, TE_Left ) ;
    anz7_item := Add_DItem( dial_an, G_Text, None, 6, 10, 25, 1, 0, $1180 );
    str((act_fs*act_fc),wert); anz:=concat('Sectors for FATs  : ',wert);
    Set_DText( dial_an, anz7_item, anz , System_Font, TE_Left ) ;
    btn_a:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn|Default,
                      3, 12, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_a, 'New Disk', System_Font, TE_Center );
    btn_b:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      15, 12, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_b, 'New Drive', System_Font, TE_Center );
    btn_c:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      27, 12, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_c, 'Format', System_Font, TE_Center );
    btn_d:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      3, 14, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_d, 'Directory', System_Font, TE_Center );
    btn_e:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      15, 14, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_e, 'CANCEL', System_Font, TE_Center );
    btn_f:= Add_DItem(dial_an, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      27, 14, 10, 1, 2, $1180 );
    Set_DText( dial_an, btn_f, 'QUIT', System_Font, TE_Center );
    Center_Dialog( dial_an );
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_an, 0 );
    Set_Mouse( M_Bee );
    if btn=btn_a then cho_anal:=0;
    if btn=btn_b then cho_anal:=1;
    if btn=btn_c then cho_anal:=2;
    if btn=btn_d then cho_anal:=3;
    if btn=btn_e then cho_anal:=0;
    if btn=btn_f then cho_anal:=9;           { Haupt-Menue }
    End_Dialog( dial_an );
    Delete_Dialog( dial_an );
    clrscr;
    END;


  PROCEDURE dir_dial( zlf : zeilenfeld; zlk : kzfeld; VAR tast : integer );
  VAR z_item                : kzfeld;
      dial_dir              : Dialog_Ptr;
      headl, i, btn, ct, fom,
      btn_a, btn_b, btn_c,
      btn_d, btn_e, btn_f   : integer;
      zeile                 : string;

  BEGIN
    Set_Mouse( M_Point_Hand );
    dial_dir  := New_Dialog( 30, 0, 0, 68, 23 );
    z_item[1] := Add_DItem( dial_dir, G_BoxText,
                            Selectable|Exit_Btn,  1, 1, 41, 1, 2, $1180);
    Set_DText(dial_dir, z_item[1], zlf[1], Small_Font, TE_Center);
    z_item[2] := Add_DItem( dial_dir, G_BoxText, None, 43, 1, 24, 1, 2, $1180);
    Set_DText(dial_dir, z_item[2], zlf[2], Small_Font, TE_Center);
    headl     := Add_DItem( dial_dir, G_Text, None, 2, 2, 65, 2, 0, $1180 );
    zeile:='FILNO FILENAME.EXT STATE  PROT SIDE TRACK SECTOR  TYPE    SIZE';
    Set_DText(dial_dir, headl, zeile, System_Font, TE_Left );
    for i:=3 to 18 do
    begin
      z_item[i]:= Add_DItem(dial_dir, G_Text, None, 2, i+1, 65, 1, 0, $1180 );
      Set_DText( dial_dir, z_item[i], zlf[i], System_Font, TE_Left );
      end;
    btn_a:= Add_DItem(dial_dir,G_Button,Selectable|Exit_Btn|Radio_Btn|Default,
                      2, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_a, 'Next Pg.', System_Font, TE_Center );
    btn_b:= Add_DItem(dial_dir, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      13, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_b, 'Prev Pg.', System_Font, TE_Center );
    btn_c:= Add_DItem(dial_dir, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      24, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_c, 'Modify', System_Font, TE_Center );
    btn_d:= Add_DItem(dial_dir, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      35, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_d, 'SUB-Dir', System_Font, TE_Center );
    btn_e:= Add_DItem(dial_dir, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      46, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_e, 'F A T', System_Font, TE_Center );
    btn_f:= Add_DItem(dial_dir, G_Button, Selectable|Exit_Btn|Radio_Btn,
                      57, 21, 9, 1, 2, $1180 );
    Set_DText( dial_dir, btn_f, 'CANCEL', System_Font, TE_Center );
    Center_Dialog( dial_dir );
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_dir, 0 );
    Set_Mouse( M_Bee );
    if btn=btn_d then
    begin
      for i:=2 to 18 do
      begin
        if zlk[i]=$10 then                 { Dateien ausw„hlbar setzen }
              begin
                Obj_SetFlags( dial_dir, z_item[i], Selectable|Exit_Btn)
                end
              else
              begin
                Obj_SetState( dial_dir, z_item[i], Disabled, True );
                Obj_SetFlags( dial_dir, z_item[i], None );
                end;
        end;
      Set_Mouse( M_Point_Hand );
      btn:=ReDo_Dialog( dial_dir, 0 );
      Set_Mouse( M_Bee );
      for i:=1 to 18 do
      begin
        if btn=z_item[i] then tast:=i+8;   { Ausgew„hlte Datei kodieren }
        end;
      end;
    if btn=btn_c then fom:=28;
    if btn=btn_e then fom:=48;
    if (btn=btn_c) or (btn=btn_e) then
    begin
      for i:=2 to 18 do
      begin
        ct:=zlk[i];
        Obj_SetFlags( dial_dir, z_item[i], Selectable|Exit_Btn);
        if ct=(ct|$10) then
              begin
                Obj_SetState( dial_dir, z_item[i], Disabled, True );
                Obj_SetFlags( dial_dir, z_item[i], None );
                end;
        if ct=(ct|$08) then
              begin
                Obj_SetState( dial_dir, z_item[i], Disabled, True );
                Obj_SetFlags( dial_dir, z_item[i], None );
                end;
        end;
      Set_Mouse( M_Point_Hand );
      btn:=ReDo_Dialog( dial_dir, 0 );
      Set_Mouse( M_Bee );
      for i:=1 to 18 do
      begin
        if btn=z_item[i] then tast:=i+fom;
        end;
      end;
    if btn=btn_a then tast:=2;
    if btn=btn_b then tast:=3;
    if btn=btn_f then tast:=8;
    if btn=z_item[1] then tast:=9;
    End_Dialog( dial_dir );
    Delete_Dialog( dial_dir );
    clrscr;
    END;

  PROCEDURE fat_file( fold : fdescript; VAR knopf : integer );
    VAR
      z_item              : kzfeld;
      dial_fat            : Dialog_Ptr;
      z_text              : zeilenfeld;
      headl, i, btn, ct,
      lc, zn, reorg,
      ic, wc, headp, clold,
      btn_a, btn_b, btn_c : integer;
      outname             : str255;
      zeile               : string;

    BEGIN
      ct:=ord(fold[27])+ord(fold[28])*256;
      knopf:=0;
      dial_fat:= New_Dialog( 20, 0, 0, 67, 22);
      zeile:= copy( fold, 1, 8);
      zeile:=concat(zeile,'.',fold[9],fold[10],fold[11]);
      zeile:=concat('File Allocation Table of ',zeile);
      headl:= Add_DItem( dial_fat, G_BoxText,
                         Selectable|Exit_Btn, 2, 1, 53, 2, 1, $11A1);
      Set_DText( dial_fat, headl, zeile, System_Font, TE_Center);
      btn_a:= Add_DItem( dial_fat, G_Button,
                         Selectable|Exit_Btn, 2, 20, 30, 1, 1, $1180 );
      Set_DText( dial_fat, btn_a, 'Back to directory', System_Font,TE_Center );
      btn_b:= Add_DItem( dial_fat, G_Button,
                         Selectable|Exit_Btn, 35, 20, 30, 1, 1, $1180 );
      Set_DText( dial_fat, btn_b, 'Cancel', System_Font, TE_Center );
      lc:=ct;
      zn:=1; reorg:=-1;
      for i:=1 to 16 do z_text[i]:=' ';
      while (lc<$FF0) and (zn<17) do
        begin
          str( lc, ens);
          z_text[zn]:=concat(z_text[zn],ens[3],ens[4],ens[5],' ');
          if length(z_text[zn])>64 then zn:=zn+1;
          ic:=trunc(lc*1.5);
          wc:=fat[ic] + fat[ic+1]*256;
          if odd(lc) then wc:=shr(wc,4);
          lc:= wc & $FFF;
          if clold<>(lc-1) then reorg:=reorg+1;
          clold:=lc;
          end;
      for i:=1 to 16 do
        begin
          z_item[i]:= Add_DItem( dial_fat, G_Text, None, 1, i+2, 66,1,0,$1180);
          Set_DText( dial_fat, z_item[i], z_text[i], System_Font, TE_Left );
          end;
      if reorg<1 then reorg:=1;
      reorg:=100 div reorg;
      if reorg>99 then zeile:='100%' else
        zeile:=concat(chr(reorg div 10 +48),chr(reorg mod 10 +48),' %');
      headp:= Add_DItem( dial_fat, G_BoxText, None, 57, 1, 8, 2, 1, $11A1);
      Set_DText( dial_fat, headp, zeile, System_Font, TE_Center);
      Center_Dialog( dial_fat );
      Set_Mouse( M_Point_Hand );
      btn:=Do_Dialog( dial_fat, 0);
      Set_Mouse( M_Bee );
      if btn=btn_a then knopf:=7;
      if btn=btn_b then knopf:=8;
      if btn=headl then knopf:=9;
      if knopf=9 then menu:=9;
      End_Dialog( dial_fat );
      Delete_Dialog( dial_fat );
      clrscr;
     END;


  PROCEDURE mod_dir( fold : fdescript; VAR fnew : fdescript; knopf : integer );
  VAR z_item              : kzfeld;
      dial_mod            : Dialog_Ptr;
      prot, hidd, syst, dele : boolean;
      headl, i, btn, ct,
      mfname,
      btn_na, btn_nb,
      btn_nc, btn_nd,
      btn_a, btn_b, btn_c,
      btn_d, btn_e, btn_f,
      btn_g               : integer;
      outname             : str255;
      zeile               : string;

  BEGIN
    ct:= ord( fold[12] );
    if ct=(ct|$01) then prot:=True else prot:=False;
    if ct=(ct|$02) then hidd:=True else hidd:=False;
    if ct=(ct|$04) then syst:=True else syst:=False;
    if ord(fold[1])=$E5 then dele:=True else dele:=False;
    fnew:= fold;
    knopf:=0;
    dial_mod  := New_Dialog( 18, 0, 0, 41, 12 );
    headl := Add_DItem( dial_mod, G_BoxText,
                        Selectable|Exit_Btn, 6, 1, 29, 2, 1, $11A1);
    Set_DText( dial_mod, headl, 'Modify File Attributes',
               System_Font, TE_Center);
    mfname:= Add_DItem( dial_mod, G_FBoxtext,
                           Editable, 3, 7, 23, 2, 2, $1180 );
    zeile:= copy( fold, 1, 11);
    Set_DEdit( dial_mod, mfname, 'Pathname ________.___',
               'FFFFFFFFFFF', zeile, System_Font, TE_Center);
    btn_a:= Add_DItem( dial_mod, G_BoxText,
                       Selectable|Exit_Btn, 3, 4, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_a, 'PROTECTED', Small_Font, TE_Center );
    btn_na:= Add_DItem( dial_mod, G_BoxText,
                        Selectable|Exit_Btn, 3, 5, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_na, 'UNPROTECTED', Small_Font, TE_Center );
    btn_b:= Add_DItem( dial_mod, G_BoxText,
                       Selectable|Exit_Btn, 15, 4, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_b, 'HIDDEN', Small_Font, TE_Center );
    btn_nb:= Add_DItem( dial_mod, G_BoxText,
                        Selectable|Exit_Btn, 15, 5, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_nb, 'SHOWN', Small_Font, TE_Center );
    btn_c:= Add_DItem( dial_mod, G_BoxText,
                       Selectable|Exit_Btn, 27, 4, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_c, 'SYSTEM-FILE', Small_Font, TE_Center );
    btn_nc:= Add_DItem( dial_mod, G_BoxText,
                        Selectable|Exit_Btn, 27, 5, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_nc, 'USER-FILE', Small_Font, TE_Center );
    btn_d:= Add_DItem( dial_mod, G_BoxText,
                       Selectable|Exit_Btn, 27, 7, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_d, 'DELETED', Small_Font, TE_Center );
    btn_nd:= Add_DItem( dial_mod, G_BoxText,
                        Selectable|Exit_Btn, 27, 8, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_nd, 'UNDELETED', Small_Font, TE_Center );
    btn_e:= Add_DItem( dial_mod, G_Button,
                           Selectable|Exit_Btn, 3, 10, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_e, 'OK', System_Font, TE_Center );
    btn_f:= Add_DItem( dial_mod, G_Button,
                           Selectable|Exit_Btn|Default, 15,10,11,1,1,$1180 );
    Set_DText( dial_mod, btn_f, 'CANCEL', System_Font, TE_Center );
    btn_g:= Add_DItem( dial_mod, G_Button,
                           Selectable|Exit_Btn, 27, 10, 11, 1, 1, $1180 );
    Set_DText( dial_mod, btn_g, 'QUIT', System_Font, TE_Center );
    if prot then Obj_SetState( dial_mod, btn_a, Selected, False)
            else Obj_SetState( dial_mod, btn_na, Selected, False);
    if hidd then Obj_SetState( dial_mod, btn_b, Selected, False)
            else Obj_SetState( dial_mod, btn_nb, Selected, False);
    if syst then Obj_SetState( dial_mod, btn_c, Selected, False)
            else Obj_SetState( dial_mod, btn_nc, Selected, False);
    if dele then Obj_SetState( dial_mod, btn_d, Selected, False)
            else Obj_SetState( dial_mod, btn_nd, Selected, False);
    Center_Dialog( dial_mod );
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_mod, mfname );
    Set_Mouse( M_Bee );
    Get_DEdit( dial_mod, mfname, outname );
    outname:=concat(outname,'          ');
    for i:=1 to 11 do
      fnew[i]:=outname[i];
    if btn=btn_a then prot:= True;
    if btn=btn_b then hidd:= True;
    if btn=btn_c then syst:= True;
    if btn=btn_d then dele:= True;
    if btn=btn_na then prot:= False;
    if btn=btn_nb then hidd:= False;
    if btn=btn_nc then syst:= False;
    if btn=btn_nd then dele:= False;
    if btn=headl then knopf:=9;
    if btn=btn_g then knopf:=9;
    if btn=btn_f then knopf:=8;
    if btn=btn_e then knopf:=7;
    if knopf<7 then
    repeat
          knopf:=0;
          if prot then Obj_SetState( dial_mod, btn_a, Selected, True)
                  else Obj_SetState( dial_mod, btn_a, Normal, True);
          if hidd then Obj_SetState( dial_mod, btn_b, Selected, True)
                  else Obj_SetState( dial_mod, btn_b, Normal, True);
          if syst then Obj_SetState( dial_mod, btn_c, Selected, True)
                  else Obj_SetState( dial_mod, btn_c, Normal, True);
          if dele then Obj_SetState( dial_mod, btn_d, Selected, True)
                  else Obj_SetState( dial_mod, btn_d, Normal, True);
          if NOT(prot) then Obj_SetState( dial_mod, btn_na, Selected, True)
                       else Obj_SetState( dial_mod, btn_na, Normal, True);
          if NOT(hidd) then Obj_SetState( dial_mod, btn_nb, Selected, True)
                       else Obj_SetState( dial_mod, btn_nb, Normal, True);
          if NOT(syst) then Obj_SetState( dial_mod, btn_nc, Selected, True)
                       else Obj_SetState( dial_mod, btn_nc, Normal, True);
          if NOT(dele) then Obj_SetState( dial_mod, btn_nd, Selected, True)
                       else Obj_SetState( dial_mod, btn_nd, Normal, True);
          Set_Mouse( M_Point_Hand );
          btn:=ReDo_Dialog( dial_mod, mfname );
          Set_Mouse( M_Bee );
          Get_DEdit( dial_mod, mfname, outname );
          outname:=concat(outname,'          ');
          for i:=1 to 11 do
            fnew[i]:=outname[i];
          if btn=btn_a then prot:= True;
          if btn=btn_b then hidd:= True;
          if btn=btn_c then syst:= True;
          if btn=btn_d then dele:= True;
          if btn=btn_na then prot:= False;
          if btn=btn_nb then hidd:= False;
          if btn=btn_nc then syst:= False;
          if btn=btn_nd then dele:= False;
          ct:=0;
          if prot then ct:=ct|$01;
          if hidd then ct:=ct|$02;
          if syst then ct:=ct|$04;
          fnew[12]:=chr(ct);
          if btn=headl then knopf:=9;
          if btn=btn_g then knopf:=9;
          if btn=btn_f then knopf:=8;
          if btn=btn_e then knopf:=7;
      until knopf>6;
    if ord(fnew[1])=$E5 then fnew[1]:='X';
    if dele=True then fnew[1]:=chr($E5);
    if knopf=8 then knopf:=0;
    if knopf=9 then menu:=9;
    if knopf=7 then menu:=7;
    End_Dialog( dial_mod );
    Delete_Dialog( dial_mod );
    clrscr;
    end;


  PROCEDURE fmt( d : integer );
  VAR  dial_fmt   : Dialog_Ptr;
       alstr      : string;
       btnp       : char;
       eingabe    : str255;
       sisd, dosd, bofl         : boolean;
       fz                       : array [1..40] of string[40];
       fx, fy, fl, fi, fs, fg   : int40;
       new_de, new_md, new_fs,
       new_sc, new_sd, new_bf, new_tr,
       new_cl,
       btn, mntr, mxtr, i,
       headl, btn_fmt, btn_bot, btn_can   : integer;

  BEGIN
    menu:=10;
    for i:=1 to 40 do fs[i]:=Normal;
    for i:=1 to 40 do fg[i]:=Normal;
    mntr:=0; mxtr:=(act_to div act_sc)-1;
    if (act_to mod act_sc)>0 then mxtr:=mxtr+1;
    new_de:=act_de; new_md:=act_md;
    new_fs:=act_fs; new_sc:=act_sc; new_sd:=act_sd;
    new_bf:=act_bf; new_tr:=act_tr; new_cl:=act_cl;
    sisd:=True;
    if act_sd=2 then dosd:=True else dosd:=False;
    if act_bf=$1234 then bofl:=True else bofl:=False;
    dial_fmt  := New_Dialog( 40, 0, 0, 58, 22);
    headl:= Add_DItem( dial_fmt, G_BoxText,
                        Selectable|Exit_Btn, 2, 1, 54, 2, 1, $11A1);
    alstr:= concat( 'Format disk inside drive ', chr(d+65));
    Set_DText( dial_fmt, headl, alstr, System_Font, TE_Center);
    Obj_SetState( dial_fmt, headl, Shadowed, False);
    for i:=1 to 23 do fs[i]:=Normal;
    fz[1]:= 'ATARI TOS';    fx[1]:=2;    fy[1]:=4;   fl[1]:=12;
    if mxtr=79 then fs[1]:=Selected;
    fz[2]:= 'MSDOS PCDOS';  fx[2]:=16;   fy[2]:=4;   fl[2]:=12;
    if mxtr=39 then fs[2]:=Selected;
    fz[3]:= 'SPECIAL';      fx[3]:=30;   fy[3]:=4;   fl[3]:=12;
    if (mxtr<>79) and (mxtr<>39) then fs[3]:=Selected;
    fz[4]:= '80 TRACKS';    fx[4]:= 2;   fy[4]:= 6;  fl[4]:=12;
    if mxtr=79 then fs[4]:=Selected;
    fz[5]:= '40 TRACKS';    fx[5]:= 16;  fy[5]:= 6;  fl[5]:=12;
    if mxtr=39 then fs[5]:=Selected;
    fz[6]:= '84 TRACKS';    fx[6]:= 30;  fy[6]:= 6;  fl[6]:=12;
    if mxtr=83 then fs[6]:=Selected;
    fz[7]:= 'PARTS';        fx[7]:= 44;  fy[7]:= 6;  fl[7]:=12;
    fz[8]:= 'SINGLE SIDED'; fx[8]:= 2;   fy[8]:= 10; fl[8]:=12;
    if sisd then fs[8]:=Selected;
    fz[9]:= 'DOUBLE SIDED'; fx[9]:= 16;  fy[9]:= 10; fl[9]:=12;
    if dosd then fs[9]:=Selected;
    fz[10]:='ONLY SIDE 0';  fx[10]:= 30; fy[10]:=10; fl[10]:=12;
    fz[11]:='ONLY SIDE 1';  fx[11]:= 44; fy[11]:=10; fl[11]:=12;
    fz[12]:='9';            fx[12]:= 2;  fy[12]:=12; fl[12]:=5;
    if new_sc=9 then fs[12]:=Selected;
    fz[13]:='10';           fx[13]:= 9; fy[13]:=12; fl[13]:=5;
    if new_sc=10 then fs[13]:=Selected;
    fz[14]:='01..12';       fx[14]:= 16; fy[14]:=12; fl[14]:=12;
    fz[15]:='2';            fx[15]:= 2;  fy[15]:=14; fl[15]:=5;
    if new_cl=2 then fs[15]:=Selected;
    fz[16]:='1';            fx[16]:= 9; fy[16]:=14; fl[16]:=5;
    if new_cl=1 then fs[16]:=Selected;
    fz[17]:='5';            fx[17]:= 2; fy[17]:=16; fl[17]:=5;
    if new_fs=5 then fs[17]:=Selected;
    fz[18]:='1';            fx[18]:= 9; fy[18]:=16; fl[18]:=5;
    if new_fs=1 then fs[18]:=Selected;
    fz[19]:='2';            fx[19]:=16; fy[19]:=16; fl[19]:=5;
    if new_fs=2 then fs[19]:=Selected;
    fz[20]:='7';            fx[20]:=23; fy[20]:=16; fl[20]:=5;
    if new_fs=7 then fs[20]:=Selected;
    fz[21]:='112';          fx[21]:=2;  fy[21]:=18; fl[21]:=5;
    if new_de=112 then fs[21]:=Selected;
    fz[22]:='64';           fx[22]:=9;  fy[22]:=18; fl[22]:=5;
    if new_de=64 then fs[22]:=Selected;
    fz[23]:='128';          fx[23]:=16; fy[23]:=18; fl[23]:=5;
    if new_de=128 then fs[23]:=Selected;
    fz[24]:= 'first track __'; fx[24]:= 16; fy[24]:= 8; fl[24]:=14;
    fz[25]:= 'last track __'; fx[25]:= 32; fy[25]:= 8; fl[25]:=13;
    fz[26]:='sector/track __'; fx[26]:= 30; fy[26]:=12; fl[26]:=16;
    fz[27]:='SECTOR/CLUSTER WITH 512 BYTE/SECTOR';
                                   fy[27]:=14; fl[27]:=35;
    fz[28]:='SECTOR/FAT';          fy[28]:=16; fl[28]:=10;
    fz[29]:='ENTRIES/DIRECTORY';   fy[29]:=18; fl[29]:=18;
    for i:=1 to 23 do
      begin
        fi[i]:= Add_DItem( dial_fmt, G_BoxText, Selectable|Exit_Btn,
                           fx[i], fy[i], fl[i], 1, 1, $1180);
        Set_DText( dial_fmt, fi[i], fz[i], Small_Font, TE_Center);
        if fs[i]=Selected then fg[i]:=Outlined;  fs[i]:=fs[i]|fg[i];
        end;
    for i:=24 to 26 do
      begin
        fi[i]:= Add_DItem( dial_fmt, G_FText, Editable,
                           fx[i], fy[i], fl[i], 1, 0, $1180);
        Set_DEdit( dial_fmt, fi[i], fz[i], '99', '00', System_Font, TE_Left);
        fs[i]:=Disabled; fg[i]:=Normal;
        end;
    for i:=27 to 29 do
      begin
        fi[i]:= Add_DItem( dial_fmt, G_Text, None,
                           30, fy[i], fl[i], 1, 0, $1180);
        Set_DText( dial_fmt, fi[i], fz[i], Small_Font, TE_Left);
        fs[i]:=Normal;
        end;
    btn_fmt:= Add_DItem( dial_fmt, G_Button, Selectable|Exit_Btn|Radio_Btn,
                         2, 20, 16, 1, 1, $1180);
    Set_DText( dial_fmt, btn_fmt, 'FORMAT', System_Font, TE_Center);
    btn_bot:= Add_DItem( dial_fmt, G_Button, Selectable|Exit_Btn|Radio_Btn,
                         21, 20, 16, 1, 1, $1180);
    Set_DText( dial_fmt, btn_bot, 'PMT-SECs', System_Font, TE_Center);
    btn_can:= Add_DItem( dial_fmt, G_Button, Selectable|Exit_Btn|Radio_Btn,
                         40, 20, 16, 1, 1, $1180);
    Set_DText( dial_fmt, btn_can, 'CANCEL', System_Font, TE_Center);
    Center_Dialog( dial_fmt );
    for i:=1 to 26 do Obj_SetState( dial_fmt, fi[i], fs[i], False);
    Set_Mouse( M_Point_Hand );
    btn:=Do_Dialog( dial_fmt, fi[24] );
    if btn=headl then menu:=9;
    if btn=btn_can then menu:=0;
    if btn=btn_bot then menu:=2;
    if btn=btn_fmt then menu:=3;
    if (btn=btn_fmt) and (fs[2]=Selected) then menu:=4;
    while menu>9 do
    begin
      btnp:='Z';
      for i:=1 to 23 do
        begin
          if btn=fi[i]
            then begin
                   btnp:=chr(i+64);
                   fs[i]:=Selected;
                   end;
          end;
      CASE btnp OF                       { ginge auch mit lauter if then }

        'A' : begin
                fs[2]:=Normal;
                fs[3]:=Normal;
                mxtr:=79;
                mntr:=0;
                new_md:=248;
                end;

        'B' : begin
                fs[1]:=Normal;
                fs[3]:=Normal;
                mxtr:=39;
                mntr:=0;
                new_md:=252;
                end;

        'C' : begin
                fs[1]:=Normal;
                fs[2]:=Normal;
                mxtr:=83;
                mntr:=0;
                new_md:=250;
               end;

        'D' : begin
                for i:=5 to 7 do fs[i]:=Normal;
                fs[24]:=Disabled;
                fs[25]:=Disabled;
                mxtr:=79;
                mntr:=0;
                end;

        'E' : begin
                fs[4]:=Normal;
                fs[6]:=Normal;
                fs[7]:=Normal;
                fs[24]:=Disabled;
                fs[25]:=Disabled;
                mxtr:=39;
                mntr:=0;
                end;

        'F' : begin
                fs[4]:=Normal;
                fs[5]:=Normal;
                fs[7]:=Normal;
                fs[24]:=Disabled;
                fs[25]:=Disabled;
                mxtr:=83;
                mntr:=0;
                end;

        'G' : begin
                for i:=4 to 6 do fs[i]:=Normal;
                fs[24]:=Normal;
                fs[25]:=Normal;
                mxtr:=0;
                mntr:=0;
                end;

        'H' : begin
                for i:=9 to 11 do fs[i]:=Normal;
                sisd:=True;
                dosd:=False;
                end;

        'I' : begin
                fs[8]:=Normal;
                fs[10]:=Normal;
                fs[11]:=Normal;
                sisd:=True;
                dosd:=True;
                end;

        'J' : begin
                fs[8]:=Normal;
                fs[9]:=Normal;
                fs[11]:=Normal;
                sisd:=True;
                dosd:=False;
                end;

        'K' : begin
                fs[8]:=Normal;
                fs[9]:=Normal;
                fs[10]:=Normal;
                sisd:=False;
                dosd:=True;
                end;

        'L' : begin
                fs[13]:=Normal;
                fs[14]:=Normal;
                fs[26]:=Disabled;
                new_sc:=9;
                end;

        'M' : begin
                fs[12]:=Normal;
                fs[14]:=Normal;
                fs[26]:=Disabled;
                new_sc:=10;
                end;

        'N' : begin
                fs[12]:=Normal;
                fs[13]:=Normal;
                fs[26]:=Normal;
                new_sc:=9;
                end;

        'O' : begin
                fs[16]:=Normal;
                new_cl:=2;
                end;

        'P' : begin
                fs[15]:=Normal;
                new_cl:=1;
                end;

        'Q' : begin
                fs[18]:=Normal;
                fs[19]:=Normal;
                fs[20]:=Normal;
                new_fs:=5;
                end;

        'R' : begin
                fs[17]:=Normal;
                fs[19]:=Normal;
                fs[20]:=Normal;
                new_fs:=1;
                end;

        'S' : begin
                fs[17]:=Normal;
                fs[18]:=Normal;
                fs[20]:=Normal;
                new_fs:=2;
                end;

        'T' : begin
                fs[18]:=Normal;
                fs[19]:=Normal;
                fs[17]:=Normal;
                new_fs:=7;
                end;

        'U' : begin
                fs[22]:=Normal;
                fs[23]:=Normal;
                new_de:=112;
                end;

        'V' : begin
                fs[21]:=Normal;
                fs[23]:=Normal;
                new_de:=64;
                end;

        'W' : begin
                fs[21]:=Normal;
                fs[22]:=Normal;
                new_de:=128;
                end;

        END;
      for i:=26 downto 1 do Obj_SetState(dial_fmt, fi[i], (fs[i]|fg[i]), True);
      btn:=ReDo_Dialog( dial_fmt, fi[24]);
      if fs[7]=Selected then
        begin
          Get_DEdit( dial_fmt, fi[24], eingabe);
          mntr:=(ord(eingabe[1])-48)*10+(ord(eingabe[2])-48);
          Get_DEdit( dial_fmt, fi[25], eingabe);
          mxtr:=(ord(eingabe[1])-48)*10+(ord(eingabe[2])-48);
          if mxtr>83 then mxtr:=83;
          if mntr>mxtr then mntr:=mxtr;
          end;
      if fs[14]=Selected then
        begin
          Get_DEdit( dial_fmt, fi[26], eingabe);
          new_sc:=(ord(eingabe[1])-48)*10+(ord(eingabe[2])-48);
          end;
      if btn=headl then menu:=9;
      if btn=btn_can then menu:=0;
      if btn=btn_bot then menu:=2;
      if btn=btn_fmt then menu:=3;
      if (btn=btn_fmt) and (fs[2]=Selected) then menu:=4;
      end;
    End_Dialog( dial_fmt );
    Delete_Dialog( dial_fmt );
    Set_Mouse( M_Bee );
    clrscr;
    if menu=4 then
      begin
        eingabe:='[2][ TOS patched for 6ms step rate |    and | drive init wi';
        eingabe:=concat(eingabe,'th 40 tracks][  YES  | NO ]');
        btn:=Do_Alert(eingabe,0);
        if btn=1 then menu:=3;
        if btn=2 then menu:=0;
        end;
    if menu=3 then
      begin
        if sisd then fmtdisk( d, mntr, mxtr, 0, $E5E5, new_sc);
        if dosd then fmtdisk( d, mntr, mxtr, 1, $E5E5, new_sc);
        menu:=2;
        end;
    if menu=2 then
      begin
        act_de:=new_de; act_md:=new_md;
        act_fs:=new_fs; act_sc:=new_sc; act_sd:=1;
        act_bf:=new_bf; act_cl:=new_cl;
        if dosd then act_sd:=2;
        act_hd:=0;  act_rs:=1;
        act_tr:=mxtr+1;
        act_to:=act_sd * act_tr * act_sc;
        act_so:=act_rs+(act_fc*act_fs)+(act_de div 16);
        if (act_de mod 16)>0 then act_so:=act_so+1;
        cr_boot_sc( d );
        end;
    if menu<9 then menu:=0;
    button:=menu;
    END;


  PROCEDURE dir( d : integer );
  VAR taste, i, ct,
      sd2, tr2, sc2,
      sd3, tr3, sc3,
      sdold, trold, scold,
      mxde, mnde, lgfil,
      st_fil, start_dir, page : integer;
      lg_fil                  : long_integer;
      alstr, titel            : string;
      wahl                    : char;
      zl                      : zeilenfeld;
      zk                      : kzfeld;
      fstate, fneu            : fdescript;

  BEGIN
    titel:='DIRECTORY OF';
    titel:=concat(titel,did,chr(65+d),'              PAGE ');
    zl[2]:='MAIN-DIRECTORY';
    mxde:=(act_de div 16)-1;
    mnde:=0;
    sdold:=0; trold:=0; scold:=0;
    start_dir:=act_rs+(act_fc*act_fs);
    page:=0;
    new(dirbuf);
    with dirbuf^ do
    begin
      repeat
        Set_Mouse( M_Bee );
        adr_sc( ( page+start_dir ), sd3, tr3, sc3 );
        if ((sdold=sd3) and (trold=tr3) and (scold=sc3))
          then
            errnr:=0
          else
            errnr:=rd_sec_c(dirbuf,01,d,sc3,tr3,sd3,1);
        sdold:=sd3; trold:=tr3; scold:=sc3;
        if errnr=0
        then
        begin
          str( (page+1), ens ); ens:=copy(ens,4,2);
          zl[1]:=concat(titel,ens);
          zk[1]:=0; zk[2]:=$10;
          for i:=1 to 16 do
          begin
            ct:=page*16+i;
            str( ct, ens );
            fstate:=parameter[i];
            zk[i+2]:=ord(fstate[12]);
            if fstate[1]='.'
              then
                begin
                  if fstate[2]='.'
                    then
                      alstr:='Folder/Root '
                    else
                      alstr:='Folder/Act. ';
                  zl[i+2]:=concat(ens,' ',alstr);
                  end
              else
                begin
                  alstr:=copy(fstate,1,8);
                  alstr:=concat(alstr,'.');
                  zl[i+2]:=concat(ens,' ',alstr);
                  alstr:=copy(fstate,9,3);
                  zl[i+2]:=concat(zl[i+2],alstr);
                  end;
            if ord(fstate[1])=$E5
              then
                alstr:=' deleted '
              else
                alstr:=' active  ';
            ct:=zk[i+2];
            if ct=(ct|$01)
              then
                alstr:=concat(alstr,'yes  ')
              else
                alstr:=concat(alstr,'no   ');
            if ct=(ct|$08) then alstr:=' Volumelabel  ';
            zl[i+2]:=concat(zl[i+2],alstr);
            st_fil:=ord(fstate[27])+ord(fstate[28])*256;
            st_fil:=act_so+act_cl*st_fil-(2*act_cl);
            adr_sc( st_fil, sd2, tr2, sc2 );
            zl[i+2]:=concat(zl[i+2],chr(48+sd2),'    ');
            str( tr2, ens ); ens:= copy( ens, 4, 2 );
            zl[i+2]:=concat(zl[i+2],ens,'    ');
            str( sc2, ens ); ens:= copy( ens, 4, 2 );
            zl[i+2]:=concat(zl[i+2],ens,'     ');
            alstr:='Normal';
            if ct=(ct|$02) then alstr:='Hidden';
            if ct=(ct|$04) then alstr:='System';
            if ct=(ct|$10) then alstr:='Subdir';
            zl[i+2]:=concat(zl[i+2],alstr);
            lg_fil:=ord(fstate[32]);
            lg_fil:=lg_fil*256+ord(fstate[31]);
            lg_fil:=lg_fil*256+ord(fstate[30]);
            lg_fil:=lg_fil*256+ord(fstate[29]);
            lgfil:=int(lg_fil div (act_cl*act_bs));
            if (lg_fil mod (act_cl*act_bs))>0 then lgfil:=lgfil+1;
            str( lgfil, ens ); zl[i+2]:=concat(zl[i+2],' ',ens);
            end;
          dir_dial( zl, zk, taste );
          if (taste>10) and (taste<27) then
            begin
              i:=taste-10;
              mxde:=1;
              titel:=copy(zl[i+2],7,12);
              titel:=concat('SUBDIR : ',titel);
              titel:=concat(titel,' ON DISK IN DRIVE ',chr(65+d),'   PAGE ');
              fstate:=parameter[i];
              taste:=0;
              start_dir:=ord(fstate[27])+ord(fstate[28])*256;
              if start_dir=0 then taste:=10;
              start_dir:=act_so+act_cl*start_dir-(2*act_cl);
              zl[2]:='BACK TO MAIN-DIRECTORY';
              page:=0;
              end;
          if (taste=10) or ((taste=30) or (taste=50)) then
            begin
              titel:='DIRECTORY OF';
              titel:=concat(titel,did,chr(65+d),'              PAGE ');
              mxde:=(act_de div 16)-1;
              mnde:=0;
              zl[2]:='MAIN-DIRECTORY';
              start_dir:=act_rs+(act_fc*act_fs);
              page:=0;
              taste:=0;
              end;
          if (taste>30) and (taste<47) then
            begin
              i:=taste-30; errnr:=0;
              taste:=0;
              fstate:= parameter[i];
              mod_dir( fstate, fneu, taste );
              parameter[i]:= fneu;
              if menu=7 then
                errnr:= wr_sec_c(dirbuf, 01, d, sc3, tr3, sd3, 1);
              if menu=7 then menu:=0;
              if errnr<>0 then
                begin
                  Error_Alert( errnr, taste);
                  if taste=1 then taste:=9;
                  if taste=2 then taste:=0;
                  end;
              if taste<9 then taste:=0;
              end;
          if (taste>50) and (taste<67) then
            begin
              i:=taste-50; errnr:=0;
              taste:=0;
              fstate:= parameter[i];
              fat_file( fstate, taste );
              if taste<9 then taste:=0;
              end;
          end
        else
          begin
            Error_Alert(errnr, i);
            if i=1 then taste:=9;
            if i=2 then taste:=0;
            end;
        if taste=2 then page:=page+1;
        if taste=3 then page:=page-1;
        if page<mnde then page:=mxde;
        if page>mxde then page:=mnde;
        if taste=4 then taste:=0;
        if taste=5 then taste:=0;
        if taste=6 then taste:=0;
        until taste>7;
      if taste=9 then button:=9;
      if taste=8 then menu:=0;
      end;
    dispose(dirbuf);
    END;


  BEGIN
    IF Init_Gem >= 0 THEN
      BEGIN
        button:=getRez;
        clrscr;
        Init_Mouse;
        menu:=1;
        if button<2 then menu:=9;
        repeat
          button:=menu;
          CASE button OF

            0  :  begin
                    anal_disk( device );
                    anal_fat( device );
                    show_anal( menu );
                    end;

            1  :  start_dev( device );

            2  :  fmt( device );

            3  :  dir( device );

            end;
          errnr:=mediach( device );
          if errnr=2 then
                     begin
                       anal_disk( device );
                       anal_fat( device );
                       end;
          until button=9;
        Set_Mouse( M_Arrow );
        Exit_Gem ;
      END ;
  END.


