How to convert IntPtr back to an object

That's all, a continuation from the previous question here: C # formatting external parameters Dll functions

Here is the specific code I'm trying to convert to C #:

FILES_GetMemoryMapping((LPSTR)(LPCTSTR)MapFile, &Size, (LPSTR)MapName, &PacketSize, pMapping, &PagePerSector); // Allocate the mapping structure memory pMapping = (PMAPPING)malloc(sizeof(MAPPING)); pMapping->NbSectors = 0; pMapping->pSectors = (PMAPPINGSECTOR) malloc((Size) * sizeof(MAPPINGSECTOR)); // Get the mapping info FILES_GetMemoryMapping((LPSTR)(LPCTSTR)MapFile, &Size, (LPSTR)(LPCTSTR)MapName, &PacketSize, pMapping, &PagePerSector); 

The function "FILES_GetMemoryMapping" is called twice, I assume that the first time to get the size of the structure, and the second to fill it.

"pMapping" is a pointer to a structure in C ++. In my C # code, I have pMapping as an IntPtr type. The following line I can convert to:

 pMapping = Marshal.AllocHGlobal(Marshal.SizeOf(new UM0516.Mapping())); 

C (UM0516.Mapping) is a structure. Cool, so I just allocated some space that IntPtr points to. Now for the next line ... "pMapping-> NbSectors = 0;"

How can I assume that you entered the allocated unmanaged memory space, enter it as a structure (UM0516.Mapping) and set one of its members? Then make sure I don't screw it too much, so the second time I call "FILES_GetMemoryMapping", can it now use this structure ??

- Well, I did some advice and now I have the following:

I tried this and I get an exception "AccessViolationException was unhandled" on the first call to "FILES_GetMemoryMapping"

Here is what I have:

 string filepath = @"C:\blah.blah"; string MapFile = @"D:\blah.blah"; UM0516.Mapping myMapping = new UM0516.Mapping(); IntPtr pMapping = Marshal.AllocHGlobal(Marshal.SizeOf(myMapping)); Marshal.StructureToPtr(myMapping, pMapping, false); ushort PacketSize = 0; ushort size = 0; string MapName = String.Empty; byte PagePerSector = 0; uint b7 = UM0516.FILES_GetMemoryMapping(MapFile, out size, MapName, out PacketSize, pMapping, out PagePerSector); 

Do you think this exception comes from the pMapping parameter? Could this come from everything I went through?

+4
source share
2 answers

To get IntPtr, you need to create a structure, set any parameters you may need, allocate memory as you already have, and then call ..

 System.Runtime.InteropServices.Marshal.StructureToPtr(yourStructVariable, pMapping, false); 

This will copy the data from your filled structure into the memory you allocated.

To copy data from memory to a new structure called " mapping ", call ...

 UM0516.Mapping mapping = (UM0516.Mapping)System.Runtime.InteropServices.Marshal.PtrToStructure(pMapping, typeof(UM0516.Mapping)) 
+10
source

To convert IntPtr back to an object, I used a method that does this:

 if (ptrToUnwrap == IntPtr.Zero) return null; GCHandle handle = (GCHandle)ptrToUnwrap; object handledObj = handle.Target; if (handles.unfreed.Contains(handle)) handles.unfreed.Remove(handle); handle.Free(); return handledObj; 

(handles.unfreed is a list of loose GCHandles that are automatically freed when descriptors are located or completed)

0
source

All Articles