views:

214

answers:

2

I've recently seen a couple of open source projects that actually do this; return an unsafe pointer from a function such as: "int* input = this.someIterator.GetUnsafePtr()".

From my understanding this has to be completely wrong. Unsafe pointers can only be obtained through 'fixed' statements and certainly those returned from within a function won't be pinned anymore (they will 'lose' their declaring scope), causing them to eventually be garbage collected.

But then I don't remember the compiler giving any warning about this either, so why bother to use a fixed statement if you can actually have 'unpinned' pointers spread all over?

+2  A: 

How about, Marshal.AllocHGlobal or Marshal.AllocCoTaskMem, both returning IntPtr, which can be freely cast to void * using the .ToPointer() function ?

Or the pointer can originate from unmanaged code. You need to fix/pin memory because the memory is managed, hence as long as it is not fixed/pinned the garbage collector is free to move it, rendering the pointer invalid.

arul
+1  A: 

I've never seen such constructions in open source projects. It will be better if you provide some samples of such usage in your question. Meaning of it may depends on behavior.
But I'm agree, unsafe pointers are evil and should be used only when you interacting with some native libraries or code.
As far as I remember you can use this construction only in unsafe block. So I think that compiler will not give any warning here. And IMO it's better to use IntPtr (unsafe blocks can be executed only in full-trust).
EDIT:
@Stephen is right, IntPtr will not keep reference to the object on GC collection.

zihotki
IntPtr is not a tracking pointer. If an IntPtr refers to a managed object and that object is moved the pointer is not updated. There is no real difference between an IntPtr and an unsafe pointer other than that an IntPtr is CLS compliant and not 'unsafe'.
Stephen Martin
You are right, thanks. I think that I need to read about CLR once more again.
zihotki