Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Win32/Win64 API (native code) (https://www.delphipraxis.net/17-win32-win64-api-native-code/)
-   -   API Hook funktioniert nicht global (https://www.delphipraxis.net/157617-api-hook-funktioniert-nicht-global.html)

Neutral General 18. Jan 2011 14:27

API Hook funktioniert nicht global
 
Hallo,

Das hier ist Teil 2 zu Kleine Verständnisfrage zu globalen Hooks.

Jetzt wollte ich eine API Funktion in der fremden Anwendung in der DLL hooken.
Und zwar so (PS: Ich muss nur in meine "Ersatzfunktion" springen. Ein Rücksprung in den Originalcode ist in meinem Fall nicht notwendig):

Delphi-Quellcode:
function HookIsClipboardFormatAvailable: Boolean;
var func: Pointer;
    hProc: THandle;
    jmp: TJump;
    bw: Cardinal;
begin
  func := GetProcPtr('user32.dll','IsClipboardFormatAvailable');

  hProc := GetCurrentProcess;
  try
    // VirtualProtect(func,4096,PAGE_EXECUTE_READWRITE,nil);
    jmp := Jump(@NewIsClipboardFormatAvailable);
    WriteProcessMemory(hProc,func,@jmp,SizeOf(TJump),bw);
    Result := bw = SizeOf(TJump);
  finally
    CloseHandle(hProc);
  end;
end;

function NewIsClipboardFormatAvailable(AFormat: Cardinal): BOOL; stdcall;
begin
  Result := true;
end;
Verwendete Funktionen/Typen:

Delphi-Quellcode:
type
  TJump = packed record
    Push: Byte;
    Dest: Pointer;
    Retn: Byte;
    Nops: Array[0..3] of Byte;
  end;

implementation

function Jump(ADest: Pointer): TJump;
begin
  Result.Push := $68;
  Result.Dest := ADest;
  Result.Retn := $C3;
  FillChar(Result.Nops[0],SizeOf(Result.Nops),$90);
end;

function GetProcPtr(ADll: String; AProc: String): Pointer;
var hLib: HModule;
begin
  hLib := LoadLibrary(PChar(ADll));
  if hLib <> 0 then
  begin
    try
      Result := GetProcAddress(hLib,PChar(AProc));
    finally
      FreeLibrary(hLib);
    end;
  end
  else
    Result := nil;
end;
Dieser Code funktioniert wenn ich ihn lokal aus meinem Prozess aufrufe und auch in meiner eigenen Anwendung per Hook. In fremden Anwendungen scheints aber nicht zu funktionieren (Originalfunktion wird scheinbar aufgerufen).

Allerdings liefert mir HookIsClipboardFormatAvailable in allen Prozessen true zurück. Bin jetzt etwas verwundert warum das nicht funktioniert. :gruebel:

Gruß
Neutral General

Namenloser 18. Jan 2011 14:37

AW: API Hook funktioniert nicht global
 
Das entscheidene wäre, zu wissen, wie und wo du diesen Code aufrufst. Wenn du eine Funktion in einem Fremdprozess hooken willst, musst du erst mal einen Thread in diesen Prozess injizieren, da deine beiden Prozesse ja verschiedene Adressräume haben.

Neutral General 18. Jan 2011 14:42

AW: API Hook funktioniert nicht global
 
Zitat:

Zitat von NamenLozer (Beitrag 1075528)
Das entscheidene wäre, zu wissen, wie und wo du diesen Code aufrufst. Wenn du eine Funktion in einem Fremdprozess hooken willst, musst du erst mal einen Thread in diesen Prozess injizieren, da deine beiden Prozesse ja verschiedene Adressräume haben.

:arrow: Siehe den im ersten Post verlinkten Vorgängerthread.

Die HookIsClipboardFormatAvailable wird im Hook-Callback in der DLL aufgerufen:
Delphi-Quellcode:
function HookProc(code: Integer; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
begin
  if FHook <> 0 then
  begin
    if code < HC_ACTION then
      Result := CallNextHookEx(FHook,code,wParam,lParam)
    else
    begin
      if (not FHooked) and (code >= HC_ACTION) then
      begin
        HookIsClipboardFormatAvailable;
        FHooked := true;
      end;
      Result := CallNextHookEx(FHook,code,wParam,lParam);
    end;
  end
  else
    Result := 0;
end;
Müsste nach meinem Verständnis also funktionieren...

Assarbad 18. Jan 2011 15:01

AW: API Hook funktioniert nicht global
 
Vista? Dann lies dich mal zu MSDN-Library durchsuchenASLR schlau. Mit etwas Glück haste das Problem nicht, aber früher oder später würde es dich ohnehin einholen.

Neutral General 18. Jan 2011 15:07

AW: API Hook funktioniert nicht global
 
Na gut, aber inwieweit wird mir das Probleme machen? Das verstehe ich nicht?
Ermittel ich die Adresse der zu hookenden Funktion nicht dynamisch?

Da dürfte das Problem doch gar nicht auftauchen oder? Oder habe ich da etwas falsch verstanden?
Wo genau siehst du das Problem und was kann ich dagegen tun?

Assarbad 18. Jan 2011 15:11

AW: API Hook funktioniert nicht global
 
Zitat:

Zitat von Neutral General (Beitrag 1075543)
Na gut, aber inwieweit wird mir das Probleme machen? Das verstehe ich nicht?
Ermittel ich die Adresse der zu hookenden Funktion nicht dynamisch?

Kann ich nicht erkennen, daß du im Zielprozess irgendwas dynamisch ermittelst. Und genau da liegt das Problem ...

Neutral General 18. Jan 2011 15:14

AW: API Hook funktioniert nicht global
 
Ist LoadLibrary + GetProcAddress nicht dynamisch? :shock:

PS: In meiner WinXP-VM funktioniert es aber auch nicht...

Assarbad 18. Jan 2011 15:17

AW: API Hook funktioniert nicht global
 
Zitat:

Zitat von Neutral General (Beitrag 1075548)
Ist LoadLibrary + GetProcAddress nicht dynamisch? :shock:

Doch. Aber es ist nicht im Zielprozeß. Wer lesen kann ... :zwinker:

Neutral General 18. Jan 2011 15:22

AW: API Hook funktioniert nicht global
 
Ja doch.. Oder nicht?! :shock:

DLL:
Delphi-Quellcode:
library HookDLL;

uses
  Windows,
  SysUtils,
  Classes,
  HookUtils in 'HookUtils.pas';

{$R *.res}

var
  FHook: HHOOK = 0;
  FHooked: Boolean = false;

function NewIsClipboardFormatAvailable(AFormat: Cardinal): BOOL; stdcall;
begin
  Result := true;
end;

function HookIsClipboardFormatAvailable: Boolean;
var func: Pointer;
    hProc: THandle;
    jmp: TJump;
    bw: Cardinal;
begin
  func := GetProcPtr('user32.dll','IsClipboardFormatAvailable');

  hProc := GetCurrentProcess;
  try
    jmp := Jump(@NewIsClipboardFormatAvailable);
    WriteProcessMemory(hProc,func,@jmp,SizeOf(TJump),bw);
    Result := bw = SizeOf(TJump);
  finally
    CloseHandle(hProc);
  end;
end;

function HookProc(code: Integer; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
begin
  if FHook <> 0 then
  begin
    if code < HC_ACTION then
      Result := CallNextHookEx(FHook,code,wParam,lParam)
    else
    begin
      if (not FHooked) and (code >= HC_ACTION) then
      begin
        FHooked := true;
        HookIsClipboardFormatAvailable;
      end;
      Result := CallNextHookEx(FHook,code,wParam,lParam);
    end;
  end
  else
    Result := 0;
end;

procedure InstallHook; stdcall;
begin
  FHook := SetWindowsHookEx(WH_GETMESSAGE,HookProc,hInstance,0);
end;

procedure UnInstallHook; stdcall;
begin
  if FHook <> 0 then
    UnhookWindowsHookEx(FHook);
end;

exports
  InstallHook,
  UnInstallHook,
  HookProc;

begin

end.

HookUtils:

Delphi-Quellcode:
unit HookUtils;

interface

uses
  Windows;

type
  TJump = packed record
    Push: Byte;
    Dest: Pointer;
    Retn: Byte;
    Nops: Array[0..3] of Byte;
  end;

  function Jump(ADest: Pointer): TJump;
  function GetProcPtr(ADll: String; AProc: String): Pointer;

implementation

function Jump(ADest: Pointer): TJump;
begin
  Result.Push := $68;
  Result.Dest := ADest;
  Result.Retn := $C3;
  FillChar(Result.Nops[0],SizeOf(Result.Nops),$90);
end;

function GetProcPtr(ADll: String; AProc: String): Pointer;
var hLib: HModule;
begin
  hLib := LoadLibrary(PChar(ADll));
  if hLib <> 0 then
  begin
    try
      Result := GetProcAddress(hLib,PChar(AProc));
    finally
      FreeLibrary(hLib);
    end;
  end
  else
    Result := nil;
end;

end.
Oder hab ich da tatsächlich grundlegend etwas nicht verstanden?!
Jetzt bin ich verwirrt.


Alle Zeitangaben in WEZ +1. Es ist jetzt 08:07 Uhr.

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