从VBA调用C ++ DLL,获取"访问违规写入位置"错误

时间:2014-07-02 01:10:31

标签: c++ excel vba dll visual-studio-2013

我有一个Excel VBA项目,我正在尝试从Visual Studio 2013输出的C ++ DLL中调用函数。我添加了对DLL的引用。当我尝试在VS调试器中运行它时,附加到Excel实例,我在其中调用DLL函数:

Private pw_ As Long

Private Sub class_initialize()
   pw_ = ProjectWiseAPI.CreateProjectWise(True)
End Sub

我收到此错误:

Unhandled exception at 0x0EBE8536 (libProjectWise.dll) in EXCEL.EXE: 
OxC0000005: Access violation writing location 0xFFFFFFFF.

它打破了这个功能:

PWAPI CreateProjectWise(LPVOID *obj, VARIANT_BOOL showErrors) {
    *obj = new XYZ_ProjectWise::ProjectWise(showErrors != FALSE);
    return S_OK;
}

专门针对*obj分配行。

另外,当我只使用Excel文件而不是VS时,当我编译VBA项目时,我收到此错误:

File not found: T:\location\of\dll\libProjectWise.dll

即使我已将DLL,EXP,ILK,LIB,MAP和PDB文件复制到T:\location\of\dll文件夹,我的ODL文件也包含以下行:

[
   dllname("T:\location\of\dll\libProjectWise.dll")
]

我对这一切感到非常困惑。我没有编写这个API,我只是粗略地了解了C ++以及如何在Visual Studio中开发它。原始开发者不可用。

编辑: 这是CreateProjectWise函数的ODL代码:

[
        helpstring("Gets an instance of the API object"),
        entry("_CreateProjectWise@8")
]
HRESULT __stdcall CreateProjectWise([in] VARIANT_BOOL showErrorMessage, [out, retval] long *obj);

1 个答案:

答案 0 :(得分:2)

该C ++签名不可能匹配该调用。 C ++有两个参数,调用只有一个。还有a [retval] attribute is allowed only on the last parameter,因此无法从VBA传递showErrors,而obj是存储在pw_中的返回值的缓冲区。

查看函数的ODL,很明显参数顺序与定义相反。因此,VBA中的showErrorMessage参数被视为C ++中的指针,具有可预测的错误结果。

MIDL编译器在处理ODL时创建头文件。对于带有实现的C或C ++代码中的#include这个头文件非常有用,这样编译器就可以自动捕获这样的问题。