gpt4 book ai didi

delphi - EnumWindows 在 64 位 Delphi 中行为异常

转载 作者:行者123 更新时间:2023-12-03 15:47:52 30 4
gpt4 key购买 nike

我正在使用 Delphi XE3,在 64 位 Windows 8 计算机上构建 32 位和 64 位应用程序。

我正在使用 EnumWindows 来查找给定进程 ID 的进程主窗口的 Windows 句柄。该代码在回调例程中使用 LPARAM 参数来传递指向记录的指针。

我使用的代码在 32 位构建中运行良好。

当我编译并运行 64 位版本时,它失败了。出现此问题的原因是 LPARAM 值似乎是在 Wnd 参数中传递的。 Param 值始终设置为 $FFFF ...换句话说,我根本没有传递 HWND 值...所以它并不是通过参数进行交换。

type
PEnumInfo = ^TEnumInfo;
TEnumInfo = record
ProcessID : DWORD;
HWND : THandle;
end;

function EnumWindowsProc(Wnd: HWND; Param : LPARAM): Bool; stdcall;
var
PID : DWORD;
PEI : PEnumInfo;
begin
// in 32-bit Param matches the address of the param that is passed
// in 64-bit Param is set to $FFFF - however Wnd = the expected address
ShowMessage('PEI = '+IntToStr(Param));

PEI := PEnumInfo(Param);
GetWindowThreadProcessID(Wnd, @PID);

// the code fails at this next line in 64-bit build because PEI = $FFFF rather than the actual pointer passed
Result := (PID <> PEI^.ProcessID) or
(not IsWindowVisible(WND)) or
(not IsWindowEnabled(WND));

if not Result then PEI^.HWND := WND; //break on return FALSE
end;


function FindMainWindow(PID: DWORD): DWORD;
var
EI : TEnumInfo;
begin
EI.ProcessID := PID;
EI.HWND := 0;
ShowMessage('PEI = '+IntToStr(LPARAM(@EI)));
EnumWindows(@EnumWindowsProc, LPARAM(@EI));
Result := EI.HWND;
end;

Win64 调用约定是否不同?或者我犯了其他一些根本性错误?

任何帮助或想法都感激地接受。

最佳答案

您问题中的代码工作正常。您的 EnumWindowsProc 声明是正确的。参数和返回值的类型正确。调用约定是正确的,尽管这对于只有一种调用约定的 x64 Windows 来说实际上并不重要。

如果您使用问题中的代码构建一个简单的应用程序,您会发现它的行为正确并正确枚举窗口。

问题肯定是您的实际代码与您显示的代码不同。我的猜测是,在您的实际代码中,EnumWindowsProc 是一个嵌套函数:Why cannot take address to a nested local function in 64 bit Delphi?但这只是一个猜测。我不知道你真正的代码是什么样的。我确实知道问题中的代码可以正常工作。

另一条评论是您错误地将 HWND 成员声明为 THandle 类型。这不会影响程序的正确性,但它在语义上是错误的。我会这样声明该类型:

type
TEnumInfo = record
PID: DWORD;
Wnd: HWND;
end;

关于delphi - EnumWindows 在 64 位 Delphi 中行为异常,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30574405/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com