这将是一篇很长的文章,但我不确定要正确解释这个问题需要哪些信息。我有一个试图从 Excel 调用的 C++ DLL。每当我调用它时,其中一个功能会导致 Excel 崩溃并显示“Microsoft Excel 已停止工作”。
头文件:
#include <string>
namespace XYZ_ProjectWise
{
class FileOperator
{
public:
static __declspec(dllexport) long __stdcall initialize(std::string dbName);
static __declspec(dllexport) long __stdcall openDoc(long projectID,long docID);
};
}
功能代码initialize()
:
long FileOperator::initialize(string dbName)
{
LPCWSTR user=L"";
LPCWSTR pwd=L"";
LPCWSTR schema=L"";
std::wstring sTemp=std::wstring(dbName.begin(),dbName.end());
LPCWSTR dbName_L=sTemp.c_str();
bool resultInit=aaApi_Initialize(AAMODULE_ALL);
bool resultLogin=aaApi_Login(AAAPIDB_UNKNOWN,dbName_L,user,pwd,schema);
return 0;
}
转储箱 /exports 的输出:
?initialize@FileOperator@XYZ_ProjectWise@@SGJV?$basic_string@DU?$char_traits@D@std@@V?
$allocator@D@2@@std@@@Z
VBA中的声明:
Private Declare Function initialize Lib "C:\Program Files
(x86)\Bentley\ProjectWise\bin\XYZ_ProjectWiseDLL.dll" _
Alias "?initialize@FileOperator@XYZ_ProjectWise@@SGJV?$basic_string@DU?
$char_traits@D@std@@V?$allocator@D@2@@std@@@Z" _
(ByVal dbName As String) As Long
如何在 VBA 中调用它:
Public Sub testDLL()
Dim result As Long
result = initialize("ABC.DEF.GHI.com:PWOPPID_XYZ")
End Sub
奇怪的是,如果我在函数中包含initialize()
函数代码openDoc()
,使用dbName
硬编码,并按openDoc()
如下方式自行调用,则不会发生崩溃:
long __stdcall FileOperator::openDoc(long projectID,long docID)
{
LPCWSTR dbName=L"ABC.DEF.GHI.com:PWOPPID_XYZ";
LPCWSTR user=L"";
LPCWSTR pwd=L"";
LPCWSTR schema=L"";
bool resultInit=aaApi_Initialize(AAMODULE_ALL);
bool resultLogin=aaApi_Login(AAAPIDB_UNKNOWN,dbName,user,pwd,schema);
long resultOpen=aaApi_OpenDocument(projectID,docID,false);
return resultOpen;
}
}
VBA 调用:
Private Declare Function openDoc Lib "C:\Program Files
(x86)\Bentley\ProjectWise\bin\XYZ_ProjectWiseDLL.dll" _
Alias "?openDoc@FileOperator@XYZ_ProjectWise@@SGJJJ@Z" _
(ByVal projectID As Long, ByVal docID As Long) As Long
Public Sub testDLL()
Dim result As Long
result = openDoc(1799,29)
End Sub
那么为什么 VBA 调用会initialize()
崩溃,但 VBA 调用中的相同代码可以openDoc()
正常工作呢?