关于HOOK 函数,能勾住,但是就是无法替换原有函数。

大肚肥肥 2010-03-11 06:31:32
代码 如下 ,这里是勾住任务栏下一个窗体的HOOK,只要内存替换这里一打开则直接报错。
OldProc := TFarProc(GetWindowLong(HReBar, GWL_WNDPROC));
SetWindowLong(HReBar, GWL_WNDPROC, integer(@WinProc));





unit Unit1;

interface
uses windows, SysUtils, Messages;
var
OldHook: HHOOK; //用来保存HOOK的返回值
OldProc: TFarProc; //用来指向窗口消息
HTrayWnd, HReBar: HWND;


function SetHook: Boolean; stdcall; export;
function UnSetHook: Boolean; stdcall; export;
function HookProc(nCode: Integer; {} wParam: WPARAM; {} lParam: LPARAM {}): LRESULT; stdcall; export;
function WinProc(Hwnd, Msg, wParam, lParam: longint): LRESULT; stdcall; export;

implementation
{###################################################################################}
//安装HOOK

function SetHook: Boolean; stdcall;

begin
if OldHook = 0 then
begin
HTrayWnd := FindWindow('Shell_TrayWnd', nil);
HReBar := FindWindowEx(HTrayWnd, 0, 'ReBarWindow32', nil);
OldHook := SetWindowsHookEx(WH_CBT, @HookProc, HInstance, GetWindowThreadProcessId(HReBar, nil));
if OldHook <> 0 then
Result := True;
end
else
Result := False;
end;

{###################################################################################}
//HOOK回调函数

function HookProc(nCode: Integer; wParam: WPARAM; lParam: LPARAM ): LRESULT; stdcall;
begin
HTrayWnd := FindWindow('Shell_TrayWnd', nil);
HReBar := FindWindowEx(HTrayWnd, 0, 'ReBarWindow32', nil);
//OldProc := TFarProc(GetWindowLong(HReBar, GWL_WNDPROC));
// SetWindowLong(HReBar, GWL_WNDPROC, integer(@WinProc));
Result := CallNextHookEx(OldHook, nCode, WParam, lParam); }
end;

{###################################################################################}
//自定义消息处理

function WinProc(Hwnd, Msg, wParam, lParam: longint): LRESULT; stdcall;
begin
Result := 1;
case Msg of
WM_MOVE: begin messagebox(0, 'move', '', 0); exit; end;
WM_WINDOWPOSCHANGING: begin messagebox(0, 'WM_WINDOWPOSCHANGING', '', 0); exit; end;
end;
Result := CallWindowProc(OldProc, Hwnd, Msg, wParam, Longint(@lParam));
end;

function UnSetHook: Boolean; stdcall;
begin
if OldHook <> 0 then
begin
UnHookWindowsHookEx(OldHook);
OldHook := 0;
Result := True;
end
else
Result := False;
end;
end.


...全文
260 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
大肚肥肥 2010-03-17
  • 打赏
  • 举报
回复
还是错误,但是找到其他办法了,加入以下代码就OK了。应该是操作EXPLORER 需要建立内存映射。

procedure MyDLLHandler(Reason: Integer);
var
FHandle: LongWORD;
begin
case Reason of
DLL_PROCESS_ATTACH:
begin {建立文件映射,以实现DLL中的全局变量}
FHandle := CreateFileMapping($FFFFFFFF, nil, PAGE_READWRITE, 0, $FF, 'MYDLLDATA');
if FHandle = 0 then
if GetLastError = ERROR_ALREADY_EXISTS then
begin
FHandle := OpenFileMapping(FILE_MAP_ALL_ACCESS, False, 'MYDLLDATA');
if FHandle = 0 then Exit;
end else Exit;
DLLData := MapViewOfFile(FHandle, FILE_MAP_ALL_ACCESS, 0, 0, 0);
if DLLData = nil then
CloseHandle(FHandle);
end;
DLL_PROCESS_DETACH:
if Assigned(DLLData) then
begin
UnmapViewOfFile(DLLData);
DLLData := nil;
end;
DLL_THREAD_ATTACH: ;
DLL_THREAD_DETACH: ;
end;
end;

exports
HookProc, EnableMsgHook, DisableMsgHook;
begin
DLLProc := @MyDLLHandler;
MyDLLhandler(DLL_PROCESS_ATTACH);
end.
cnzdgs 2010-03-17
  • 打赏
  • 举报
回复
function HookProc(nCode: Integer; wParam: WPARAM;  lParam: LPARAM ): LRESULT; stdcall;
begin
if OldProc = nil then
begin
HTrayWnd := FindWindow('Shell_TrayWnd', nil);
HReBar := FindWindowEx(HTrayWnd, 0, 'ReBarWindow32', nil);
OldProc := TFarProc(GetWindowLong(HReBar, GWL_WNDPROC));
SetWindowLong(HReBar, GWL_WNDPROC, integer(@WinProc));
end;
Result := CallNextHookEx(OldHook, nCode, WParam, lParam); }
end;
大肚肥肥 2010-03-16
  • 打赏
  • 举报
回复
function HookProc(nCode: Integer; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
begin
HTrayWnd := FindWindow('Shell_TrayWnd', nil);
HReBar := FindWindowEx(HTrayWnd, 0, 'ReBarWindow32', nil);
if OldProc = nil then
OldProc := TFarProc(GetWindowLong(HReBar, GWL_WNDPROC));
if OldProc <> nil then
SetWindowLong(HReBar, GWL_WNDPROC, integer(@WinProc));
Result := CallNextHookEx(OldHook, nCode, WParam, lParam);
end;
cnzdgs 2010-03-16
  • 打赏
  • 举报
回复
把改过之后的HookProc贴出来看看.
大肚肥肥 2010-03-15
  • 打赏
  • 举报
回复
直接 CallWindowProc 会 除错的。。
cnzdgs 2010-03-14
  • 打赏
  • 举报
回复
你先试试在WinProc直接CallWindowProc,不做其它处理,看看是否有问题。
大肚肥肥 2010-03-13
  • 打赏
  • 举报
回复
大大们在解释一下嘛。。
dj2437 2010-03-12
  • 打赏
  • 举报
回复
有些内存有属性,读写前必需修改其属性,为可读写
大肚肥肥 2010-03-12
  • 打赏
  • 举报
回复
郁闷。。。挂上后不立马除错,但是 运行不到1分钟以内 explorer 立马死掉。。问题基本还是没解决。。。
大肚肥肥 2010-03-12
  • 打赏
  • 举报
回复
if OldProc = nil then
OldProc := TFarProc(GetWindowLong(HReBar, GWL_WNDPROC));
if OldProc <> nil then
SetWindowLong(HReBar, GWL_WNDPROC, integer(@WinProc));

加上后,已能正常调试,感谢楼上大大!!
大肚肥肥 2010-03-12
  • 打赏
  • 举报
回复
怎么改其属性?

用什么函数?

再给点提示好么?楼上大大
cnzdgs 2010-03-11
  • 打赏
  • 举报
回复
判断一下OldProc的值,不要重复替换。
贝隆 2010-03-11
  • 打赏
  • 举报
回复
UP UP UPUPUPUPUPUPUP

1,183

社区成员

发帖
与我相关
我的任务
社区描述
Delphi Windows SDK/API
社区管理员
  • Windows SDK/API社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧