aM000

Hi,

I have an C++ ActiveX dll which I am trying to call from C# project by adding reference to it in the solution. The Visual Studio itself converts function parameters from C++ to C#. One of the functions in C++ looks like the following:

Scan(unsigned char* List);

If used like this in C++ it works fine:

for (i=0; i<10; i++)

ListIdea = (unsigned char *)malloc(100);

Scan((unsigned char*)List);

Function Output:

List[1]: COM1

List[2]: COM2

List[3]: JTAG

C# conversion by compiler itself: Scan(ref byte List);

byte[][] List =new byte[10][];

for (int i = 0; i < 10; i++)

ListIdea = new byte[100];

Scan (ref List[0][0]);

The code in C# compiles fine but throws runtime exception. Can somebody guide me in the right direction please



Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

Martin Platt

Since nobody else has answered, I'll take a shot for you.

Could this be a problem with the activeX project being removed from memory, and C# is managed, so creates problems

Have you tried wrapping the C++ ActiveX in a C# class, so that the class can manage the above problem

What's the exception that gets thrown

I hope this helps,

Martin Platt.






Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

aM000

Yes I tried to make a wrapper in C++ and call it in C#. It gives runtime error and the program terminates. In C# I get the "System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt"





Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

Mario Cossi

aM000,

the problem I see is that your List (in the C++ code) seems to be an unsigned char **, that you later cast to an unsigned char* for the call. Since the API is not complaining, I guess that is what it is expecting: an array of pointers and not an array of bytes. While it's not hard to guess for a C programmer, it is probably too hard for compilers and tools to figure out, and this is why you get the conversion to "ref byte", which obviously cannot work.

While fixing the ActiveX would be nice, I'll assume you cannot do so.

Unfortunately I don't know any easy way to marshal a nested array, but you could use something like this:

Code Snippet

[DllImport (@"c:\Test\SampleDLL.dll")]

static extern void Scan (IntPtr [] list);

...

IntPtr [] list = new IntPtr [10];

byte [][] result = new byte [10][];

for (int i = 0; i < 10; i++) {

list [i] = Marshal.AllocHGlobal (100);

result [i] = new byte [100];

}

Scan (list);

for (int i = 0; i < 10; i++) {

Marshal.Copy (list [i], result [i], 0, 100);

Marshal.FreeHGlobal (list [i]);

}

...

The result array will contain the results at the end.

Probably not the most elegant solution you can find, but it should work fine. Add your own flavor of error checking.

HTH

--mc





Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

aM000

Thanks for your code. I tried it but now I get the EntryPointNotFoundException. The dll I am calling is an OLE COM Component. I am not sure, but I think you cannot use DLLImport on such dlls. That can be one of the reasons for this exception.





Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

Martin Platt

Ah!

COM component! That would have been useful before! Big Smile

You need to go to references, right click, add reference, click on the COM tab, then click on the component you want to add, and add it. Visual Studio will works it's magic, and you can access the class directly. Visual studio will provide you with a wrapper that it creates for you to call.

I hope that gets everything working!

Martin Platt.






Re: Visual C# General System.AccessViolationException when trying to call C++ dll function

vishal82

Hi,

Does any one know what's the solution for this problem