unit Unit2;
interface
uses
Windows, Sysutils;
// {$DEFINE Set_BreakPoint}
implementation
function GetProcSize(proc : Pointer) : Cardinal;
begin
result := 1;
while(true)
do
begin
if(Byte((pointer(Cardinal(proc) + result - 1))^) = $C3)
then
Break;
Inc(result);
end;
end;
function ExpandFileName(
const FileName:
string):
string;
var
FName: PChar;
Buffer:
array[0..MAX_PATH - 1]
of Char;
begin
SetString(Result, Buffer, GetFullPathName(PChar(FileName), SizeOf(Buffer),
Buffer, FName));
end;
procedure Thread(param:Pointer);
stdcall;
var
(* API-Pointer *)
pLoadLibrary,pGetProcAddress:pointer;
(* inkludierte API-Funktionen *)
LoadLibrary :
function(libname:PChar):THandle;
stdcall;
GetProcAddress :
function(hModule:THandle;ProcName:PChar):Pointer;
stdcall;
MsgBox :
function (h:THandle;Text,Caption:PChar;typ:integer):integer;
stdcall;
(* Zeichenketten *)
user32 : PChar;
kernel32 : PChar;
msg_api : PChar;
(* normale Variablen *)
h:THandle;
begin
asm
{$IFDEF Set_BreakPoint}
int 3
{$ENDIF}
mov eax,[ebp+8]
// Parameter
xor ebx,ebx
mov bl, [eax]
// Parameter - Anzahl d. Zeichenketten
add eax, ebx
inc eax
// Springe hinter die Längenangaben der Zeichenketten
(* LoadLibrary und GetProcAddress werden ermittelt *)
mov ebx, [eax]
// Parameter - LoadLibrary
mov pLoadLibrary,ebx
add eax, 4
mov ebx, [eax]
// Parameter - GetProcAddess
mov pGetProcAddress,ebx
(* Zeichenketten *)
xor ecx, ecx
xor edx, edx
mov al,[ebp+8]
// eax = Länge der Zeichenketten
mov ebx, eax
// ebx = Pointer auf Zeichenkette
mov cl, [eax]
// ecx = Anzahl d. Zeichenketten
add ebx, ecx
add ebx, 9
inc eax
mov user32, ebx
// Zeichenkette 1 - user32.dll
inc ebx
mov
dl,[eax]
add ebx,edx
inc eax
mov kernel32, ebx
// Zeichenkette 2 - kernel32.dll
inc ebx
mov
dl,[eax]
add ebx,edx
inc eax
mov msg_api, ebx
// Zeichenkette 3 - MessageBoxA
end;
@LoadLibrary:=pLoadLibrary;
@GetProcAddress:=pGetProcAddress;
h:=LoadLibrary('
user32.dll');
@MsgBox:=GetProcAddress(h,msg_api);
MsgBox(0,user32,kernel32,0);
end;
var param : pByteArray;
p : Pointer;
pAPI : Pointer;
tmp : DWORD;
s : PChar;
len : byte;
num : byte;
hProcess : THandle;
ThreadSize: DWORD;
procedure AddPtr(
var p:Pointer;i:integer);
begin
p:=ptr(DWORD(p)+i);
end;
begin
ThreadSize:=GetProcSize(@Thread);
num:=0;
hProcess:=OpenProcess(PROCESS_ALL_ACCESS,false,GetCurrentProcessID());
param:=VirtualAllocEx(hProcess,
nil, 30 + threadsize, MEM_COMMIT, PAGE_READWRITE);
WriteProcessMemory(hProcess,param,@num,SizeOf(num),tmp);
p:=param;
(* Die Länge des Strings "user32.dll" wird ermittelt und gespeichert *)
AddPtr(p,1);
len:=length('
user32.dll');
inc(num);
WriteProcessMemory(hProcess,p,@len,SizeOf(len),tmp);
(* Die Länge des Strings "kernel32.dll" wird ermittelt und gespeichert *)
AddPtr(p,1);
len:=length('
kernel32.dll');
inc(num);
WriteProcessMemory(hProcess,p,@len,SizeOf(len),tmp);
(* Die Länge des Strings "MessageBoxA" wird ermittelt und gespeichert *)
AddPtr(p,1);
len:=length('
MessageBoxA');
inc(num);
WriteProcessMemory(hProcess,p,@len,SizeOf(len),tmp);
(* Die Anzahl der Zeichenketten wird aktuallisiert *)
WriteProcessMemory(hProcess,param,@num,SizeOf(num),tmp);
(* Die API-Adressen werden gespeichert *)
AddPtr(p,1);
pAPI:=GetProcAddress(GetModuleHandle('
kernel32.dll'), '
LoadLibraryA');
WriteProcessMemory(hProcess,p,@pAPI,SizeOf(pAPI),tmp);
AddPtr(p,SizeOf(pAPI));
pAPI:=GetProcAddress(GetModuleHandle('
kernel32.dll'), '
GetProcAddress');
WriteProcessMemory(hProcess,p,@pAPI,SizeOf(pAPI),tmp);
(* Zeichenketten werden geschrieben *)
(* user32.dll *)
AddPtr(p,SizeOf(pAPI));
s:='
user32.dll';
pAPI:=@s;
pAPI:=Pointer(DWORD(pAPI^));
WriteProcessMemory(hProcess,p,pAPI,length(s),tmp);
AddPtr(p,length(s)+1);
(* kernel32.dll *)
s:='
kernel32.dll';
pAPI:=@s;
pAPI:=Pointer(DWORD(pAPI^));
WriteProcessMemory(hProcess,p,pAPI,length(s),tmp);
AddPtr(p,length(s)+1);
(* MessageBoxA *)
s:='
MessageBoxA';
pAPI:=@s;
pAPI:=Pointer(DWORD(pAPI^));
WriteProcessMemory(hProcess,p,pAPI,length(s),tmp);
AddPtr(p,length(s)+1);
writeProcessMemory(hProcess,p,@Thread,1024,tmp);
CreateRemoteThread(hProcess,
nil,0,p,param,0,tmp);
end.