天天看点

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

目录

  • 1 如何查看dll是32位还是64位
  • 2 如何查看dll的依赖库
  • 3 如何导出自己的dll

1 如何查看dll是32位还是64位

注意:

dumpbin

这个命令要在VS环境下的cmd/powershell才能使用,不然会找不到命令。

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll
# 可以查看位数
dumpbin.exe /headers .\human_pose_Demo.dll
           
vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

2 如何查看dll的依赖库

# 查看依赖的库
dumpbin.exe /dependents .\human_pose_Demo.dll
           

注意:记得把依赖的动态库拷贝给别人哈。

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

3 如何导出自己的dll

可以用

__declspec(dllexport)

来导数函数,而导入函数可以使用

__declspec(dllimport)

下面给出一个案例,其主要的思路是

  1. 静态库就不需要

    __declspec(dllexport)

    __declspec(dllimport)

  2. 如果定义了

    XXX_API_EXPORTS

    ,那么执行导出DLL操作

    __declspec(dllexport)

    ,不然即为导入

    __declspec(dllimport)

  3. 如果想C/C++混编,就定义

    __cplusplus

    ,进而需要定义

    extern "C"

  4. 如果在Linux下需要

    __attribute__((visibility ("default")))

    ,可以用

    _MSC_VER

    宏来区分
  5. 其中

    XXX_API

    放在声明和定义之前,编译就会导出这个函数

上面的思路不一定是最好的,但是是推荐的。

简单的解释:

6.

extern "C"

的目的是实现类C和C++的混合编程。在C++源文件中的语句前面加上extern “C”,表明它按照类C的编译和连接规约来编译和连接,而不是C++的编译的连接规约。这样在类C的代码中就可以调用C++的函数或者变量等。

7.

_MSC_VER

:微软公司推出的C/C++编译器在ANSI/ISO C99标准之外扩展的宏定义,用来定义当前微软公司自己的编译器的主版本。

8.

__cplusplus

是c++预定义宏,常见的两个值:c++ 98中,是199711L(很多版本都是这个值),c++ 11中,是201103L

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

9.

__attribute__((visibility ("default"))

:如果编译的时候用了这个属性,那么动态库的符号都是hidden的,除非强制声明。

下面的预处理命令。放在希望导出的.hpp中

#ifdef _MSC_VER		//vs编译器
	#ifdef __cplusplus		//c/c++混编
		#ifdef XXX_STATIC_LIB	//静态库?
			#define XXX_API  extern "C"
		#else
			#ifdef XXX_API_EXPORTS	// 由XXX_API_EXPORTS控制导入还是导出
				#define XXX_API extern "C" __declspec(dllexport)
			#else
				#define XXX_API extern "C" __declspec(dllimport)
			#endif
		#endif
	#else
		#ifdef XXX_STATIC_LIB
			#define XXX_API
		#else
			#ifdef XXX_API_EXPORTS
				#define XXX_API __declspec(dllexport)
			#else
				#define XXX_API __declspec(dllimport)
			#endif
		#endif
	#endif
#else //Linux
	#ifdef __cplusplus
		#ifdef XXX_API_EXPORTS
			#define XXX_API  extern "C" __attribute__((visibility ("default")))
		#else
			#define XXX_API extern "C"
		#endif
	#else
		#ifdef XXX_API_EXPORTS
			#define XXX_API __attribute__((visibility ("default")))
		#else
			#define XXX_API
		#endif
	#endif
#endif
           

这样子直接在.cpp中,加入如下,编译器就知道你要XXX_API_EXPORTS

导出

dll了,那么,如果不在.cpp文件写下面的代码,就是

导入

了,

结合.lib,.dll,.h就很方便了

。对于这种代码,编译器只会显示可执行的,不执行的是灰色。

#ifndef XXX_STATIC_LIB
#define XXX_API_EXPORTS
#endif // !LJCV_STATIC_LIB
           

并不是所有函数都会导出,需要预先定义的前缀XXX_API

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

最后,项目->属性->配置类型->选择DLL

vs2017/2019如何导出dll动态库及附属依赖库(dumpbin无法执行?)1 如何查看dll是32位还是64位2 如何查看dll的依赖库3 如何导出自己的dll

只需要编译,不需要运行,运行会出错,本来就无法运行。