gpt4 book ai didi

c# - C++/C# Interop - 用于处理谓词的互操作定义

转载 作者:行者123 更新时间:2023-11-30 04:07:30 25 4
gpt4 key购买 nike

所以我正在尝试围绕 C++ API 编写一个包装器,以便我可以将它与 C# 一起使用。 C++ API 及其相关信息位于 here .

因此,我正在尝试通过 C# 代码与 C++ dll 进行交互。我能够在一定程度上成功地做到这一点。但是现在我挂断了试图让某个功能正常工作。在 C++ 中对函数的有效调用示例是:

interception_set_filter(context, interception_is_keyboard, INTERCEPTION_FILTER_KEY_DOWN | INTERCEPTION_FILTER_KEY_UP);

其中 INTERCEPTION_FILTER_KEY_DOWN 和 INTERCEPTION_FILTER_KEY_DOWN 定义为:

typedef int (*InterceptionPredicate)(InterceptionDevice device);

enum InterceptionKeyState
{
INTERCEPTION_KEY_DOWN = 0x00,
INTERCEPTION_KEY_UP = 0x01,
...
};

enum InterceptionFilterKeyState
{
INTERCEPTION_FILTER_KEY_DOWN = INTERCEPTION_KEY_UP,
INTERCEPTION_FILTER_KEY_UP = INTERCEPTION_KEY_UP << 1,
};

和 interception_is_keyboard 是可以传递到 interception_set_filter 的各种谓词之一。谓词的功能是这样描述的:

The interception_set_filter function has three parameters, the context of communication, a function pointer and a desired filter. This second parameter, the function pointer, is a device selection predicate, a function that receives a device id (like INTERCEPTION_KEYBOARD(0), INTERCEPTION_KEYBOARD(1), etc) as parameter and returns true if the device id passed is one of a device that must be filtered through the chosen filter, or false for the devices that are not to be filtered through this filter. So the interception_set_filter works by scanning all possible devices, and using the provided predicate as the criteria to know for which devices the provided filter should be applied.

此外,在代码中定义了实现此谓词 interception_is_keyboard 签名的方法,因此:

int interception_is_keyboard(InterceptionDevice device)
{
return device >= INTERCEPTION_KEYBOARD(0) && device <= INTERCEPTION_KEYBOARD(INTERCEPTION_MAX_KEYBOARD - 1);
}

interception_set_filter在.h文件中的定义是:

void ITERCEPTION_API interception_set_filter(InterceptionContext context, InterceptionPredicate predicate, InterceptionFilter filter);

ITERCEPTION_API 在哪里:

#define ITERCEPTION_API __declspec(dllimport)

所以,我的问题是,如何设置才能调用 interception_set_filter 并使用来自 C# 应用程序(托管代码)的谓词 interception_is_keyboard?


最佳答案

您可以使用 C# 委托(delegate)为 PInvoke 参数创建函数指针。问了一个类似的问题here .

EDIT 过滤器由枚举或 Int32 给出。所以这是众所周知的。

EDIT 2 Hans Passant 评论说我不需要使用 [MarshalAs(UnmanagedType.FunctionPtr)]​​,假设(默认)我学到了一些新东西,谢谢你汉斯)。他还指出了一个重要观点,“确保委托(delegate)保持引用状态,以便在 native 代码进行回调时它不会被垃圾收集”。非常感谢。

EDIT 3 我从您提供的链接中读了一些内容,显然 context 是一个 void*。我假设您还必须 PInvoke interception_create_context 来获取您的 void*,然后传递该指针。假设您有一个有效的指针,我已经相应地调整了答案。

此外,我没有看到您在哪里定义 InterceptionDevice,我现在假设为 Int32

我的 C# 委托(delegate)看起来像这样:

[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void InterceptionPredicateType(Int32 device);

[DllImport("your.dll")]
public extern static int interception_is_keyboard(IntPtr context, InterceptionPredicateType predicate, Int32 filter);

关于c# - C++/C# Interop - 用于处理谓词的互操作定义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22463061/

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