home *** CD-ROM | disk | FTP | other *** search
/ Programmer 7500 / MAX_PROGRAMMERS.iso / PASCAL / MADTRB15.ZIP / DISKRE.PAS < prev    next >
Encoding:
Pascal/Delphi Source File  |  1985-08-02  |  21.1 KB  |  716 lines

  1. { This program demonstrates some additional functions which     }
  2. { should be considered if a requirement is for analysis of      }
  3. { diskette data on a direct basis. It includes work initially   }
  4. { done by Bela Lubkin of Borland and has been extended to allow }
  5. { direct access to diskette data at a Head, Track, and Sector   }
  6. { level of addressing. This is a requirement when working with  }
  7. { non-DOS, and DOS's with different logical configurations (i.e.}
  8. { DOS 1.1 doesn't know of sector 9, DOS 2.1 of sector 10).  What}
  9. { makes this possible is through direct diskette i/o using      }
  10. { interrupt 13h as referenced in the system bios section of the }
  11. { IBM Technical Reference Manual.               Al Edlund       }
  12.  
  13. PROGRAM DISKREAD;
  14. const      w1x1 = 1;
  15.            w1x2 = 64;
  16.            w1y1 = 1;
  17.            w1y2 = 25;
  18.            w2x1 = 65;
  19.            w2x2 = 80;
  20.            w2y1 = 5;
  21.            w2y2 = 20;
  22.  
  23. type   regpack      = record
  24.                        ax,bx,cx,dx,bp,di,si,ds,es,flags : integer;
  25.                       end;
  26.        Str          = String[4];
  27.  
  28.  
  29. var    recpack                    : regpack;
  30.        ah,al,ch,cl,dh,dl          : byte;
  31.        DiskStatus                 : integer;
  32.        drivenumber                : integer;
  33.        headnumber                 : integer;
  34.        tracknumber                : integer;
  35.        sectornumber               : integer;
  36.        DR,LS,Result,C             : integer;
  37.        k,x,y                      : integer;
  38.        max_sector_count,mode      : integer;
  39.        max_count,moden            : integer;
  40.        W,selch                    : Char;
  41.        V                          : Str;
  42.        Changed                    : Boolean;
  43.        t248,t249,t252             : boolean;
  44.        t253,t254,t255             : boolean;
  45.        errmsg                     : string[14];
  46.        disktype                   : string[14];
  47.        DiskRecord                 : array[0..511] of byte;
  48.        altered_byte               : array[0..511] of boolean;
  49.  
  50.  
  51. Procedure Analyze_Status(errcode : integer);
  52. begin
  53.  case errcode of
  54.   0   : errmsg := 'Clean Complete';
  55.   1   : errmsg := 'Bad Command   ';
  56.   2   : errmsg := 'No Addr Mark  ';
  57.   3   : errmsg := 'Write Protect ';
  58.   4   : errmsg := 'No Sector     ';
  59.   8   : errmsg := 'DMA Overrun   ';
  60.   9   : errmsg := 'DMA 64K Error ';
  61.   16  : errmsg := 'Data CRC Error';
  62.   32  : errmsg := 'Disk Ctrlr Err';
  63.   64  : errmsg := 'Seek Failure  ';
  64.   128 : errmsg := 'Disk Time Out ';
  65.  end;
  66. end;
  67.  
  68. Function __ReadWriteSectors(Var Buffer;
  69.                             Drive, NumberSectors, LogicalSector: Integer;
  70.                             WriteFlag: Byte): Integer;
  71.   Var Result: Integer;
  72.   Begin
  73.     Result := 0;
  74.     Inline($8A/$86/ Drive /           {       MOV  AL,[BP+Drive]             }
  75.            $8B/$8E/ NumberSectors /   {       MOV  CX,[BP+NumberSectors]     }
  76.            $8B/$96/ LogicalSector /   {       MOV  DX,[BP+LogicalSector]     }
  77.            $55/                       {       PUSH BP                        }
  78.            $1E/                       {       PUSH DS                        }
  79.            $C5/$9E/ Buffer /          {       LDS  BX,[BP+Buffer]            }
  80.            $80/$BE/ WriteFlag /$01/   {       CMP  BYTE PTR [BP+WriteFlag],1 }
  81.            $74/$04/                   {       JE   Write                     }
  82.            $CD/$25/                   {       INT  25H                       }
  83.            $EB/$02/                   {       JMP  WrapUp                    }
  84.            $CD/$26/                   {Write: INT 26H                        }
  85.            $5B/                       {WrapUp:POP  BX     ;Dispose of flags  }
  86.            $1F/                       {       POP  DS                        }
  87.            $5D/                       {       POP  BP                        }
  88.            $73/$04/                   {       JNB  Ok                        }
  89.            $89/$86/ Result            {       MOV  [BP+Result],AX            }
  90.            );                         {Ok:                                   }
  91.     __ReadWriteSectors := Result;
  92.   End;
  93.  
  94. Function ReadSectors(Var Buffer;
  95.                      Drive, NumberSectors, LogicalSector: Integer): Integer;
  96.   Begin
  97.     ReadSectors:=
  98.       __ReadWriteSectors(Buffer,Drive,NumberSectors,LogicalSector,0);
  99.   End;
  100.  
  101. Function WriteSectors(Var Buffer;
  102.                       Drive, NumberSectors, LogicalSector: Integer): Integer;
  103.   Begin
  104.     WriteSectors:=
  105.       __ReadWriteSectors(Buffer,Drive,NumberSectors,LogicalSector,1);
  106.   End;
  107.  
  108.  
  109. Procedure Read_Disk_Data(drivenumber,headnumber,tracknumber,sectornumber:integer);
  110. var sectorcount : integer;
  111.  
  112. begin
  113.  SectorCount := 1;
  114.  ah := 2;            {read command}
  115.  al := SectorCount;
  116.  ch := TrackNumber;
  117.  cl := SectorNumber;
  118.  dh := HeadNumber;
  119.  dl := DriveNumber;
  120.   with recpack do begin
  121.    ax := ah shl 8 + al;
  122.    cx := ch shl 8 + cl;
  123.    dx := dh shl 8 + dl;
  124.    es := seg(DiskRecord);
  125.    bx := ofs(DiskRecord);
  126.   end;
  127.  intr($13,recpack);
  128. end;
  129.  
  130. Procedure Write_Disk_Data(drivenumber,headnumber,tracknumber,sectornumber:integer);
  131. var  changetrack : boolean;
  132.      sectorcount : integer;
  133.  
  134. begin
  135.  SectorCount := 1;
  136.  ah := 3;            {write command}
  137.  al := SectorCount;
  138.  ch := TrackNumber;
  139.  cl := SectorNumber;
  140.  dh := HeadNumber;
  141.  dl := DriveNumber;
  142.   with recpack do begin
  143.    ax := ah shl 8 + al;
  144.    cx := ch shl 8 + cl;
  145.    dx := dh shl 8 + dl;
  146.    es := seg(DiskRecord);
  147.    bx := ofs(DiskRecord);
  148.   end;
  149.  intr($13,recpack);
  150. end;
  151.  
  152.  
  153. Procedure Read_Disk_Status;
  154. begin
  155. diskstatus := 0;
  156.  ah := 1;                   {read status command}
  157.   with recpack do begin
  158.    ax := ah shl 8 + al;
  159.   end;
  160.  intr($13,recpack);
  161.   with recpack do begin
  162.    ah := ax shr 8;
  163.    DiskStatus := ah;
  164.   end;
  165.  Analyze_Status(diskstatus);
  166. end;
  167.  
  168. Procedure Disk_Reset;
  169. begin
  170.  ah := 0;                   {reset disk command}
  171.   with recpack do begin
  172.    ax := ah shl 8 + al;
  173.   end;
  174.  intr($13,recpack);
  175. end;
  176.  
  177. Function Int2Hex2(B: Byte): Str;
  178.   Const H: Array [0..15] Of Char='0123456789ABCDEF';
  179.   Begin
  180.     Int2Hex2:=H[B Shr 4]+H[B And 15];
  181.   End;
  182.  
  183. Function Int2Hex4(I: Integer): Str;
  184.   Const H: Array [0..15] Of Char='0123456789ABCDEF';
  185.   Begin
  186.     Int2Hex4:=H[I Shr 12]+H[(I Shr 8) And 15]+H[(I Shr 4) And 15]+H[I And 15];
  187.   End;
  188.  
  189. Function Hex2Int1(C: Char): Byte;
  190.   Begin
  191.     Case Upcase(C) Of
  192.       '0'..'9': Hex2Int1:=Ord(C) And 15;
  193.       'A'..'F': Hex2Int1:=Ord(C) And 15+9;
  194.       Else Hex2Int1:=0;
  195.      End;
  196.   End;
  197.  
  198. Function Hex2Int4(S: Str; Default: Integer): Integer;
  199.   Var I: Integer;
  200.   Begin
  201.     If S='' Then Hex2Int4:=Default
  202.     Else
  203.      Begin
  204.       I:=0;
  205.       While S<>'' Do
  206.        Begin
  207.         I:=I Shl 4 + Hex2Int1(S[1]);
  208.         Delete(S,1,1);
  209.        End;
  210.       Hex2Int4:=I;
  211.      End;
  212.   End;
  213.  
  214.  
  215.  
  216.  
  217. Procedure ShowSector(Var S);
  218.   Var Buffer : Array [0..31,0..15] Of Byte Absolute S;
  219.       colarr : Array [0..31,0..15] of boolean absolute altered_byte;
  220.       I,J    : Integer;
  221.       B      : Byte;
  222.  
  223.   Begin
  224.     window(w1x1,w1y1,w1x2,w1y2);
  225.     clrscr;
  226.     gotoxy(7,4);
  227.     write(' 0 1 2 3  4 5 6 7   8 9 A B  C D E F   0123456789ABCDEF');
  228.     gotoxy(1,5);
  229.     textcolor(white);
  230.     For I:=0 To 15 Do
  231.      Begin
  232.       Write(Int2Hex4(I Shl 4),'| ');
  233.       For J:=0 To 15 Do
  234.        Begin
  235.         if colarr[i,j] = true then textcolor(yellow)
  236.          else textcolor(white);
  237.         Write(Int2Hex2(Buffer[I,J]));
  238.         If J And 3 = 3 Then Write(' ');
  239.         if j and 15 = 7 then write(' ');
  240.        End;
  241.       Write('| ');
  242.       For J:=0 To 15 Do
  243.        Begin
  244.         B:=Buffer[I,J];
  245.         If B<127 Then textcolor(blue)
  246.         Else textcolor(cyan);
  247.         B:=B And $7F;
  248.         If B<32 Then B:=Ord('.');
  249.         Write(Chr(B));
  250.        End;
  251.       textcolor(white);
  252.       WriteLn;
  253.      End;
  254.      gotoxy(1,23); clreol;
  255.      writeln('(CR) to continue');
  256.      read(selch);
  257.      gotoxy(1,5);
  258.     For I:=16 To 31 Do
  259.      Begin
  260.       Write(Int2Hex4(I Shl 4),'| ');
  261.       For J:=0 To 15 Do
  262.        Begin
  263.         if colarr[i,j] = true then textcolor(yellow)
  264.          else textcolor(white);
  265.         Write(Int2Hex2(Buffer[I,J]));
  266.         If J And 3 = 3 Then Write(' ');
  267.         if j and 15 = 7 then write(' ');
  268.        End;
  269.       Write('| ');
  270.       For J:=0 To 15 Do
  271.        Begin
  272.         B:=Buffer[I,J];
  273.         If B<127 Then textcolor(blue)
  274.         Else textcolor(cyan);
  275.         B:=B And $7F;
  276.         If B<32 Then B:=Ord('.');
  277.         Write(Chr(B));
  278.        End;
  279.       textcolor(white);
  280.       WriteLn;
  281.      End;
  282.     gotoxy(1,23); clreol;
  283.     window(w2x1 + 1, w2y1 + 1, w2x2 - 1, w2y2 - 1);
  284.     writeln;
  285.    End;
  286.  
  287. Procedure Real_Read;
  288.  
  289. begin
  290.  clrscr;
  291.  disk_reset;
  292.  read_disk_status;    {to clear the adapter}
  293.  gotoxy(1,1);
  294.  Writeln(' Real Mode');
  295.  writeln;
  296.  writeln(' DR HD TR SC');
  297.  writeln(' ', drivenumber:2, ' ', headnumber:2, ' ',tracknumber:2, ' ',sectornumber:2);
  298.  writeln;
  299.  write(' Drive #  = '); readln(drivenumber);
  300.  write(' Head #   = '); readln(headnumber);
  301.  write(' Track #  = '); readln(tracknumber);
  302.  write(' Sector # = '); readln(sectornumber);
  303.  read_disk_data(drivenumber,0,0,2);
  304.  read_disk_status;
  305.  case diskrecord[0] of
  306.   255 : disktype := 'DBLSIDED--8SEC';
  307.   254 : disktype := 'SNGSIDED--8SEC';
  308.   253 : disktype := 'DBLSIDED--9SEC';
  309.   252 : disktype := 'SNGSIDED--9SEC';
  310.   249 : disktype := 'DBLSIDED-15SEC';
  311.   248 : disktype := 'HARD DISK     ';
  312.  end;
  313.  read_disk_data(drivenumber,headnumber,tracknumber,sectornumber);
  314.  read_disk_status;
  315.  if diskstatus = 0 then begin
  316.   for k := 0 to 511 do begin
  317.    altered_byte[k] := false;
  318.   end;
  319.   textcolor(green);
  320.   gotoxy(1,w2y2 - w2y1 - 2);
  321.   write(errmsg);
  322.   textcolor(white);
  323.   gotoxy(1,11);
  324.   writeln(' Disktype =');
  325.   write(disktype);
  326.   showsector(diskrecord);
  327.   clrscr;
  328.   gotoxy(1,1);
  329.   writeln(' Do you wish');
  330.   write(' to alter this');
  331.   writeln(' record (Y/N)');
  332.   read(selch);
  333.    If Upcase(selch)='Y' then begin
  334.     repeat
  335.      clrscr;
  336.      gotoxy(1,1);
  337.      Writeln(' Enter the ');
  338.      writeln(' positon of');
  339.      writeln(' the byte to');
  340.      writeln(' change.    ');
  341.      write('( 0-1FF, CR to end): ');
  342.      ReadLn(V);
  343.      C:=Hex2Int4(V,-1);
  344.       If (C >= 0) And (C < 511) Then begin
  345.        clrscr;
  346.        gotoxy(1,1);
  347.        Writeln(' Enter new');
  348.        writeln(' value [',Int2Hex2(diskrecord[C]),']: ');
  349.        ReadLn(V);
  350.         If Length(V) > 1 Then
  351.          If V[1] In ['''','"'] Then diskrecord[C] := Ord(V[2])
  352.           Else diskrecord[C] := Hex2Int4(V,diskrecord[C])
  353.            Else diskrecord[C] := Hex2Int4(V,diskrecord[C]);
  354.             Changed := True;
  355.              if changed = true then altered_byte[c] := true;
  356.           End
  357.          Else C := -1;
  358.     Until C = -1;
  359.     showsector(diskrecord);
  360.     If Changed then begin
  361.      gotoxy(1,1); clrscr;
  362.      Write(' Write changes');
  363.      writeln(' back to real');
  364.      writeln(' sector # ');
  365.      writeln(' DR HD TR SC');
  366.      writeln(' ', drivenumber:2, ' ', headnumber:2, ' ',tracknumber:2, ' ',sectornumber:2);
  367.      writeln(' (Y/N)? ');
  368.      Read(W);
  369.       If Upcase(W)='Y' then begin
  370.        Write_disk_data(drivenumber,headnumber,tracknumber,sectornumber);
  371.        read_disk_status;
  372.         if diskstatus = 0 then textcolor(green)
  373.          else textcolor(20);
  374.        gotoxy(1,w2y2 - w2y1 - 2);
  375.        writeln(errmsg);
  376.        textcolor(white);
  377.       End;    {end write back}
  378.      end;     {end test for changed}
  379.    end;       {end change record (y/n)}
  380.  end;        { good complete from read}
  381.  if diskstatus <> 0 then begin
  382.   window(w1x1,w1y1,w1x2,w1y2);
  383.   clrscr;
  384.   window(w2x1 + 1, w2y1 + 1, w2x2 - 1, w2y2 - 1);
  385.   clrscr;
  386.   textcolor(20);
  387.   gotoxy(1,w2y2 - w2y1 - 2);
  388.   write(errmsg);
  389.   gotoxy(1,1);
  390.   textcolor(white);
  391.   writeln(' Disk Error ');
  392.   writeln;
  393.   writeln(' DR HD TR SC');
  394.   writeln(' ', drivenumber:2, ' ', headnumber:2, ' ',tracknumber:2, ' ',sectornumber:2);
  395.   writeln;
  396.   writeln;
  397.   writeln(' Any key to ');
  398.   writeln(' continue   '); read(kbd,selch);
  399.  end;
  400. end;         {end real record}
  401.  
  402. Procedure Simulate_Logical;
  403.  
  404. begin
  405.  clrscr;
  406.  gotoxy(1,1);
  407.  Writeln(' Simulate');
  408.  writeln(' Logical');
  409.  writeln;
  410.  writeln(' Which DOS ');
  411.  writeln(' would you ');
  412.  writeln(' like to ');
  413.  writeln(' simulate ');
  414.  write(' 1 or 2 ?? ');
  415.  read(moden);
  416.   if moden in [1..2] then mode := moden;
  417.  clrscr;
  418.  writeln(' Enter the ');
  419.  writeln(' drive # to');
  420.  writeln(' read.');
  421.  write(' (CR to end): ');
  422.  read(dr);
  423.  if dr in [0..1] then drivenumber := dr;
  424.  disk_reset;
  425.  read_disk_status;    {to clear the adapter}
  426.  read_disk_data(drivenumber,0,0,2);
  427.  read_disk_status;
  428.  case diskrecord[0] of
  429.   255 : t255 := true;
  430.   254 : t254 := true;
  431.   253 : t253 := true;
  432.   252 : t252 := true;
  433.  end;
  434.  clrscr;
  435.  writeln(' Enter the');
  436.  write('logical sector');
  437.  writeln(' # to read: ');
  438.  write(' '); readln(ls);
  439. {******************************************************************}
  440.   if mode = 1 then begin
  441.    max_sector_count := 8;
  442.     if t255 = true then begin
  443.      tracknumber := trunc(ls / (max_sector_count * 2));
  444.      if odd(trunc(ls / max_sector_count)) then headnumber := 1
  445.       else headnumber := 0;
  446.     end;
  447.     if t254 = true then begin
  448.      tracknumber := trunc(ls / max_sector_count);
  449.      headnumber := 0;
  450.     end;
  451.    sectornumber := (ls mod max_sector_count) + 1;
  452.   end;
  453. {********************************************************************}
  454.   if mode = 2 then begin
  455.    max_sector_count := 9;
  456.    if ls <= (max_sector_count * 40) - 1 then begin
  457.     tracknumber := trunc(ls / max_sector_count);
  458.     headnumber := 0;
  459.    end;
  460.    if t253 = true then begin
  461.     if ls > (max_sector_count * 40) - 1 then begin
  462.      tracknumber := trunc((ls - ((max_sector_count * 40) - 1)) / max_sector_count);
  463.      headnumber := 1;
  464.     end;
  465.    end;
  466.    sectornumber := (ls mod max_sector_count) + 1;
  467.   end;
  468.  read_disk_data(drivenumber,headnumber,tracknumber,sectornumber);
  469.  read_disk_status;
  470.  if diskstatus = 0 then begin
  471.   for k := 0 to 511 do begin
  472.    altered_byte[k] := false;
  473.   end;
  474.   textcolor(green);
  475.   gotoxy(1,w2y2 - w2y1 - 2);
  476.   write(errmsg);
  477.   textcolor(white);
  478.   showsector(diskrecord);
  479.   clrscr;
  480.   gotoxy(1,1);
  481.   writeln(' Do you wish');
  482.   write(' to alter this');
  483.   writeln(' record (Y/N)');
  484.   read(selch);
  485.    If Upcase(selch)='Y' then begin
  486.     repeat
  487.      clrscr;
  488.      gotoxy(1,1);
  489.      Writeln(' Enter the ');
  490.      writeln(' positon of');
  491.      writeln(' the byte to');
  492.      writeln(' change.    ');
  493.      write('( 0-1FF, CR to end): ');
  494.      ReadLn(V);
  495.      C:=Hex2Int4(V,-1);
  496.       If (C >= 0) And (C < 511) Then begin
  497.        clrscr;
  498.        gotoxy(1,1);
  499.        Writeln(' Enter new');
  500.        writeln(' value [',Int2Hex2(diskrecord[C]),']: ');
  501.        ReadLn(V);
  502.         If Length(V) > 1 Then
  503.          If V[1] In ['''','"'] Then diskrecord[C] := Ord(V[2])
  504.           Else diskrecord[C] := Hex2Int4(V,diskrecord[C])
  505.            Else diskrecord[C] := Hex2Int4(V,diskrecord[C]);
  506.             Changed := True;
  507.              if changed = true then altered_byte[c] := true;
  508.           End
  509.          Else C := -1;
  510.     Until C = -1;
  511.     showsector(diskrecord);
  512.     If Changed then begin
  513.      gotoxy(1,1); clrscr;
  514.      Write(' Write changes');
  515.      writeln(' back to real');
  516.      writeln(' sector # ');
  517.      writeln(' DR HD TR SC');
  518.      writeln(' ', drivenumber:2, ' ', headnumber:2, ' ',tracknumber:2, ' ',sectornumber:2);
  519.      writeln;
  520.      write('DR LS# MCT MDE');
  521.      writeln(dr:2, ' ', ls:3, ' ', max_sector_count:2, '   ', mode:1);
  522.      writeln(' (Y/N)? ');
  523.      Read(W);
  524.       If Upcase(W)='Y' then begin
  525.        Write_disk_data(drivenumber,headnumber,tracknumber,sectornumber);
  526.        read_disk_status;
  527.         if diskstatus = 0 then textcolor(green)
  528.          else textcolor(20);
  529.        gotoxy(1,w2y2 - w2y1 - 2);
  530.        writeln(errmsg);
  531.        textcolor(white);
  532.       End;    {end write back}
  533.      end;     {end test for changed}
  534.    end;       {end change record (y/n)}
  535.  end;        { good complete from read}
  536.  if diskstatus <> 0 then begin
  537.   window(w1x1,w1y1,w1x2,w1y2);
  538.   clrscr;
  539.   window(w2x1 + 1, w2y1 + 1, w2x2 - 1, w2y2 - 1);
  540.   clrscr;
  541.   textcolor(20);
  542.   gotoxy(1,w2y2 - w2y1 - 2);
  543.   write(errmsg);
  544.   gotoxy(1,1);
  545.   textcolor(white);
  546.   writeln(' Disk Error ');
  547.   writeln;
  548.   writeln(' DR HD TR SC');
  549.   writeln(' ', drivenumber:2, ' ', headnumber:2, ' ',tracknumber:2, ' ',sectornumber:2);
  550.   writeln;
  551.   write('DR LS# MCT MDE');
  552.   writeln(dr:2, ' ', ls:3, ' ', max_sector_count:2, '   ', mode:1);
  553.   writeln;
  554.   writeln(' Any key to ');
  555.   writeln(' continue   '); read(kbd,selch);
  556.  end;
  557. end;         {end sim.log record}
  558.  
  559.  
  560. Procedure Logical_Read;
  561. begin
  562.     clrscr;
  563.     writeln(' Logical Read');
  564.     writeln;
  565.     writeln(' Drive Sector');
  566.     writeln('  ', dr:2, '   ', ls:4);
  567.     writeln;
  568.     writeln(' Enter the ');
  569.     writeln(' drive # to');
  570.     writeln(' read.');
  571.     writeln(' (CR to end): ');
  572.     readln(DR);
  573.     If DR In [0..25] then begin
  574.       clrscr;
  575.       writeln(' Enter the');
  576.       write('logical sector');
  577.       writeln(' # to read: ');
  578.       readln(ls);
  579.       Result:=ReadSectors(diskrecord,DR,1,LS);
  580.        if result = 0 then begin
  581.         for k := 0 to 511 do begin
  582.          altered_byte[k] := false;
  583.         end;
  584.         textcolor(green);
  585.          gotoxy(1,w2y2 - w2y1 - 2);
  586.          WriteLn(' Result = ',Result);
  587.          Changed := False;
  588.          textcolor(white);
  589.          ShowSector(diskrecord);
  590.          clrscr;
  591.          gotoxy(1,1);
  592.          writeln(' Do you wish');
  593.          write(' to alter this');
  594.          writeln(' record (Y/N)');
  595.          read(selch);
  596.           If Upcase(selch) = 'Y' then begin
  597.            repeat
  598.             clrscr;
  599.             gotoxy(1,1);
  600.             Writeln(' Enter the ');
  601.             writeln(' positon of');
  602.             writeln(' the byte to');
  603.             writeln(' change.    ');
  604.             write('( 0-1FF, CR to end): ');
  605.             ReadLn(V);
  606.             C:=Hex2Int4(V,-1);
  607.              If (C >= 0) And (C < 511) then begin
  608.               clrscr;
  609.               gotoxy(1,1);
  610.               Writeln(' Enter new');
  611.               writeln(' value [',Int2Hex2(diskrecord[C]),']: ');
  612.               ReadLn(V);
  613.                If Length(V) > 1 Then
  614.                 If V[1] In ['''','"'] then diskrecord[C] := Ord(V[2])
  615.                  Else diskrecord[C] := Hex2Int4(V,diskrecord[C])
  616.                   Else diskrecord[C] := Hex2Int4(V,diskrecord[C]);
  617.                   Changed := True;
  618.                    if changed = true then altered_byte[c] := true;
  619.                End
  620.               Else C := -1;
  621.            Until C = -1;
  622.            showsector(diskrecord);
  623.            If Changed then begin
  624.             clrscr;
  625.             gotoxy(1,1);
  626.             Write(' Write changes');
  627.             writeln(' back to');
  628.             writeln(' drive', DR:2);
  629.             writeln(' sector ',LS:4);
  630.             writeln(' (Y/N)? ');
  631.             Read(W);
  632.              If Upcase(W) = 'Y' then begin
  633.               Result := WriteSectors(diskrecord,DR,1,LS);
  634.               gotoxy(1,w2y2 - w2y1 - 2);
  635.               WriteLn('Result = ',Result);
  636.              end; {end write of new data}
  637.            end;  {end sample for changed data}
  638.           end;   {test for really want to change}
  639.          end; { good read }
  640.          if result <> 0 then begin
  641.           window(w1x1,w1y1,w1x2,w1y2);
  642.           clrscr;
  643.           window(w2x1 + 1, w2y1 + 1, w2x2 - 1, w2y2 - 1);
  644.           clrscr;
  645.           textcolor(20);
  646.           gotoxy(1,w2y2 - w2y1 - 2);
  647.           writeLn('Result = ',Result);
  648.           gotoxy(1,1);
  649.           textcolor(white);
  650.           writeln(' Disk Error ');
  651.           writeln;
  652.           writeln(' drive', DR:2);
  653.           writeln(' sector ',LS:4);
  654.           writeln;
  655.           writeln;
  656.           writeln(' Any key to ');
  657.           writeln(' continue   '); read(kbd,selch);
  658.          end;
  659.         end;     {end dr valid}
  660. end; {logical read}
  661.  
  662.  
  663. begin
  664.  drivenumber := 0;
  665.  headnumber := 0;
  666.  tracknumber := 0;
  667.  sectornumber := 1;
  668.  dr := 0;
  669.  ls := 0;
  670.  mode := 2;
  671.  selch := ' ';
  672.  textcolor(white);
  673.  window(1,1,80,25);  {define the screen}
  674.  textcolor(yellow);
  675.  gotoxy(w2x1,w2y1); write(chr(201));
  676.  for x := w2x1 + 1 to w2x2 - 1 do write(chr(205));
  677.  write(chr(187));
  678.  for y := w2y1 + 1 to w2y2 - 1 do
  679.    begin
  680.      gotoxy(w2x1,y);
  681.      write(chr(186), ' ':w2x2 - w2x1 - 1, chr(186))
  682.    end;
  683.  gotoxy(w2x1,w2y2); write(chr(200));
  684.  for x := w2x1 + 1 to w2x2 - 1 do write(chr(205));
  685.  write(chr(188));
  686.  repeat
  687.   FillChar(diskrecord,SizeOf(diskrecord),'z');
  688.   for k := 0 to 511 do begin
  689.    altered_byte[k] := false;
  690.   end;
  691.   disktype := '              ';
  692.   t255 := false;
  693.   t254 := false;
  694.   t253 := false;
  695.   t252 := false;
  696.   window(w1x1,w1y1,w1x2,w1y2);
  697.   clrscr;
  698.   window(w2x1 + 1, w2y1 + 1, w2x2 - 1, w2y2 - 1);
  699.   clrscr;
  700.   gotoxy(1,1);
  701.   textcolor(white);
  702.   writeln(' DISK READ '); writeln;
  703.   writeln(' Enter Mode'); writeln;
  704.   writeln(' (r)eal');
  705.   writeln(' (l)ogical');
  706.   write(' (s)im.logical');
  707.   writeln(' e(x)it');
  708.   read(kbd,selch);
  709.    if upcase(selch) = 'R' then real_read;
  710.    if upcase(selch) = 'L' then logical_read;
  711.    if upcase(selch) = 'S' then simulate_logical;
  712.  until selch = 'x';
  713.  window(1,1,80,25);
  714.  clrscr;
  715. End.
  716.