1

我有带有 MS Office 64 位的 64 位 Windows 10。我正在尝试让 Powerpoint 的 VBA 加载和执行自写的 64 位 Windows DLL 中的函数。为了防止导出名称损坏,我使用了 extern C:

extern "C" {
    __declspec(dllexport) long jaadd(long a, long b)
    {
        return a + b;
    }
}

这个简单的函数可以被 C++ 模块毫无问题地调用

    hinstDLL = LoadLibrary(L"D:\\Visual Studio 2017\\Projects\\PopUpDLL\\x64\\Debug\\PopUpDLL.dll");
    if (hinstDLL != NULL)
    {
        jaadd = (AddFunc)GetProcAddress(hinstDLL, "jaadd");
        if (jaadd != NULL) {
            result = jaadd(13, 40);
        }       
        fFreeDLL = FreeLibrary(hinstDLL);
    }

尝试从 Powerpoint 中的 VBA 调用 DLL 时会出现问题。GetProcAddress 总是返回零,FreeLibrary 也是如此

    Private Declare PtrSafe Function FreeLibrary Lib "kernel32" (ByVal      hLibModule As Long) As LongLong
    Private Declare PtrSafe Function LoadLibrary Lib "kernel32" Alias "LoadLibraryA" (ByVal lpLibFileName As String) As Long
    Private Declare PtrSafe Function GetProcAddress Lib "kernel32" (ByVal hModule As Long, ByVal lpProcName As String) As Long
    Private hLib As Long
    Sub LLib()
        hLib = LoadLibrary("D:\\Visual Studio 2017\\Projects\\PopUpDLL\\x64\\Debug\\PopUpDLL.dll")
        MsgBox hLib
        Dim pprocaddress As Long
        pprocaddress = GetProcAddress(hLib, "jaadd")  ***** always returns 0
        MsgBox pprocaddress
        xx = FreeLibrary(hLib)  ***** always returns 0
        MsgBox xx
    End Sub

感激地收到任何帮助。

4

1 回答 1

0

Did you every try

Private Declare PtrSafe Function jaadd Lib "......\x64\Debug\PopUpDLL.dll" 
Alias "_jaadd@8" (ByVal arg1 As Long, ByVal arg2 as Long) As Long

Note the Alias mangling "algorithm": _ + your original name + @ + sum of argument bytes.

You have two VBA Longs, or two C# ints, 4 + 4 = 8.

You can also dispense with the twin \ thing here in VBA-land.

See also https://docs.microsoft.com/en-us/office/client-developer/excel/how-to-access-dlls-in-excel

Lastly, make sure you use a 32-bit DLL for 32-bit VBA, and a 64-bit DLL for 64-bit VBA.

So many websites in their DECLARE statements have the handle for LoadLibrary and return of GetProcAddress as Long instead of LongPtr.

Problem is that the information is stale - the code was never updated to reflect the post-Excel 2009 state of VBA.

于 2020-02-07T21:08:47.227 回答