[Mono-list] How to marshal a native function pointer to a native function with p/invoke?
Ben Henderson
bhenderson at ipswitch.com
Mon Mar 23 10:05:50 EDT 2009
I have entered the following defect for this issue:
Bug 487758 - Marshaling a native function pointer to native function call
throws assertion
But, I have also found a work around for the problem. I'll post it here in
case anyone else runs into this problem.
The work around is: Create a managed delegate that calls the un-managed
function. The following code is what I posted in the defect in BugZilla.
The Workaround class shows how to make it work with the managed delegate,
and the Bug class demonstrates the defect.
using System;
using System.Runtime.InteropServices;
namespace FunctionPointerInterop
{
class Workaround
{
[DllImport("testdll.dll")]
public extern static void foo();
[DllImport("testdll.dll")]
public extern static void bar(foo_delegate foo);
// Delegate definition
public delegate void foo_delegate();
static foo_delegate my_foo_delegate;
// Managed delegate that calls the native function "foo"
static void ManagedFooDelegate()
{
// Make the native call
foo();
}
public static void Start()
{
// Create delegate for managed callback
my_foo_delegate = new foo_delegate(ManagedFooDelegate);
// Call native function with managed delegate
bar(my_foo_delegate);
}
}
class Bug
{
[DllImport("testdll.dll")]
public extern static void foo();
[DllImport("testdll.dll")]
public extern static void bar(foo_delegate foo);
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void foo_delegate();
static foo_delegate my_foo_delegate;
public static void Start()
{
// Create delegate with native pointer
my_foo_delegate = new foo_delegate(foo);
bar(my_foo_delegate);
}
}
class Program
{
static void Main(string[] args)
{
Workaround.Start();
Bug.Start();
}
}
}
Ben Henderson wrote:
>
> Hello all,
>
> I am having an interesting problem with Mono 2.2 with trying to pass a
> native function pointer to a function in the same native library. The
> sample code below works with the .NET CLR, but dies in the mono runtime
> with the following assertion/error (I have also tried changing the
> prototype for the P/Invoke method to use the delegate, but get the same
> assertion when calling the method):
>
> **
> ERROR:marshal.c:9235:mono_marshal_get_managed_wrapper: assertion failed:
> (!mono_
> method_signature (method)->pinvoke)
>
> This application has requested the Runtime to terminate it in an unusual
> way.
> Please contact the application's support team for more information.
> **
>
> So.. my question is... Am I doing something wrong? Is this not supported
> in mono? Is there a workaround for mono (other than LoadLibrary/dlopen)
> -- I would like to utilized managed code to do this and not have to add
> #if's for different platforms!
>
> Thanks in advance!
>
> Ben
>
> ******* Code *******
>
> TESTDLL.DLL code:
> **************
> #include "stdafx.h"
> #include <stdio.h>
>
> extern "C" void TESTDLL_EXPORT foo()
> {
> printf("foo!\n");
> }
>
> extern "C" void TESTDLL_EXPORT bar(void (*fn)(void))
> {
> if (fn)
> {
> fn();
> }
> }
>
> Test Program code:
> ***************
> using System;
> using System.Runtime.InteropServices;
>
> namespace FunctionPointerInterop
> {
> class Program
> {
> [DllImport("testdll.dll")]
> public extern static void foo();
>
> [DllImport("testdll.dll")]
> public extern static void bar(IntPtr foo);
>
> [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
> public delegate void foo_delegate();
>
> static foo_delegate my_foo_delegate;
>
> static void Main(string[] args)
> {
> my_foo_delegate = new foo_delegate(foo);
> IntPtr ptr =
> Marshal.GetFunctionPointerForDelegate(my_foo_delegate);
> bar(ptr);
> }
> }
> }
>
>
--
View this message in context: http://www.nabble.com/How-to-marshal-a-native-function-pointer-to-a-native-function-with-p-invoke--tp22608410p22660798.html
Sent from the Mono - General mailing list archive at Nabble.com.
More information about the Mono-list
mailing list