none
关于托管和非托管的问题,搞了我好久了,请帮帮忙 RRS feed

  • 问题

  • 在别人的.H中如下定义#define CALLBACK __stdcall
    NET_DVR_API LONG __stdcall NET_DVR_RealPlay_V30(LONG lUserID, LPNET_DVR_CLIENTINFO lpClientInfo, void(CALLBACK *fRealDataCallBack_V30) (LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser) = NULL, void* pUser = NULL, BOOL bBlocked = FALSE);


    我用下面方法调用
    #include"HCNetSDK.h"
    #pragma comment(lib,"HCNetSDK.lib")


    public delegate void  MyRealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void *pUser);

    ::jiankong::Frm_juzheng ^ MyFrm_junzheng = gcnew ::jiankong::Frm_juzheng();
    MyRealDataCallBack^ f=gcnew  MyRealDataCallBack(MyFrm_junzheng,&jiankong::Frm_juzheng::RealDataCallBack);
    m_lPlayHandle = NET_DVR_RealPlay_V30(lUserID, &struPlayInfo,f,NULL, bPreviewBlock);


    void CALLBACK RealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser)
    {

    TO DO
    }

    为什么编译时会出现
    error C2664: “NET_DVR_RealPlay_V30”: 不能将参数 3 从“jiankong::MyRealDataCallBack ^”转换为“void (__stdcall *)(LONG,DWORD,BYTE *,DWORD,void *)”
            没有用户定义的转换运算符,或者
            没有使该转换得以执行的上下文


    • 已编辑 xulezhong 2011年11月15日 13:34
    2011年11月15日 11:24

答案

  • 你好,

    我想你是在C++/CLI项目中引用了C++ native DLL。

    你可以尝试这样修改一下C++/CLI代码:

    public delegate void  MyRealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void *pUser);
    
    [DllImport(“HCNetSDK.dll”)]
    long NET_DVR_RealPlay_V30(LONG IUserID,LPNET_DVR_CLIENTINFO lpClientInfo, MyRealDataCallBack^ f,NULL,FALSE);
    
    ::jiankong::Frm_juzheng ^ MyFrm_junzheng = gcnew ::jiankong::Frm_juzheng();
    
    MyRealDataCallBack^ f=gcnew  MyRealDataCallBack(RealDataCallBack); 
    
    m_lPlayHandle = NET_DVR_RealPlay_V30(lUserID, &struPlayInfo,f,NULL, bPreviewBlock);
    
    void CALLBACK RealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser)
    {
    TO DO 
    }
    
    

    希望对你有所帮助。


    Helen Zhao [MSFT]
    MSDN Community Support | Feedback to us


    • 已编辑 Helen Zhao 2011年11月17日 8:13
    • 已建议为答案 Helen Zhao 2011年11月21日 3:03
    • 已标记为答案 Helen Zhao 2011年11月22日 3:13
    2011年11月17日 7:28

全部回复

  • 别沉啊!!!
    2011年11月15日 13:33
  • 在别人的.H中如下定义#define CALLBACK __stdcall
    NET_DVR_API LONG __stdcall NET_DVR_RealPlay_V30(LONG lUserID, LPNET_DVR_CLIENTINFO lpClientInfo, void(CALLBACK *fRealDataCallBack_V30) (LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser) = NULL, void* pUser = NULL, BOOL bBlocked = FALSE);


    我用下面方法调用
    #include"HCNetSDK.h"
    #pragma comment(lib,"HCNetSDK.lib")


    public delegate void  MyRealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void *pUser);

    ::jiankong::Frm_juzheng ^ MyFrm_junzheng = gcnew ::jiankong::Frm_juzheng();
    MyRealDataCallBack^ f=gcnew  MyRealDataCallBack(MyFrm_junzheng,&jiankong::Frm_juzheng::RealDataCallBack);
    m_lPlayHandle = NET_DVR_RealPlay_V30(lUserID, &struPlayInfo,f,NULL, bPreviewBlock);


    void CALLBACK RealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser)
    {

    TO DO
    }

    为什么编译时会出现
    error C2664: “NET_DVR_RealPlay_V30”: 不能将参数 3 从“jiankong::MyRealDataCallBack ^”转换为“void (__stdcall *)(LONG,DWORD,BYTE *,DWORD,void *)”
            没有用户定义的转换运算符,或者
            没有使该转换得以执行的上下文



    //呵呵。

    好像是PInvoke 和 C++ interop 混合在一起了。

     

    你的NET_DVR_RealPlay_V30 这么可能有 托管版的参数呢?

     

    如果用 C++ interop ,那么你定义一个 Native 的 Callback 函数,然后再这个函数里再呼叫你的 Delegate。

     

    如果使用 PInvoke,那么需要使用 DllImport.


    我也有自己的签名档哦!
    2011年11月16日 1:45
  • 你好,

    我想你是在C++/CLI项目中引用了C++ native DLL。

    你可以尝试这样修改一下C++/CLI代码:

    public delegate void  MyRealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void *pUser);
    
    [DllImport(“HCNetSDK.dll”)]
    long NET_DVR_RealPlay_V30(LONG IUserID,LPNET_DVR_CLIENTINFO lpClientInfo, MyRealDataCallBack^ f,NULL,FALSE);
    
    ::jiankong::Frm_juzheng ^ MyFrm_junzheng = gcnew ::jiankong::Frm_juzheng();
    
    MyRealDataCallBack^ f=gcnew  MyRealDataCallBack(RealDataCallBack); 
    
    m_lPlayHandle = NET_DVR_RealPlay_V30(lUserID, &struPlayInfo,f,NULL, bPreviewBlock);
    
    void CALLBACK RealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser)
    {
    TO DO 
    }
    
    

    希望对你有所帮助。


    Helen Zhao [MSFT]
    MSDN Community Support | Feedback to us


    • 已编辑 Helen Zhao 2011年11月17日 8:13
    • 已建议为答案 Helen Zhao 2011年11月21日 3:03
    • 已标记为答案 Helen Zhao 2011年11月22日 3:13
    2011年11月17日 7:28
  • 你好,

    我想你是在C++/CLI项目中引用了C++ native DLL。

    你可以尝试这样修改一下C++/CLI代码:

    public delegate void  MyRealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void *pUser);
    
    [DllImport(“HCNetSDK.dll”)]
    long NET_DVR_RealPlay_V30(LONG IUserID,LPNET_DVR_CLIENTINFO lpClientInfo, MyRealDataCallBack^ f,NULL,FALSE);
    
    ::jiankong::Frm_juzheng ^ MyFrm_junzheng = gcnew ::jiankong::Frm_juzheng();
    
    MyRealDataCallBack^ f=gcnew  MyRealDataCallBack(RealDataCallBack); 
    
    m_lPlayHandle = NET_DVR_RealPlay_V30(lUserID, &struPlayInfo,f,NULL, bPreviewBlock);
    
    void CALLBACK RealDataCallBack(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer, DWORD dwBufSize, void* pUser)
    {
    TO DO 
    }
    
    

    希望对你有所帮助。


    Helen Zhao [MSFT]
    MSDN Community Support | Feedback to us


    我在 MSDN 里面看到,在传人回调函数之前,MSDN 先钉住了这个 Delete 实例,我想知道这个操作是必须的吗?

    我也有自己的签名档哦!
    2011年11月17日 8:24