注册和调用DLL回调的正确方法是什么

问题描述 投票:0回答:2

如何正确注册DLL的所有回调并进行回调调用?我已经在这个问题上被阻止了一段时间,最后我提出了一个解决方法......目前,这是我从DLL注册回调的方法......

我不得不使用dumpbin / export MyDLL.dll来获取地址,这样的寄存器......

LPCALLBACKFUNC ObjectDllCallback = (LPCALLBACKFUNC) GetProcAddress(hDll, "_ObjectDllCallback@4");
ObjectDllCallback(MyCallbackFunc);

我的问题是,我想以“正确”的方式做到这一点,假设有一个。为什么我不得不求助于dumbin然后以_ObjectDllCallback @ 4形式放入一个奇怪的GetProcAddress,这是非常神秘的。

有没有一种正确的方法来使我的寄存器回调函数正确?

void __stdcall MyCallbackFunc(const char* str)
{
    printf("%s\n", str);
}
c++ callback
2个回答
0
投票

您所看到的是“C ++名称修改”,其中C ++编译器为链接生成唯一的名称。为避免名称损坏,您可以在extern C子句中声明您的函数,例如沿着这些行:

#define APICALL  __declspec(dllexport) 

extern "C" 
{
   APICALL void _stdcall ObjectDllCallback(LPCALLBACKFUNC callbackFunction);
};

然后你可以使用

LPCALLBACKFUNC fnObjectDllCallback = (LPCALLBACKFUNC) GetProcAddress(hDll, "ObjectDllCallback");

0
投票

这是头文件

#ifdef OBJECTDLL_EXPORTS
#define OBJECTDLL_API __declspec(dllexport)
#else
#define OBJECTDLL_API __declspec(dllimport)
#endif

#define MAX_BUFF_STR_SIZE 256

namespace XInterface
{
    // exported global var
    extern OBJECTDLL_API int nObjectDll;

    // Object Base class
    class CObjectDllBase {
    public:

        // TODO: add your pure virtual methods here.
        virtual int InvokeMethod() const = 0;
        virtual int InvokeMethod(const char*, char*, int) const = 0;

        // object callback interface
        typedef void (__stdcall* CallbackMethod)(const char*, void*);
        virtual void InvokeCallback(CallbackMethod, void*) = 0;
    };

    // This class is exported from the ObjectDll.dll
    class OBJECTDLL_API CObjectDll : public CObjectDllBase {
    public:

        CObjectDll();

        // TODO: add your methods here.
        int InvokeMethod() const;
        int InvokeMethod(const char* str, char* res, int size) const;

        // demonstrate object callback
        void InvokeCallback(CallbackMethod funcname, void* context);

    private:

        CallbackMethod m_callback;
    };

    // exported functions to be accessed externally
    extern "C"
    {
        // ordinary functions
        OBJECTDLL_API int   ObjectDllMethod();
        OBJECTDLL_API int   ObjectDllFunction(const char* str, char* res, int size);

        // demonstrate callback
        typedef void  (__stdcall* CallbackFunc)(const char*);
        OBJECTDLL_API void  __stdcall ObjectDllCallback(CallbackFunc funcname);

        // virtual class object./
        OBJECTDLL_API void* ObjectDllCreate();
        OBJECTDLL_API void  ObjectDllFree(void* pObj);
        OBJECTDLL_API void  ObjectDllInvokeMethod(void* pObj);

        // wrapper for class callback
        typedef void (__stdcall* CallbackMethod)(const char*, void*);
        OBJECTDLL_API void  __stdcall ObjectDllInvokeCallback(void* pObj, CallbackMethod funcname, void* context);
    };

    // exported typedefs to be accessed externally [one defined for each exported declaration]
    typedef int   (*LPFUNC)(const char*, char*, int);
    typedef void  (*LPCALLBACKFUNC)(CallbackFunc);
    typedef void  (*LPCALLBACKMETHOD)(CallbackMethod);

    typedef void* (*LPOBJECTCREATE)(void);
    typedef void  (*LPOBJECTFREE)(void*);
};

这是CPP文件

// ObjectDll.cpp : Defines the exported functions for the DLL application.
//

#include "stdafx.h"
#include "stdio.h"
#include "ObjectDll.h"

namespace XInterface
{
    // This is an example of an exported variable
    OBJECTDLL_API int nObjectDll=0;

    // This is an example of an exported function.
    OBJECTDLL_API int ObjectDllMethod()
    {
        printf("%s\n", __FUNCTION__);
        return 0;
    }

    OBJECTDLL_API int ObjectDllFunction(const char* str, char* res, int size)
    {
        memset(res, 0, size);
        _snprintf(res, size, "%s%s", str, __FUNCTION__);
        return 0;
    }

    OBJECTDLL_API void __stdcall ObjectDllCallback( CallbackFunc funcname )
    {
        CallbackFunc callbackfunc = funcname;

        if (callbackfunc)
        {
            // ... some work here... then lets call our function
            callbackfunc(__FUNCTION__);
        }
    }

    OBJECTDLL_API void* ObjectDllCreate()
    {
        return new CObjectDll();
    }

    OBJECTDLL_API void ObjectDllFree( void* pObj )
    {
        CObjectDll* pObjDll = static_cast<CObjectDll*>(pObj);
        if (pObjDll)
        {
            delete pObjDll;
            pObjDll = NULL;
        }
    }

    OBJECTDLL_API void ObjectDllInvokeMethod( void* pObj )
    {
        CObjectDll* pObjDll = static_cast<CObjectDll*>(pObj);
        if (pObjDll)
        {
            pObjDll->InvokeMethod();
        }
    }

    /*
    OBJECTDLL_API void __stdcall ObjectDllInvokeCallback( void* pObj, CallbackMethod funcname, void* context )
    {
        CObjectDll* pObjDll = static_cast<CObjectDll*>(pObj);
        if (pObjDll)
        {
            pObjDll->InvokeCallback(funcname, context);
        }
    }
    */

    // This is the constructor of a class that has been exported.
    // see ObjectDll.h for the class definition
    CObjectDll::CObjectDll()
    {}

    int CObjectDll::InvokeMethod() const
    {
        printf("%s\n", __FUNCTION__);
        return 0;
    }

    int CObjectDll::InvokeMethod(const char* str, char* res, int size) const
    {
        memset(res, 0, size);
        _snprintf(res, size, "%s%s", str, __FUNCTION__);
        return 0;
    }

    void CObjectDll::InvokeCallback( CallbackMethod funcname = NULL, void* context = NULL)
    {
        m_callback = funcname;

        if (m_callback)
        {
            // ... some work here... then lets call our function
            m_callback(__FUNCTION__, context);
        }
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.