8

我需要将托管回调传递给非托管 TCP 接收器。由于它是一个需要在应用程序的生命周期中存在的线程,我需要防止它被垃圾收集。我到处读到不需要固定函数指针,GCHandle.Alloc 将完成防止垃圾收集的工作。

但这是给定的吗?我已经看到托管此代码的 AppPool 因访问冲突而崩溃。为什么我不应该怀疑由于函数指针被垃圾回收而发生此错误的事实?

这篇文章支持了这个事实。

更新:这似乎大大减少了崩溃。这种方法有问题吗?

typedef void (__cdecl *ProcMessageFunc)(void* param, void* paramBuf, ULONG bufSize);
FuncDelegate^ fp = gcnew MessageFuncDelegate(this, &Handler); 
pin_ptr<MessageFuncDelegate^> pinnedFunctionPointer = &fp; 
ret = Receiver ((ProcMessageFunc)pinnedFunctionPointer);
4

1 回答 1

9

我完全按照您的建议做 - GCHandle.Alloc 在代表上,但没有固定 - 在许多不同的平台和 .NET 版本 2.0 - 4 上广泛使用时没有任何问题。比如:

 DelegateHandle = GCHandle.Alloc(xlDelegate);
 FunctionPointer = Marshal.GetFunctionPointerForDelegate(xlDelegate);

FunctionPointer然后传递给本机代码,并保留DelegateHandle以供以后清理。

这似乎是最好的参考: http: //msdn.microsoft.com/en-us/library/367eeye0 (v=vs.80).aspx 。

您指向的帖子中没有任何内容与此参考相矛盾-您确实需要保护委托免受垃圾收集,只是不需要固定

于 2012-07-09T19:28:25.613 回答