2

I'm trying to use a C written DLL (FlyCapture API, from Point Grey Research Inc) in a C# code, but I always get a runtime error. Here I have two samples of code using the DLL: one is written in C++, and in the other I tried to do exactly the same thing in C# using an unsafe context.

C++ code:

void Callback(void* Param, int Message, unsigned long lParam)
{
    cout << Message << "\t" << lParam << endl;
}

int main(int argc, char *argv[])
{
    void *context;
    FlyCaptureCallback *callback = Callback;

    flycaptureCreateContext(&context);
    flycaptureModifyCallback(context, callback, NULL, true);

    _sleep(5000);

    flycaptureModifyCallback(context, callback, NULL, false);
    flycaptureDestroyContext(context);

    return 0;
}

C# code:

[DllImport("pgrflycapture.dll")]
static extern int flycaptureCreateContext(void** pContext);

[DllImport("pgrflycapture.dll")]
static extern int flycaptureDestroyContext(void* context);

[DllImport("pgrflycapture.dll")]
static extern int flycaptureModifyCallback(void* context, IntPtr pfnCallback, void* pParam, bool bAdd);

delegate void FlyCaptureCallback(void* Param, int Message, uint lParam);

static void Callback(void* Param, int Message, uint lParam)
{
    Console.WriteLine(Message.ToString() + "\t" + lParam.ToString());
}

static void Main(string[] args)
{
    void *context;
    IntPtr callback = Marshal.GetFunctionPointerForDelegate((FlyCaptureCallback) Callback);

    flycaptureCreateContext(&context);
    flycaptureModifyCallback(context, callback, null, true);

    Thread.Sleep(5000);

    flycaptureModifyCallback(context, callback, null, false);
    flycaptureDestroyContext(context);
}

The purpose of this program is to register a callback function so that when an event occurs in a camera bus, this function is called. The program then waits for 5 seconds and removes the callback from the register. The C++ application works fine, if I remove the camera from the computer during those 5 seconds, a message appears in the console. The C# application, in other hand, only works fine when no event occurs, hence the callback function is not called. If I try to remove the camera from the computer, the Callback function is successfully called and the right numbers appear in the screen, but Windows displays a message saying that "vshost32-clr2.exe has stopped working" during the function flycaptureDestroyContext.

Any ideas? Thanks!

4

1 回答 1

1

我懂了!问题是 API 的函数(flycaptureCreateContext、flycaptureModifyCallback 和 flycaptureDestroyContext)在 C 头文件中声明为 __cdecl,但我没有在 DllImport 语句中考虑它。以下是更正后的 C# 代码:

[DllImport("pgrflycapture.dll", CallingConvention = CallingConvention.Cdecl)]
static extern int flycaptureCreateContext(void** pContext);

[DllImport("pgrflycapture.dll", CallingConvention = CallingConvention.Cdecl)]
static extern int flycaptureDestroyContext(void* context);

[DllImport("pgrflycapture.dll", CallingConvention = CallingConvention.Cdecl)]
static extern int flycaptureModifyCallback(void* context, FlyCaptureCallback pfnCallback, void* pParam, bool bAdd);

[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
delegate void FlyCaptureCallback(void* Param, int Message, uint lParam);

static void Callback(void* Param, int Message, uint lParam)
{
    Console.WriteLine(Message.ToString() + "\t" + lParam.ToString());
}

static void Main(string[] args)
{
    void *context;
    FlyCaptureCallback callback = (FlyCaptureCallback) Callback;

    flycaptureCreateContext(&context);
    flycaptureModifyCallback(context, callback, null, true);

    Thread.Sleep(5000);

    flycaptureModifyCallback(context, callback, null, false);
    flycaptureDestroyContext(context);
}

感谢 lnmx 和 Jim Mischel 的宝贵帮助!

于 2013-08-13T19:32:30.543 回答