📄 httpproxyextend.pas
字号:
unit httpProxyExtend;
interface
uses proxy2,mem_utils;
type
THttpProxy = class(TProxyClient)
protected
dataAll_P1, dataAll_P2 : TMemWeb;
(* alle Daten die empfangen wurden, nach OnDataEvent-Modifications,
aber OHNE Header/Content-Event Modifications *)
gotHeader_P1,gotHeader_P2 : boolean; //Header bereits empfangen
// EVENT Function Pointer
Proc_P1_HttpHeader, Proc_P1_HttpHeaderModified, Proc_P2_HttpHeader,
Proc_P1_HttpContent, Proc_P2_HttpContent : TProxyClientData;
// EVENT WRAPPER METHODS
function On_P1_Header(p : pointer; VAR s : longint) : pointer;
function On_P1_HeaderModified(p : pointer; VAR s : longint) : pointer;
function On_P2_Header(p : pointer; VAR s : longint) : pointer;
function On_P1_Content(p : pointer; VAR s : longint) : pointer;
function On_P2_Content(p : pointer; VAR s : longint) : pointer;
//overridden methods
procedure P1_DataAvailable(Sender: TObject; Error: Word); override;
procedure P2_DataAvailable(Sender: TObject; Error: Word); override;
//new stuff
function foundBreak(dataAll : TMem; VAR dataHeader: TMem; VAR dataRest: TMem) : boolean;
public
function search_destaddr : boolean;
procedure before_work; override;
procedure look4addr; override;
constructor Create; override;
destructor Destroy; override;
published
property OnP1HttpHeader : TProxyClientData
read Proc_P1_HttpHeader
write Proc_P1_HttpHeader;
property OnP1HttpHeaderModified : TProxyClientData
read Proc_P1_HttpHeaderModified
write Proc_P1_HttpHeaderModified;
property OnP2HttpHeader : TProxyClientData
read Proc_P2_HttpHeader
write Proc_P2_HttpHeader;
property OnP1HttpContent : TProxyClientData
read Proc_P1_HttpContent
write Proc_P1_HttpContent;
property OnP2HttpContent : TProxyClientData
read Proc_P2_HttpContent
write Proc_P2_HttpContent;
end;
(* type
THttpProxyExtended = class(THttpProxy)
protected
p2data : TMemWeb;
procedure logDataP2(p : pointer; VAR s:longint); virtual;
function Do_P2_DataAvailable(p : pointer; VAR s : longint) : pointer; override;
procedure P2_SessionClosed(Sender: TObject; Error: Word); override;
public
destructor destroy; override;
end;
*)
implementation
uses sysutils,httphelp,windows, dialogs, wsocket;
////////////////// HTTP PROXY ///////////////////////////
constructor THttpProxy.Create;
begin;
gotHeader_P1:=false;
gotHeader_p2:=false;
inherited;
end;
destructor THttpProxy.destroy;
begin;
if Assigned(dataAll_P1.p) then begin;
dataAll_P1.free_mem;
end;
if Assigned(dataAll_P2.p) then begin;
dataAll_P2.free_mem;
end;
inherited destroy;
end;
procedure THttpProxy.before_work;
begin;
if connectiontype=connect2sameproxy then begin;
On_p2_dbgout(Pchar('Tries to connect to : '+dest_addr+' at Port:'+dest_port));
got_addr:=true;
FP2Socket.addr:=dest_addr;
FP2Socket.Port:=dest_port;
Do_Connect2;
end;
end;
function THttpProxy.foundBreak(dataAll : TMem; VAR dataHeader: TMem; VAR dataRest: TMem) : boolean;
var break_p,break_epos_p : pointer;
break_s, break_epos_s : longint;
ret : boolean;
const break : string = chr(13)+chr(10)+chr(13)+chr(10);
begin;
ret:=false;
break_p:=mem_pos(dataAll.p,dataAll.s,pchar(break),4,break_s);
if ((break_p<>NIL) and (break_s>=4)) then begin;
ret:=true;
//Splitten urgl:
break_epos_p:=mem_epos(dataAll.p,dataAll.s,pchar(break),4,break_epos_s);
dataRest.s:=break_epos_s;
dataHeader.s:=dataAll.s-break_epos_s;
On_P2_dbgout(PCHAR('dataRest.s='+inttostr(dataRest.s)+' dataHeader='+inttostr(dataHeader.s)+
'dataAll.s='+inttostr(dataAll.s)));
dataHeader.init:=true;
getmem(dataHeader.p,dataHeader.s);
mem_copy(dataHeader.p,dataAll.p,dataHeader.s);
if (dataRest.s>0) then begin;
getmem(dataRest.p,dataRest.s);
dataRest.init:=true;
mem_copy(dataRest.p,break_epos_p,dataRest.s);
end;
(* On_P2_dbgout(mem2pchar(dataHeader.p,dataHeader.s));
On_P2_dbgout(pchar(mem_show(dataRest.p,dataRest.s)));
*)
end;
result:=ret;
end;
procedure THttpProxy.P2_DataAvailable(Sender: TObject; Error: Word);
var
Buffer : array [0..4095] of char; //besser 32.767 = 32 KB * 1024 -1
Count : longint;
new_data : pointer; //Daten nach dem sie ueber die Handlerfunktion ver鋘dert werden kann
dataPacket,dataHeader,dataRest : TMemWeb;
begin
{ Receive as much data as possible }
Count := FP2Socket.Receive(@Buffer, SizeOf(Buffer)-1);
On_P2_dbgout(Pchar('P2 Data received ('+inttostr(count)+' Bytes)'));
if (count>0) then begin;
lasttransmission:=gettickcount;
anyrec:=true;
//copy buffer to new memory space
getmem(new_data,count);
mem_copy(new_data,@buffer, count);
dataPacket.p:=new_data;
dataPacket.s:=count;
dataPacket.init:=true;
//OnP2DataReceived EVENT
dataPacket.p:=On_P2_DataAvailable(dataPacket.p,dataPacket.s);
//(modifiziertes) dataPacket in den dataAll Stream schreiben
dataAll_P2.cat(dataPacket);
if dataPacket.s > 0 then begin;
if (gotHeader_P2) then begin
dataPacket.p:=On_P2_Content(dataPacket.p,dataPacket.s); //streaming-EVENT
end
else begin // Header bisher noch nicht empfangen
if (foundBreak(dataAll_P2,dataHeader,dataRest)) then begin;
gotHeader_P2:=true;
//On_P2_dbgout(mem2pchar(dataHeader.p,dataHeader.s));
//On_P2_dbgout(pchar(mem_show(dataRest.p,dataRest.s)));
dataHeader.p:=On_P2_Header(dataHeader.p,dataHeader.s); //en bloc-EVENT
dataRest.p:=On_P2_Content(dataRest.p,dataRest.s); //streaming-EVENT
//dataPacket wird aus den R點kgabedaten der Events neu gebildet
dataPacket.setfrom_mem(dataHeader);
dataPacket.cat(dataRest);
dataHeader.free_mem;
dataRest.free_mem;
end; //foundBreak
end; //else gotHeader
end; //dataPacket.s>0
//DataPacket Senden
if dataPacket.p<>NIL then begin;
if dataPacket.s > 0 then begin;
if Fp1Socket.State=wsconnected then begin;
Do_Send1(dataPacket.p,dataPacket.s);
end;
end;
end;
//und Speicher freigeben
dataPacket.free_mem;
end; //count>0
end;
procedure THttpProxy.look4addr;
begin;
On_P1_dbgout('P1 looking for HTTP-dest. addr....');
if search_destaddr=true then begin;
// do_vip_dbgout(Pchar(dest_port));
fp2socket.Addr:=dest_addr;
fp2socket.port:=dest_port;
fp2socket.proto:=DC_TCP;
Do_Connect2;
got_addr:=true;
end;
end;
function THttpProxy.search_destaddr : boolean; //hat noch ne make!! brauch #0 ?
var
bufp : array[0..2000] of char;
i, i2: longint;
ret : boolean;
ndests, nport: string;
length_buf : integer;
p2,p3,destp : pchar;
ln1,ln1_up: string;
ende_ln1 : longint;
ftpi,i3 : longint;
param,param2,param3 : string;
parami,parami2 : longint;
userstr, pwdstr : string;
new_p : pointer;
new_s : longint;
header : boolean;
begin;
if buf_init=true then begin
ret:=false;
i:=0;
if buf_s<1000 then i:=buf_s;
if buf_s>=1000 then i:=999;
mem_copy(bufp,buf_p,i);
bufp[i]:=#0;
ln1:= readfirstln(bufp,i, ende_ln1);
ln1_up:=ansiuppercase(ln1);
ftpi:=pos('FTP://',ln1_up);
if ftpi>0 then begin;
// Do_Send1str('FTP Over HTTP direct to the inet NOT supported yet');
end;
//showmessage(bufp);
p2:=nil; p3:=nil;
p2:=strPos(bufp, PChar('Host:'));
if p2<>NIL then begin;
p3:=AnsiStrPos(buf_p,pchar(chr(13)+chr(10)+chr(13)+chr(10)));
if p3=nil then begin;
on_p1_dbgout('Header (nach Host:) noch nicht vollst鋘dig abgeschlossen:');
//do_p1_dbgout(pchar(mem_show(buf_p,buf_s)));
header:=false;
end else begin;
on_p1_dbgout('Header vollst鋘dig empfangen');
header:=true;
buf_p:=on_P1_Header(buf_p,buf_s);
end;
p3:=strScan(p2,chr(10));
end;
ndests:='';
if ((p2<>nil) and (p3<>nil)) and (header) then begin;
length_buf:=strlen(p2)-strlen(p3)-1;
destp:=stralloc(length_buf+1);
strmove(destp,p2, length_buf);
destp[length_buf]:=#0;
on_P1_dbgout(Pchar('Analyse "'+destp+'"; '));
//pchar
// showmessage(destp);
ndests:=destp;
strdispose(destp);
delete(ndests,1,6);
i2:=pos(':',ndests);
nport:='';
if i2>0 then begin;
nport:=copy(ndests,i2+1,length(ndests)-i2);
dest_port:=nport;
ndests:=copy(ndests,1,i2-1);
on_P1_dbgout(Pchar('New port found: "'+nport+'"; '));
end;
// showmessage(ndests);
on_P1_dbgout(Pchar('Host found: "'+ndests+'"; '));
dest_addr:=ndests;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -