unit Unit1; interface uses SysUtils, WinTypes, WinProcs, Messages, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls, Grids, Outline, DirOutln, FileCtrl, Buttons, Gauges, ExtCtrls, Spin, Mask; type TForm1 = class(TForm) DriveComboBox1: TDriveComboBox; FilterComboBox1: TFilterComboBox; FileListBox1: TFileListBox; DirectoryListBox1: TDirectoryListBox; SpeedButton1: TSpeedButton; SpeedButton2: TSpeedButton; Memo1: TMemo; Memo2: TMemo; Memo3: TMemo; SpeedButton3: TSpeedButton; SpeedButton4: TSpeedButton; Gauge1: TGauge; SpeedButton5: TSpeedButton; SpeedButton6: TSpeedButton; SpinButton1: TSpinButton; MaskEdit1: TMaskEdit; SpeedButton8: TSpeedButton; SpinButton2: TSpinButton; okm: TCheckBox; Label1: TLabel; procedure FormActivate(Sender: TObject); procedure SpinButton1DownClick(Sender: TObject); procedure SpinButton1UpClick(Sender: TObject); procedure showadress(Sender: TObject); procedure SpeedButton6Click(Sender: TObject); procedure SpeedButton8Click(Sender: TObject); procedure MaskEdit1Change(Sender: TObject); procedure SpinButton2DownClick(Sender: TObject); procedure SpinButton2UpClick(Sender: TObject); procedure SpeedButton3Click(Sender: TObject); procedure Memo2Click(Sender: TObject); private { Private-déclarations } public { Public-déclarations } end; const UNESEC = 1000; DIXSEC = 4000; ACK = $00; NAK = $FF; MAXTRY = 5; type DBloc = array[ 1..15534 ] of byte; type BHEADER = record case boolean of true : ( Checksum:byte; Lenb : byte; Lenh : byte; Token : byte; ); false : ( Champ : array[ 0..3 ] of byte ); end; var Form1: TForm1; Inlpt : word; Outlpt : word; times : longint; Block : DBLOC; adress :longint; errors: boolean; reste:integer; pop:boolean; implementation {$R *.DFM} function Getlpt( Number : integer ) : boolean; begin Outlpt := MemW[ $0040: 6 + Number * 2 ]; if ( Outlpt <> 0 ) then begin Inlpt := Outlpt + 1; Getlpt := TRUE; end else Getlpt := FALSE; end; function getfirstlpt:byte; var i:integer; begin i:=1; while (not(getlpt(i)) or (i>4)) do inc(i); if (getlpt(i)=false) then i:=0; getfirstlpt:= i; end; function getb:byte; begin getb:=port[inlpt] and $F8 end; procedure putb(what:byte); begin port[outlpt]:=what; end; procedure starttimer; begin times:=GetTickCount; end; function endtimer:longint; begin endtimer:=getTickCount-times; end; function Initlpt( Emetteur : boolean ) : boolean; begin errors:=false; putb($10); putb($18); putb($10); starttimer; if ( Emetteur ) then begin while ( ( GetB <> $00 ) and ( Endtimer <= DIXSEC ) ) do; end else begin while ( ( GetB <> $00 ) and ( Endtimer <= DIXSEC ) ) do; PutB( $10 ); end; Initlpt := ( Endtimer <= DIXSEC ); end; function sendlpt( Wert : byte ) : boolean; var Retour : byte; label fin; begin if errors then goto fin; Starttimer; PutB( Wert and $0F ); while ( ( ( GetB and 128 ) = 0 ) and ( Endtimer <= DIXSEC )) do; if ( Endtimer > DIXSEC ) then begin errors:=true; goto fin; end; Retour := ( GetB shr 3 ) and $0F; Starttimer; PutB( ( Wert shr 4 ) or $10 ); while ( ( ( GetB and 128 ) <> 0 ) and ( Endtimer <= DIXSEC ) ) do if ( Endtimer > DIXSEC ) then begin errors:=true; goto fin; end; Retour := Retour or ( ( GetB shl 1 ) and $F0 ); fin: sendlpt := ( Wert = Retour ); end; function receivelpt : byte; var LoNib, HiNib : byte; label fin; begin if errors then goto fin; Starttimer; while ( ( ( GetB and 128 ) = 0 ) and ( Endtimer <= DIXSEC )) do; if ( Endtimer > DIXSEC ) then begin errors:=true; goto fin; end; LoNib := ( GetB shr 3 ) and $0F; PutB( LoNib ); Starttimer; while ( ( ( GetB and 128 ) <> 0 ) and ( Endtimer <= DIXSEC ) ) do; if ( Endtimer > DIXSEC ) then begin errors:=true; goto fin; end; HiNib := ( GetB shl 1 ) and $F0; PutB( ( HiNib shr 4 ) or $10 ); fin: receivelpt := ( LoNib or HiNib ); end; function checksum8(Nombre:word;Dptr : pointer):byte ; var donnees : ^DBloc ; i:word; ch:byte; begin ch:=0; donnees:=dptr; for i:=1 to Nombre do ch:=ch + Donnees^[ i ]; checksum8:=ch; end; function SendlptBlock( Token : byte; Nombre : word; Dptr : pointer ):boolean; var header : BHEADER; ok : boolean; i : word; trys : word; Donnees : ^DBloc; label fin; begin form1.gauge1.visible:=true; header.Token := Token; header.Lenb := (Nombre and $FF00) shr 8; header.Lenh := Nombre and $FF; header.Checksum:=checksum8(nombre,Dptr); trys := MAXTRY; repeat ok := TRUE; for i := 0 to 3 do ok := ok and sendlpt( Header.Champ[ i ] ); if ( ok ) then ok := ok and sendlpt( ACK ) else ok := ok and sendlpt( NAK ); if ( not ok ) then dec( trys ); until ( ( ok ) or ( trys = 0 ) or (errors)); if ( (trys = 0) or (errors)) then begin goto fin; SendlptBlock:=false; end; if ( Nombre > 0 ) then begin Donnees := DPTR; trys := MAXTRY; repeat ok := TRUE; for i := Nombre downto 1 do begin ok := ok and sendlpt( Donnees^[ i ] ); reste:=trunc(100-i/nombre*100); form1.gauge1.progress:=reste end; if ( ok ) then ok := ok and sendlpt( ACK ) else ok := ok and sendlpt( NAK ); if ( not ok ) then dec( trys ); until ( ( ok ) or ( trys = 0 ) or (errors)); if ( (trys = 0) or (errors)) then begin goto fin; SendlptBlock:=false; end; end; SendlptBlock:=true; fin: form1.gauge1.visible:=false; end; function ReceivelptBlock( var Token : byte; var Len : word; Dptr : pointer ):boolean; var header : BHEADER; ok : boolean; i : word; trys : word; EscapeStatus : boolean; ByteBuffer : byte; Donnees : ^DBloc; label fin,good; begin form1.gauge1.visible:=true; trys := MAXTRY; repeat for i:= 0 to 3 do Header.Champ[ i ] := receivelpt; ByteBuffer := receivelpt; if ( ByteBuffer <> ACK ) then dec( trys ); until ( ( trys = 0 ) or ( ByteBuffer = ACK ) or (errors)); if ( (trys = 0) or (errors)) then begin goto fin; receivelptblock:=false; end; Token := Header.Token; Len := Header.Lenh+(Header.Lenb shl 8); if ( Len > 0 ) then begin Donnees := Dptr; trys := MAXTRY; repeat for i := len downto 1 do begin Donnees^[ i ] := receivelpt; reste:=trunc(100-i/len*100); form1.gauge1.progress:=reste end; ByteBuffer := receivelpt; if ( ByteBuffer <> ACK ) then dec( trys ); until ( ( trys = 0 ) or ( ByteBuffer = ACK ) ); if ( trys = 0 ) then begin goto fin; receivelptblock:=false; end; end; receivelptblock:=true; fin: form1.gauge1.visible:=false; end; function Sendfile(name:string):boolean; var lus:word; Fichier:file; begin assign( Fichier, Name ); reset( Fichier, 1 ); Blockread( Fichier, Block, 15000, Lus ); if lus>0 then Sendfile:=SendlptBlock( 1, Lus, @Block ) else Sendfile:=false; end; procedure TForm1.FormActivate(Sender: TObject); begin adress:=0; showadress(sender); Memo2Click(Sender); SpeedButton8Click(Sender); pop:=true; end; procedure TForm1.SpinButton1DownClick(Sender: TObject); begin if (adress>0) and okm.checked then begin dec(adress); SpeedButton6Click(Sender); end; end; procedure TForm1.SpinButton1UpClick(Sender: TObject); begin if (adress<65536*16) and okm.checked then begin inc(adress); SpeedButton6Click(Sender); end; end; function hextoint(hex:string;n:word):longint; var resu,exp:longint; i:word; begin hex :=UpperCase(hex); resu:=0; exp:=1; for i:=n downto 1 do begin resu:=resu+(Pos(hex[i],'0123456789ABCDEF')-1)*(exp); exp:=exp*16 end; hextoint:=resu; end ; function adresstoint(hex:string):longint; begin adresstoint:=hextoint(Copy(hex, 1, 4),4)shl 4 + hextoint(Copy(hex, length(hex)-3, 4),4) end; procedure TForm1.showadress(Sender: TObject); var i,j,adh,adl:word; adress2:longint; old,old2:string; begin memo1.clear; memo2.clear; memo3.clear; for i:=0 to 29 do begin adress2:=adress+i*16; adl:=adress2 and $FFFF; adh:=(adress2 and $F0000) shr 4; memo1.lines.add(IntToHex(adh,4)+':'+IntToHex(adl,4)) ; old:=''; old2:=''; for j:=1 to 16 do begin old:=old+inttohex(block[i*16+j],2); if block[i*16+j]=0 then old2:=old2+'.' else old2:=old2+char(block[i*16+j]) ; if j mod 2=0 then old:=old+' '; end; memo2.lines.add(old) ; memo3.lines.add(old2) ; end end; procedure TForm1.SpeedButton8Click(Sender: TObject); begin if getfirstlpt=0 then showmessage('Pas de port parallèle détecté'); errors:=false; end; procedure TForm1.SpeedButton6Click(Sender: TObject); var adl,adh,good:word; tok:byte; ok:boolean; begin if (inlpt=0) then SpeedButton8Click(sender); if ((inlpt<>0) and (initlpt(true))) then begin adl:=adress and $FFFF; adh:=(adress and $F0000) shr 4; Block[1]:=lo(adl); Block[2]:= hi(adl); Block[3]:= lo(adh); Block[4]:= hi(adh); Block[5]:= lo(512); Block[6]:= hi(512) ; ok:=false; if SendlptBlock( 1,6,@Block) then ok:=receivelptBlock(tok,good ,@Block); {demande de RAM} if not(ok) or errors then Showmessage('Erreur de transmission !!!!!!!!!!'); showadress(sender); end else Showmessage('Pas de PC distant'); putb($08); errors:=false; end; procedure TForm1.MaskEdit1Change(Sender: TObject); begin if pop then begin adress:=adresstoint(maskedit1.text); if okm.checked=true then SpeedButton6Click(sender); showadress(sender); end; end; procedure TForm1.SpinButton2DownClick(Sender: TObject); begin if (adress+16*30<=65536*16) and okm.checked then begin adress:=adress+16*30; SpeedButton6Click(Sender); end; end; procedure TForm1.SpinButton2UpClick(Sender: TObject); begin if (adress-16*30>=0) and okm.checked then begin adress:=adress-16*30; SpeedButton6Click(Sender); end; end; procedure TForm1.SpeedButton3Click(Sender: TObject); var adl,adh,good:word; adress2:longint; tok:byte; ok:boolean; begin if (inlpt=0) then SpeedButton8Click(sender); if ((inlpt<>0) and (initlpt(true))) then begin adress2 :=adresstoint(maskedit1.text); adl:=adress2 and $FFFF; adh:=(adress2 and $F0000) shr 4; Block[1]:=lo(adl); Block[2]:= hi(adl); Block[3]:= lo(adh); Block[4]:= hi(adh); ok:=SendlptBlock( 7,4,@Block); if not(ok) or errors then Showmessage('Erreur de transmission !!!!!!!!!!'); end else Showmessage('Pas de PC distant'); putb($18); errors:=false; end; procedure TForm1.Memo2Click(Sender: TObject); var ligne,col,pos,adl,adh:word; adress2:longint; begin ligne:=memo2.selstart div 42; col:= (trunc((memo2.selstart mod 42+1) / 2.5)); pos:=16*ligne+col; label1.caption:=inttostr(ligne)+':'+inttostr(col)+':'+inttostr(pos); adress2:=pos+adress; adl:=adress2 and $FFFF; adh:=(adress2 and $F0000) shr 4; pop:=false; maskedit1.text:=inttohex(adh,4)+':'+inttohex(adl,4); pop:=true; end; end.