【问题标题】:C++ cross-platform dynamic libraries for Linux and Windows适用于 Linux 和 Windows 的 C++ 跨平台动态库
【发布时间】:2010-11-17 03:15:49
【问题描述】:

我想写一些跨平台的库代码。

我正在创建一个静态和动态库,大部分开发都是在 Linux 中完成的,我已经在 Linux 中生成了静态和共享库,但现在想生成一个 Windows 版本的静态和动态库,形式为.lib.dll 使用相同的源代码。

这可能吗?我有点担心,因为我注意到生成 Windows .dll 文件需要使用 _dllspec 或您的源代码中的类似内容。

我正在寻找在 Windows 上编译我的代码的最佳和最快的解决方案。我不需要在Linux下进行编译;我很乐意直接在 Windows 下进行。此外,我正在使用两个外部库,即 Boost 和 Xerces XML,我已经在我的 Windows 和 Linux 系统上安装了它们,所以希望它们不会成为问题。

我真正想要的是拥有一个可以在 Linux 和 Windows 下编译的单一源代码副本,以生成特定于每个平台的库。我真的不在乎是否必须编辑我的代码以支持 Windows 或 Linux,只要我可以拥有一个源代码副本。

【问题讨论】:

  • 交叉编译通常是指在一个平台上构建要在另一个平台上运行的软件。既然你说你想要可以在 Linux 和 Windows 上编译的源代码,那么你的问题实际上更多是关于编写一个可移植的、跨平台的源代码库,而不是关于交叉编译。
  • GIYF 实际上,在这种情况下,libtool 是你的朋友......
  • 等待答案时,请查看 CMake:cmake.org
  • 我很高兴交叉编译或可移植的代码可以做到这一点。当然,交叉编译是理想的,因为它可以节省我的时间,但就像我说的那样,我无法选择,我会选择最好或最简单的方法。另外如何使用 code::blocks IDE 我听说他们有共享库模板并且它在 linux 和 windows 中可用,有人知道这是否符合我的要求吗?

标签: c++ cross-platform shared-libraries


【解决方案1】:

总的来说,您需要关注两个问题:

  1. 要求,在 Windows 上,您的 DLL 显式导出应该对外界可见的符号(通过 __declspec(dllexport),并且
  2. 能够维护构建系统(理想情况下,不必维护单独的 makefile 和 Microsoft Visual C++ 项目/解决方案)

首先,您需要了解__declspec(dllexport)。在仅限 Windows 的项目中,这通常以我在对this question 的回答中描述的方式实现。您可以通过确保您的导出符号(例如 MY_PROJECT_API)已定义但在为 Linux 构建时扩展为空来进一步扩展此步骤。这样,您可以根据需要将导出符号添加到您的代码中,而不影响 linux 构建。

其次,您可以研究某种跨平台构建系统。

如果您对 GNU 工具集感到满意,您可能需要研究 libtool(可能与 automake 和 autoconf 结合使用)。 这些工具在 Linux 上原生支持,在 Windows 上通过CygwinMinGW/MSYS 支持。 MinGW 还为您提供了交叉编译的选项,即在运行 Linux 的同时构建您的本机 Windows 二进制文件。我发现对导航 Autotools(包括 libtool)很有帮助的两个资源是 "Autobook"(特别是 DLLs and Libtool 部分)和 Alexandre Duret-Lutz's PowerPoint slides

正如其他人所提到的,CMake 也是一种选择,但我自己不能代表它。

【讨论】:

  • 谢谢,我确实做了一些谷歌搜索,我猜我搜索了错误的东西,libtool 听起来很有趣,也许是上面提到的 cmake。我是 linux 的新手,所以这个工具不会很快响起:p
  • Se usi Boost puoi usare boost/config.hh che definisce le macro per esportare i simboli in maniera appropriata per tutti i compilatori e piattaforme
【解决方案2】:

您可以使用#ifdef 轻松做到这一点。在 Windows 上,_WIN32 应该由编译器定义(即使是 64 位),所以代码类似于

#ifdef _WIN32
#  define EXPORTIT __declspec( dllexport )
#else
#  define EXPORTIT
#endif

EXPORTIT int somefunction();

应该适合你。

【讨论】:

  • 嗯,是的,我想过,我会看看会怎样,如果我对上述工具不满意,可能会将此作为我最后的手段
  • @iQ:即使使用上述工具,您仍然必须这样做。他们不为您处理导出,他们只是隐藏了不同平台上构建过程之间的一些差异。
  • 是的,我猜你是对的,我将不得不使用宏。我目前正在尝试查看代码块,我认为它可以自动为您定义一个 .def 文件,尽管我不知道这是好是坏。我将不得不进行一些实验。
【解决方案3】:

添加 extern "C" 可能会更好!!!,

/* 文件 CMakeLists.txt */

 SET (LIB_TYPE SHARED)
 ADD_LIBRARY(MyLibrary ${LIB_TYPE} MyLibrary.h)

/* 文件 MyLibrary.h */

#if defined(_WIN32) || defined(__WIN32__)
#  if defined(MyLibrary_EXPORTS) // add by CMake 
#    define  MYLIB_EXPORT extern "C" __declspec(dllexport)
#  else
#    define  MYLIB_EXPORT extern "C" __declspec(dllimport)
#  endif // MyLibrary_EXPORTS
#elif defined(linux) || defined(__linux)
# define MYLIB_EXPORT
#endif

MYLIB_EXPORT inline int Function(int a) {
    return a;
}

【讨论】:

  • @tstenner 你的意思是说你不只是绝对喜欢人们在输入代码时即时创建自己的格式样式? :)
猜你喜欢
  • 2017-12-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-06-23
  • 1970-01-01
相关资源
最近更新 更多