当通过 PInvoke 传递托管 byte[] 数组以供 Win32 填充时,是否需要固定它?

发布于 2024-08-21 03:22:25 字数 126 浏览 7 评论 0原文

假设您正在调用一个 Win32 函数来填充您的字节数组。您创建了一个大小为 32 的空数组。然后将其传递给要填充 int 的 Win32 函数,并稍后在托管代码中使用它。字节数组在分配和由 Win32 函数填充之间是否有可能被移动或覆盖?

Suppose you're calling a Win32 function that will fill in your byte array. You create an array of size 32, empty. Then pass it in to the Win32 function to be filled int, and use it later in your managed code. Does there exist the chance that the byte array might be moved or overwritten in between the time it was allocated and it is filled in by the Win32 function?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

め七分饶幸 2024-08-28 03:22:25

简短回答:不,在这种情况下不需要固定

较长回答:

当托管对象跨越 PInvoke 边界时,CLR 将自动固定对托管对象的引用。一旦 PInvoke 函数退出,引用就会被取消固定。因此,在使用本机函数填充 byte[] 等情况下,无需手动固定,因为该对象仅在函数调用期间由本机代码使用。

如果本机代码缓存托管指针,则需要手动固定数组。发生这种情况时,您必须手动固定数组,直到本机代码不再需要指针。在这种情况下,我认为指针没有被缓存,因此没有必要固定

参考 - http://msdn.microsoft.com/en-us/magazine/cc163910.aspx#S2

Short Answer: No, pinning is not necessary in this case

Longer Answer:

The CLR will automatically pin references to managed objects when they cross the PInvoke boundary. As soon as the PInvoke function exits the reference will be unpinned. So in situations like having a native function fill a byte[] no manually pinning is necessary because the object is only used by native code during the function call.

Manually pinning of the array becomes necessary if the native code caches the managed pointer. When this happens you must manually pin the array until the native code no longer needs the pointer. In this case I presume the pointer is not cached hence it's not necessary to pin

Reference - http://msdn.microsoft.com/en-us/magazine/cc163910.aspx#S2

傲世九天 2024-08-28 03:22:25

根据msdn 编组类型数组仅通过引用传递的数组可以由非托管代码写入。因此,如果您想在非托管端填充数组参数,则似乎必须声明数组参数 [out] 或 [in,out]。

此页面 http://msdn.microsoft.com/en -us/library/aa719896(VS.71).aspx 设法继续下去,而没有明确表示编组器在从托管到非托管的调用期间固定数组,但它所描述的大部分内容都不会如果编组器没有固定,则工作。

according to msdn Marshaling Arrays of Types only an array passed by reference can be written to by unmanaged code. So it appears that you must declare the array parameter [out] or [in,out] if you want to fill it in on the unmanaged side.

This page http://msdn.microsoft.com/en-us/library/aa719896(VS.71).aspx manages to go on and on without ever explicitly saying that the marshaller pins the arrays during the call from managed to unmanaged, but much of what it describes wouldn't work if the marshaller didn't pin.

不回头走下去 2024-08-28 03:22:25

很抱歉回答我自己的问题,但我相信如果类型是 blittable,就像 byte[] 一样,那么数组将在运行时编组时被固定,因此不需要固定。其他时间的物体会有所不同。如果我错了,请纠正我。

Sorry to answer my own question but I believe if the type is blittable, as byte[] is, then the array would be pinned while being marshalled by the runtime, so no pinning would be needed. An object on the other time would be different. Please correct me if I'm wrong.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文