Eusebiu

Hello.

I have a dll(a.dll), C++ unmanaged, that has a an entry point with a parameter. This parameter is a pointer to a void function :

Code Snippet

typedef void (__stdcall *ReceiveCallbackFunction)(XXX myObject);

int WINAPI open(ReceiveCallbackFunction receiveCallbackFunction)

The XXX type is written once in a.dll and once in a MANAGED code(in other dll - b.dll... The difference between the XXX in a.dll and b.dll is that XXX from b.dll has a ref keyword in it`s declaration).

In C#, I declare a delegate, make an instance of it that points to a callback method and import the function from a.dll:

Code Snippet

public delegate void ReceiveCallbackFunction(XXX myObject);

public static ReceiveCallbackFunction del = new ReceiveCallbackFunction(App.CallbackMethod);

[DllImport("a.dll")]

public extern static void open(ReceiveCallbackFunction del);

//callbakc method

public static void CallbackMethod(XXX myObject)

{

int i = 0;

}

//invoke the open method

private void button1_Click(object sender, EventArgs e)

{

App.openPort(App.del);

}

When I run the application, I get this exception :

The runtime has encountered a fatal error. The address of the error was at 0x79f00d6e, on thread 0xe50. The error code is 0xc0000005. This error may be a bug in the CLR or in the unsafe or non-verifiable portions of user code. Common sources of this bug include user marshaling errors for COM-interop or PInvoke, which may corrupt the stack.

I have removed the XXX object and replaced it with void. And the callback worked(I've put a brakepoint at the line int i = 0; I am sure that I replace XXX object with an int, it will work). So.. I'm thinking that is a problem between the conversion from an unmanaged object to a managed one. I guess it dosen`t like my XXX managed object.

I don't really want to have the XXX class in 2 places... so I want to remove the one from managed code. But I don't know how to use the XXX class from unmanaged code in C#.

How can I consume the unmanaged class in C#

Or... anyone with any ideea how to solve this problem

Thanks




Re: Common Language Runtime Callback functions from C++(unamanaged) to C#.NET

Mattias Sjogren

Eusebiu wrote:

So.. I'm thinking that is a problem between the conversion from an unmanaged object to a managed one. I guess it dosen`t like my XXX managed object.

I don't really want to have the XXX class in 2 places... so I want to remove the one from managed code. But I don't know how to use the XXX class from unmanaged code in C#.

How can I consume the unmanaged class in C#

Or... anyone with any ideea how to solve this problem

Sorry, but you have to declare the type in managed code as well. And you have to make sure the native and managed definitions match so that the argument gets marshaled correctly.






Re: Common Language Runtime Callback functions from C++(unamanaged) to C#.NET

Eusebiu

The XXX class is defined in managed code and in unmanaged code. The only diference is the ref keyword.

I thought that if I replace the XXX object with a value type, the callback will work. I was right. I've replaced it with a structure with value types as members... and it worked - ONLY ONCE(with common value types like int workes fine)... I get a MessaageBox(with Abort, Retry and Ignore buttons) that says : Debug Error! Run-time Check Failuare #0 : The value of ESP was not properly saved across function call. This is usually a result of calling a function declared with one calling convention with a pointer declared with a diffrent calling convention.

But it worked... Sad((((( once ... =)))))))






Re: Common Language Runtime Callback functions from C++(unamanaged) to C#.NET

Eusebiu

Hello... I've had an ideea.... if value types work... why not use IntPtr So.. I've send a pointer to the XXX object from unmanaged code.

How can build from the memory-data that points the pointer to, the XXX object in managed code (The XXX class from unmanaged is the SAME as the on in manged).

I've done some tests where XXX was an int[], and I used these lines :

Code Snippet

int[] a = new int[3];

Marshal.Copy(pointer, a, 0, a.Length);

and it worked fine. I got the array correctly.






Re: Common Language Runtime Callback functions from C++(unamanaged) to C#.NET

Eusebiu

It works with Marshal.PtrToStructure(...) if XXX is a struct. ( the overload that returns an object)