Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Delphi Code-Injection JMP Adresse ermitteln... (https://www.delphipraxis.net/134353-delphi-code-injection-jmp-adresse-ermitteln.html)

xice 20. Mai 2009 13:48


Delphi Code-Injection JMP Adresse ermitteln...
 
Hallo !

Ich versuche eine Art Code-Injection zu programmieren.
Mein Problem ist nun die Sprungstelle zum Code-Cave
Die Adresse stimmt nicht mit der zugewiesenen überein.

Die Sprungadresse müsste z.B.: $080C0000 lauten. Ich kriege aber $0046e1a0

Mach ich was falsch ? Bin für jede Hilfe dankbar!

Delphi-Quellcode:
var mem :Pointer;

...

procedure Inject;
begin
  asm
    push mem <-- Sprungstelle zum Code-Cave ... Adresse wird weiter unten im Quelltext ermittelt
    ret
    nop
  end;
end;

procedure Code_Cave;
begin
  asm
    mov [edi+04],00000001
    fcom dword ptr [edi+04]
    add esp,08
    fnstsw ax
    push $006C37C2
    ret
  end;
end;

procedure Test;
var process,PID:Cardinal;
    wbyte:DWORD;
begin
  PID:=GetPID('Anwendung');
  process := OpenProcess(PROCESS_ALL_ACCESS,false,PID);

 // Speicher anfordern
  mem := VirtualAllocEx(process, nil,19,MEM_COMMIT,PAGE_EXECUTE_READWRITE);

 //-- Schreibe in mem
  WriteProcessMemory(process,mem,@Code_Cave,19, wbyte);

 //-- Überschreibe vorhanden Code durch ein sprung zum Code-Cave
  WriteProcessMemory(process,ptr($006C37C2),@Inject,8, wbyte);

//  VirtualFreeEx(process,mem,0,MEM_RELEASE);
  CloseHandle(process);
end;

Fridolin Walther 20. Mai 2009 19:02

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Das kann nicht funktionieren.
Delphi-Quellcode:
procedure Inject;
begin
  asm
    push mem <-- Sprungstelle zum Code-Cave ... Adresse wird weiter unten im Quelltext ermittelt
    ret
    nop
  end;
end;
Das bedeutet nicht, daß da mem durch die Adresse die in mem steht getauscht wird. Dazu müsste sich der Code selbst modifizieren zur Laufzeit. Stattdessen wird daraus:
Delphi-Quellcode:
push dword ptr [Adresse von mem]
ret
nop
Da an der Adresse im fremden Prozess aber irgendetwas steht nur wahrscheinlich nicht die Adresse der Code Cave, wird entsprechend der falsche Wert gelesen und auf den Stack gepackt ;).

Lösung: Mach Inject zu nem Byte Array. In das packst die korrekten Opcodes (Intel Manual) und die korrekte Adresse zu der gesprungen werden soll und schreibst das Byte Array in den Zielprozess.

brechi 21. Mai 2009 12:09

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Delphi-Quellcode:
  TJmpCode = packed record
    bPush: Byte;
    pAddr: Pointer;
    bRet : Byte;
  end;
mit

Delphi-Quellcode:
  JumpCode.bPush := $68;
  JumpCode.bRet := $C3;
  JumpCode.bAddr := // Deine addresse
und WriteProcessMemory(.. jmpCode, SizeOf(TJmpCode)) sollte helfen

xice 21. Mai 2009 21:35

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Dank eurer Lösung hab ich das Problem gelöst.

Ich hätte da noch gewusst, ob es eine Möglichkeit gibt,
die Größe der Code_Cave Procedure zu ermitteln,
damit ich mit VirtualAllocEx soviel Speicher reservieren kann, wie Code_Cave umfasst ?

Mein jetziger Ansatz ist:

Delphi-Quellcode:
//--Code_Cave SIZE
size := DWORD(@Code_Cave) - DWORD(@Inject);
Damit erhalte ich 16 Bytes, was zu wenig ist, denn ich brauche 19.
Wo sind die restlichen 3 Bytes ?

Danke.

Fridolin Walther 21. Mai 2009 21:50

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Ich bin mir grade nicht so sicher, ob man davon ausgehen kann, daß die Funktionen im Kompilat in exakt der Reihenfolge vorliegen wie im Source und nicht durch andere Funktionen unterbrochen sind. Darauf würdest Du Dich in Deinem Falle ja verlassen. Aber angenommen, das man davon ausgehen kann, ist Deine Berechnung falsch:

Inject ist vor Code_Cave definiert (liegt also auch im Speicher vor Code_Cave). So wäre der Abstand zw. Code_Cave und Inject die größe von Inject, nicht von Code_Cave. Dort kommen 16 Bytes auf Grund des Alignments durchaus hin. Du müsstest den Abstand zw. Test und Code_Cave berechnen um die Größe von Code_Cave zu erhalten.

xice 21. Mai 2009 22:03

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Stimmt, die Berechnung war falsch.
Die Reihenfolge scheint sich wohl nicht zu ändern.

Aber mit der Korrektur erhalte ich nun 24 Bytes, also 5 zuviel.

Fridolin Walther 21. Mai 2009 22:17

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Den exakten Wert wirst Du so wahrscheinlich eher nicht errechnen auf Grund des Alignments, außer natürlich es fällt zufällig auf eine Alignmentgrenze. Allerdings sollte es nicht wirklich ein Problem sein die Padding Bytes mit zu kopieren.

Apollonius 22. Mai 2009 10:01

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Mit VirtualAllocEx kannst du sowieso nur Vielfache von 4096 Byte (das ist normalerweise die Speicherseitengröße) reservieren - eigentlich kannst du dir den Aufwand also sparen.

xice 24. Mai 2009 21:23

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Danke nochmal für die Informationen.
Ich hab da noch ein kleines Problem.

Wie kann ich aus diesem ASM-Code

Delphi-Quellcode:
mov [edi+04],00000001
eine variable Wertübergabe machen ?

Delphi-Quellcode:
mov [edi+04],Variable

xice 18. Jun 2009 14:53

Re: Delphi Code-Injection JMP Adresse ermitteln...
 
Zitat:

Zitat von xice
Danke nochmal für die Informationen.
Ich hab da noch ein kleines Problem.

Wie kann ich aus diesem ASM-Code

Delphi-Quellcode:
mov [edi+04],00000001
eine variable Wertübergabe machen ?

Delphi-Quellcode:
mov [edi+04],Variable

Problem gelöst...

Delphi-Quellcode:
type TData=packed record
   b1:array [0..2] of Byte;
    s:single;
end;


Alle Zeitangaben in WEZ +1. Es ist jetzt 03:40 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz