如何在有.dll文件和头文件的情况下制作.lib文件

69

我正在尝试在Visual Studio中创建一个应用程序,它能够访问一个已经存在的.dll文件。我需要这个应用程序来调用例程。我已经有一个头文件了。

我在互联网上进行了一些研究,并发现我需要创建一个.lib文件。看了这里类似的问题,我找到了一个链接:http://support.microsoft.com/kb/131313 但是我无法按照说明操作。

该链接中的信息说要制作一个DEF文件(我在其他地方读到过需要将其编译为同名DLL文件,但不确定该名称是否与.dll文件相同?)。但我不理解第一条指令“使用DUMPBIN /EXPORTS”。然后我需要“存根”函数,再做一些与.OBJ文件有关的操作(我不知道这些文件是什么)。

是否有类似于上面链接的易于遵循的逐步说明?


1
你想使用哪个编译器来使用生成的库?Visual Studio吗?哪个版本? - David Feurle
1
我打算使用Microsoft Visual Studio 2010作为DLL和Matlab之间的应用程序。该DLL名为Wintab32,它可以在使用图形板时找到。 - hde
6个回答

95

您需要 Microsoft Visual C++ 2010 Express(或者其他 MSVC 命令行工具),以及您的 DLL。

步骤:

  1. dumpbin /EXPORTS yourfile.dll > yourfile.exports
  2. yourfile.exports 中粘贴需要的函数名称到一个新的 yourfile.def 文件中。在该文件顶部添加一行单词 EXPORTS
  3. VC\bin 目录(其中包含 lib.exe 和其他编译工具)运行以下命令。

 

 vcvars32.bat

 lib /def:yourfile.def /out:yourfile.lib

或者适用于x64版本

 lib /def:yourfile.def /machine:x64 /out:yourfile64.lib

你应该会生成两个文件: yourfile.libyourfile.exp


5
使用 dumpbin.exe /EXPORTS yourfile.dll 代替 Dependency Walker 在获取导出函数名称方面同样有效,可作为第一步和第二步的工具。 - Christ A
dumpbin 对我失败了 ("LINK : fatal error LNK1328: table de chaînes manquante"),所以我使用了 depends 并手动创建了 def 文件。 - jpo38
1
@jpo38,dumpbin 运行正常,这只是您的工具安装环境问题。 - David Heffernan

23
你可以使用Digital Mars的IMPLIB工具。它可以仅使用dll创建一个lib文件,而不需要.def文件。
下载链接是http://ftp.digitalmars.com/bup.zip
命令行如下:
implib.exe /s mydll.lib mydll.dll

这不是C++代码 :) 只需打开控制台(cmd),并使用您的dll执行implib(如在kernel32示例中所示)。然后将生成的.lib文件放入IDE的lib文件夹中(或放入项目文件夹并将库路径添加到项目中)。之后,您就可以自由地使用该库了(只需记得将DLL保留在与exe相同的文件夹中)。 - Desu_Never_Lies
这篇博客似乎解释得更清楚: http://adrianhenke.wordpress.com/2008/12/05/create-lib-file-from-dll/ 或者你已经尝试过了吗?如果是,它起作用了吗? - Lothar
嗨,我在VS 2015中使用了这种方法,但出现了文件损坏的错误。我不得不使用Sany Liew的解决方案来正确地使库文件工作。 - Jonas
2
我怀疑Digital Mars的解决方案是否有效。由于VS使用PE-COFF格式,而DM使用OEM格式,因此需要额外的步骤将其转换为可在VS中使用的形式。 - khalfan
数字玛斯导入库管理器版本7.6B1n 版权所有(C)Digital Mars 2000。保留所有权利。错误:命令行中出现意外字符'F'。 - CS QGB
显示剩余2条评论

4

创建.def文件有更加简单的方法。在网上搜索gendef实用工具(如果你已安装Mingw-64,可能已经拥有了),然后只需要打开命令行并输入以下命令:

gendef myfile.dll

它将创建一个myfile.def文件。之后,只需按照John的说明使用lib.exe创建myfile.lib文件。


哇,谢谢,这让生活变得更容易了! 顺便说一下,在Cygwin中也有一个gendef包。 - user2745509
lib.exe在msvc中解决了我的问题。我只需运行lib.exe /DEF:.\src\build\windows\curl-windows\bin\libcurl-x64.def,然后就可以使用库并通过将生成的.lib文件作为输入来解决实现/依赖项/外部符号__imp__curl_easy_init:cl.exe libcurl-x64.lib ... - masterxilo

2

以下是使用Cygwin的解决方案:

  • install gendef and mingw64-x86_64-binutils Cygwin packages
  • run in Cygwin console:
    gendef.exe awesome.dll
    x86_64-w64-mingw32-dlltool.exe -d awesome.def -l awesome.lib
    
  • you get awesome.lib in the same dir.

使用这个文件,VS 2019 链接器完全链接成功。


0

第一种类型

#define YOURPROJECT_API _declspec(dllexport)

void yourf()

cpp

#include "pch.h"
#include "YOURPROJECT.H"
void yourf() {}

然后将它们包含进来

链接器->输入->定义文件,然后从父级或项目默认继承

编译


-1

我可能有答案。当我创建一个需要 .dll 文件的 .exe 控制台应用程序时,我也遇到了这个问题。当我尝试使用 IMPLIB 应用程序时,它找不到任何导出文件。你需要添加一个 #ifdef FILENAME_EXPORTS(将 FILENAME 替换为你的 .dll 文件名)并创建一个 _API。以下是 #ifdef 导出 api 命令的代码:

#ifdef FILENAME_EXPORTS
#define FILENAME_API __declspec(dllexport)
#else
#define FILENAME_API __declspec(dllimport)
#endif

现在您已经定义了导出API,需要将其应用于.dll项目中头文件中的所有函数。例如:

void FILENAME_API function();

正常声明您的导出函数,但在声明类型和函数名称之间包含API。

对于在.dll项目中的.cpp文件中定义函数,您不需要在声明中使用API。

以下是包含所有代码的文件名.h和文件名.cpp的示例。

// Code for filename.h
#pragma once

// Define your Export API
#ifdef FILENAME_EXPORTS
#define FILENAME_API __declspec(dllexport)
#else
#define FILENAME_API __declspec(dllimport)
#endif

// Declare your functions with your API

void FILENAME_API function1();
void FILENAME_API function2();
void FILENAME_API function3();

-------------------------------------------------------------------------------------------
// Code for filename.cpp
#include <iostream>
#include "pch.h"
#include "filename.h"
using namespace std;

void function1()
{
    cout << "Hello Function1!";
}

void function2()
{
    cout << "Hello Function2!";
}

void function3()
{
    cout << "Hello Function3!";
}

现在当您编译项目时,您应该会在编译文件保存的文件夹中看到.dll、.lib和.exp文件。现在您可以将.exe文件与.lib文件链接起来。不用谢!

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接