PingPhotonics
asked on
C#.NET. How Do I get values of an array of longs in a C++ DLL?
Hello
Im developing a C#.NET application using Visual Studio 2008.
Im having trouble accessing data in a C++ DLL within my solution.
The C++ DLL is called myDLL.dll. Ive defined this in my C#.NET code thus;
[DllImport(@"myDLL.dll")]
static extern int GetArray(UInt32[] pBuffer, int Size);
In the C++ source the code is like;
int GetArray(unsigned long* pBuffer, long BufferSz)
{
int result = 0;
//
// getValues in a manufacturer DLL. It returns a pointer to "unsigned long*"
pBuffer = GetValues();
return(result);
}
In my C++ DLL the GetArray function is exported thus;
__declspec(dllexport) int GetArray(unsigned long* pBuffer, long BufferSz);
I now try and access the values from my C#.NET code. ie.
int size = 1000;
UInt32[] pBuf = new UInt32[size];
int = GetArray(pBuf, size);
However I get an exception when I call GetArray. It is
"Attempted to read or write protected memory. This is often an indication that other memory is corrupt"
Can anyone spot why this may not be working? Note we can't put a breakpoint in this particular DLL for some reason. We've spent ages trying to fix this but it seems its a known bug in Visual Studio.
Im developing a C#.NET application using Visual Studio 2008.
Im having trouble accessing data in a C++ DLL within my solution.
The C++ DLL is called myDLL.dll. Ive defined this in my C#.NET code thus;
[DllImport(@"myDLL.dll")]
static extern int GetArray(UInt32[] pBuffer, int Size);
In the C++ source the code is like;
int GetArray(unsigned long* pBuffer, long BufferSz)
{
int result = 0;
//
// getValues in a manufacturer DLL. It returns a pointer to "unsigned long*"
pBuffer = GetValues();
return(result);
}
In my C++ DLL the GetArray function is exported thus;
__declspec(dllexport) int GetArray(unsigned long* pBuffer, long BufferSz);
I now try and access the values from my C#.NET code. ie.
int size = 1000;
UInt32[] pBuf = new UInt32[size];
int = GetArray(pBuf, size);
However I get an exception when I call GetArray. It is
"Attempted to read or write protected memory. This is often an indication that other memory is corrupt"
Can anyone spot why this may not be working? Note we can't put a breakpoint in this particular DLL for some reason. We've spent ages trying to fix this but it seems its a known bug in Visual Studio.
may be use out instead of ref since c++ alloc memory
ASKER
Hi thanks for the suggestion.
I tried it and when executing the GetArray function the debugger shows pBuf as containing uint[0].
ie. an array with one element set to zero.
Thats not what Im expecting. Im hoping to see an array of 1000 elements.
I tried it and when executing the GetArray function the debugger shows pBuf as containing uint[0].
ie. an array with one element set to zero.
Thats not what Im expecting. Im hoping to see an array of 1000 elements.
SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
@EDDYKT
may be use out instead of ref since c++ alloc memoryThat shouldn't matter. The difference between "out" and "ref" is that when "ref" is used, the variable would be required to be initialized prior to passing into the function, which according to the above, it is. I concede that you could remove the initialization and then use "out" instead to save a small bit of processing (i.e. the managed initialization of the variable prior to the call).
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
kaufmed
I suspect you may be correct. Im investigating.
I suspect you may be correct. Im investigating.
SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
I thought I pointed to 'memcpy()' earler, didn't I?
Yup, but I hadn't noticed any non-C# responses as I scanned the question earlier, to be honest I just missed your comment.
At any rate, no one had yet to mention the calling convention issue, plus my comment slightly elaborated on yours (or at least attempts to do so) - so not quite a duplicate.
At any rate, no one had yet to mention the calling convention issue, plus my comment slightly elaborated on yours (or at least attempts to do so) - so not quite a duplicate.
Curses! I was going to mention calling convention, but I thought that's what "__declspec" was doing... too much managed code for me, I guess ; )
ASKER
Hi
Thanks for the responses.
I tried changing the C# DLLImport definition to
[DllImport("MyDll.dll", CallingConvention = CallingConvention.Cdecl)] private static extern int GetArray(uint[] pBuff, int cBuff)
This didn't affect the result. Im now trying to get information from the vendors to tell me what the GetValues() function is doing. I'll report back when I hear from them.
Thanks for the responses.
I tried changing the C# DLLImport definition to
[DllImport("MyDll.dll", CallingConvention = CallingConvention.Cdecl)] private static extern int GetArray(uint[] pBuff, int cBuff)
This didn't affect the result. Im now trying to get information from the vendors to tell me what the GetValues() function is doing. I'll report back when I hear from them.
ASKER
Hi
Okay I managed to fix this. Due to poor documentation I had failed to set a parameter which caused the camera capture to fail and therefore the pointer didn't point to anything.
Im not sure how to award points in this case so Im just going to award points to several of the answers which were generally useful and were relevant to the code I posted.
Okay I managed to fix this. Due to poor documentation I had failed to set a parameter which caused the camera capture to fail and therefore the pointer didn't point to anything.
Im not sure how to award points in this case so Im just going to award points to several of the answers which were generally useful and were relevant to the code I posted.
Open in new window
Open in new window