Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What's the difference between HandleRef and GCHandle?

What's the difference between HandleRef and GCHandle?

http://msdn.microsoft.com/en-us/library/system.runtime.interopservices.handleref.aspx

http://msdn.microsoft.com/en-us/library/system.runtime.interopservices.gchandle.aspx

Thanks

like image 250
Vitaliy Zaverchuk Avatar asked Dec 19 '11 14:12

Vitaliy Zaverchuk


1 Answers

The point of both these structures is to prevent the garbage collector from releasing a resource and invalidating the handle before the P/Invoke call has finished. The documentation you linked indicates that these are special types recognized by the interop marshaller.

What I gather from the documentation is that HandleRef is essentially a special case of the more general GCHandle structure.

The HandleRef structure is specifically intended for wrapping handles to unmanaged resources that are used with P/Invoke code. For example, window handles (HWND) or device contexts (HDC). It has a Handle property that returns a value of type IntPtr, which is an integer value the size of a pointer on the underlying system's architecture. You can use this to quickly & easily obtain the handle it wraps.

Whereas the GCHandle structure allows one to specify the type of handle it wraps using one of the members of the GCHandleType enumeration, the HandleRef structure was specifically designed to wrap handles to unmanaged resources. You'd probably use the GCHandle structure when you're dealing directly with unmanaged memory, rather than the special handles that the Win32 API treats as black boxes.

It is not necessary to use either. One can simply call GC.KeepAlive to keep the garbage collector from prematurely releasing the resource.

And even that is probably not necessary. I've been writing P/Invoke code for years, and I've found that when it's correctly written, there's no need for either of these structures. If a class object gets garbage collected while the API call is in the middle of executing, then that's a bug in your application. I actually want to be notified of the failure via an exception, not hide it.

like image 113
Cody Gray Avatar answered Oct 15 '22 09:10

Cody Gray