从VB6调用DLL函数

时间:2020-03-05 18:46:25  来源:igfitidea点击:

我有一个用C / C ++编写的Windows DLL(所有导出的函数均为" C")。该DLL在VC ++中对我来说工作正常。我已经将DLL交给了另一家在VB中进行所有开发的公司。他们似乎在链接到功能时遇到问题。我已经十年没有使用VB了,甚至没有安装它。可能是什么问题呢?

我已经声明了我所有的公共职能,如下所示:

#define MYDCC_API __declspec(dllexport)

MYDCCL_API unsigned long MYDCC_GetVer( void);
.
.
.

有任何想法吗?

终于回到今天,并使其正常工作。答案使我走上了正确的道路,但我发现这最有帮助:

http://www.codeproject.com/KB/DLL/XDllPt2.aspx

另外,在将字符串传递给DLL函数时遇到了一些问题,我发现这很有帮助:

http://www.flipcode.com/archives/Interinterface_Visual_Basic_And_C.shtml

解决方案

回答

通过使用__declspec进行导出,函数名称将被导出,其中包含类型信息以帮助C ++编译器解决重载。

VB6无法处理变形的名称。解决方法是,必须取消名称的组合。最简单的解决方案是使用VC ++中的导出定义文件链接DLL文件。导出定义文件非常简单,仅包含DLL的名称和导出函数的列表:

LIBRARY mylibname
EXPORTS
    myfirstfunction
    secondfunction

另外,我们必须指定stdcall调用约定,因为这是VB6可以处理的唯一调用约定。有一个项目使用程序集注入来处理C调用,但是我想我们不想使用这种困难且容易出错的方法。

回答

尝试在末尾添加__stdcall

#define MYDCC_API __declspec(dllexport) __stdcall

我们有一些与旧的VB6应用程序交互的C ++ dll,它们都在末尾具有该功能。

回答

VB6 DLL始终是COM dll。我将用尽可能少的词来描述一个例子。假设我们在VB6中有一个ActiveX DLL项目,其类名为CTest,其中包含如下所示的方法

公共函数vbConcat(ByVal a作为字符串,ByVal b作为字符串)作为字符串
vbConcat = a和b
结束功能

并且我们已经在VB6项目属性中将项目名称设置为VBTestLib,并且
我们已将项目编译为F:\ proj \ VB6 \ ActiveXDLL \ VBTestDLL.dll

我们需要使用Windows命令注册dll
regsvr32 F:\ proj \ VB6 \ ActiveXDLL \ VBTestDLL.dll

现在C ++代码:

#import" F:\ proj \ VB6 \ ActiveXDLL \ VBTestDLL.dll"
使用命名空间VBTestLib;

无效的CDialogTestDlg :: OnButton1()
{

HRESULT hresult;
 CLSID clsid;
 _CTest *t; // a pointer to the CTest object
 _bstr_t bstrA = L"hello";
 _bstr_t bstrB = L" world"; 
 _bstr_t bstrR;
 ::CoInitialize(NULL);
  hresult=CLSIDFromProgID(OLESTR("VBTestLib.CTest"), &clsid);
  hresult= CoCreateInstance(clsid,NULL,CLSCTX_INPROC_SERVER,
                               __uuidof(_CTest),(LPVOID*) &t);
  if(hresult == S_OK)
  {
     bstrR  = t->vbConcat(bstrA , bstrB);
     AfxMessageBox((char*)bstrR);
   }

}

这就是开始的全部内容。