使用cmake构建Windows DLL的简单示例

时间:2014-07-21 18:32:38

标签: python c++ visual-studio-2010 dll cmake

几年前,我背负着建立和修改位于NorthEast(也许是“Down East”)的合作工程机构的庞大包裹的困扰。这个软件包是用一个名为“cmake”的东西构建的,以Linux为目标... cmake,恕我直言,这是一个令人惊讶的令人抓狂,文档记录错误,构造奇怪的构建系统,因为我有限的能力,我曾经有过不愉快的工作(28年) * NIX系统的专业经验和构建开源代码。)

然后我不得不用“cmake”建立另一个针对MSVS的项目。哦,快乐!最后SOMETHING可以可靠地生成那些讨厌的“项目”和“解决方案”文件。那些相同的CMakeLists.txt文件可以重新定位Linux!哇,我见过光。

尽管如此,我仍然很黑。除非我开始使用CMakeLists.txt文件,否则我似乎无法从头开始学习并在该过程中花费不到一天的时间来解决最简单的问题。

我有一个使用MSVS构建DLL的任务,可以使用ctypes从Python脚本访问它。基本上,这意味着一个在板上有符号的DLL。由于我有一个10年前的错误,我的VS 2008和VS 2010的安装无法创建一个新的C ++项目,我想我会选择用cmake生成DLL解决方案。

我一直无法找到一个现代的(又名post cmake 2.8.5)使用cmake构建DLL的完整示例,这个任务应该比过去好得多。

潜入教程http://www.cmake.org/cmake/help/cmake_tutorial.html这很糟糕,因为他们希望你在学习cmake的同时编写C ++代码。 (嘿,伙计!我有足够的麻烦让cmake工作,让make代码将编译!)本教程虽然构建一个简单的二进制文件,然后使用库创建二进制文件,但它不会生成DLL。

在行之间阅读http://www.cmake.org/Wiki/BuildingWinDLL,我天真地将一些代码添加到lib目录中的CMakeLists.txt文件中:

在:

add_library(MathFunctions mysqrt.cxx)

install (TARGETS MathFunctions DESTINATION bin)
install (FILES MathFunctions.h DESTINATION include)

后:

add_library(MathFunctions SHARED mysqrt.cxx)
GENERATE_EXPORT_HEADER( MathFunctions
             BASE_NAME MathFunctions
             EXPORT_MACRO_NAME MathFunctions_EXPORT
             EXPORT_FILE_NAME MathFunctions_Export.h
             STATIC_DEFINE MathFunctions_BUILT_AS_STATIC
)
install (TARGETS MathFunctions DESTINATION bin)
install (FILES MathFunctions.h DESTINATION include)

cmake 3.0.0和cmake 2.8.12.2这两个文件的winge:

CMake Error at MathFunctions/CMakeLists.txt:2 (GENERATE_EXPORT_HEADER):
  Unknown CMake command "GENERATE_EXPORT_HEADER".

该函数似乎在cmake安装中作为GenerateExportHeader.cmake,并且没有任何调试显示此错误的“原因”。我无法在互联网上找到此错误。

那是我一天中的前六个小时。

我最终决定删除有问题的命令并试试这个:

add_library(MathFunctions mysqrt.cxx)

install (TARGETS MathFunctions DESTINATION bin)
install (FILES MathFunctions.h DESTINATION include)

娲-LA! cmake已配置并生成,MSVS已成功构建,并且DLL出现在库目录的Debug子目录中。 Kuel。

但是,此DLL不包含允许python / ctypes访问所需函数的符号。在BuildingWinDLL页面中进行了一些工作之后,我设法引出符号。 Python非常高兴,我现在有一个未来工作的模型,即使它是一个粗鲁,头脑简单的黑客!

所以,经过冗长的讨论之后:

  • 是BuildingWinDLL,简单地引用了cmake 2.8.5及更高版本 错?
  • 这样做的正确方法是什么?
  • 有没有人有一个简单的“cmake 101”示例创建一个带有导出符号的MSVS DLL,这些符号不是黑客,所以我可以扔掉我的黑客?

PS:非常,友好,友好的文章组合系统在stackoverflow。我会喜欢这个,假设我被允许回来......

在steveire回答后更新:

原来的问题回答了,我看到我错过了BuildingWinDLL页面中的提示。我还发现我没有为自己的代码更改示例中的一个字段。

所以现在我们进入下一层。使用引用的示例,VS2010解决方案构建抱怨:

LINK : fatal error LNK1104: cannot open file 'MathFunctions\Debug\MathFunctions.lib'

我从BuildingWinDLL收集到,GENERATE_EXPORT_HEADER()在构建DLL时全部都在跳舞。未生成.lib文件,生成的.dll不包含符号...

BuildingWinDLL页面讨论了pre-cmake-2.8.5进程。页面顶部提到的2.8.5过程是如何使用GENERATE_EXPORT_HEADER()自动生成页面底部的文件。 仍然需要将这些碎片编织在一起,这在文中并不清楚。

因此,MathFunctions_Export.h由GENERATE_EXPORT_HEADER()cmake命令生成,并在此处显示特定参数,并创建带有宏的C头,以便导出符号。显然必须明确引用此文件,并且要正确导出符号:

#include <math.h>
#include <Mathfunctions/MathFunctions_Export.h>

MathFunctions_EXPORT double mysqrt(double v) {
    return sqrt(v);
}

现在添加#include和* EXPORT限定符会导致符号被导出,VS现在知道生成.lib并用符号填充.dll。

SUCCESS!感谢所有帮助过这个过程并在我痛苦中受苦的人。

1 个答案:

答案 0 :(得分:6)

include(GenerateExportHeader)

使用前。

http://www.cmake.org/cmake/help/v3.0/module/GenerateExportHeader.html

CMake默认构建STATIC库,因此如果要构建共享库,请保留SHARED。