首页 文章

MinGW与MinGW-W64对比交叉编译中的MSVC(VC)

提问于
浏览
5

让我们这样说:我们将创建一个需要跨平台的库,我们选择GCC作为编译器,它在Linux上运行得非常好,我们需要在Windows上编译它,我们让MinGW完成工作 .

MinGW尝试在Windows上实现编译C的本机方式,但它不支持某些功能,如 mutexthreads .

我们有MinGW-W64是支持这些功能的MinGW的分支,我想知道哪一个使用?知道GCC是最常用的C编译器之一 . 或者最好在Windows上使用MSVC(VC)和在Linux上使用GCC,并使用CMake处理独立编译器?

提前致谢 .

4 回答

  • 7

    就个人而言,我更喜欢基于MinGW的解决方案,它可以在Linux上进行交叉编译,因为有很多平台独立的库几乎不可能(或者是巨大的PITA)在Windows上构建 . (例如,使用 ./configure 脚本来设置它们的构建环境的那些 . )但是,即使在Linux上交叉编译所有这些库及其依赖项也很烦人,如果你自己必须 ./configuremake . 这就是MXE的用武之地 .

    从评论中,您似乎担心依赖性 . 如果必须单独交叉编译每个库,那么在交叉编译时,它们在构建环境设置方面成本很高 . 但是有MXE . 它构建了一个交叉编译器和大量独立于平台的库(如boost,QT和许多不太值得注意的库) . 使用MXE,作为解决方案,提升变得更具吸引力 . 我已经使用MXE来构建一个依赖于Qt,boost和libexiv2的项目,几乎没有问题 .

    使用MXE增强线程

    为此,首先安装mxe:

    git clone -b master https://github.com/mxe/mxe.git
    

    然后构建你想要的包( gccboost ):

    make gcc boost
    

    带有MXE的

    C 11个线程

    如果你仍然喜欢C 11线程,那么MXE也是如此,但它需要两阶段编译gcc .

    首先,检查mxe的主(开发)分支(这是安装它的常规方法):

    git clone -b master https://github.com/mxe/mxe.git
    

    然后构建 gccwinpthreads 而不做任何修改:

    make gcc winpthreads
    

    现在,编辑mxe / src / gcc.mk . 找到以 $(PKG)_DEPS := 开头的行,并将 winpthreads 添加到该行的末尾 . 并找到 --enable-threads=win32 并将其替换为 --enable-threads=posix .

    现在,重新编译 gcc 并享受你的C 11线程 .

    make gcc
    

    Note: 您必须这样做,因为默认配置使用WINAPI而不是posix pthreads支持Win32线程 . 但是GCC的libstdc(实现 std::threadstd::mutex 的库)没有使用WINAPI线程的代码,所以它们添加了一个预处理器块,当启用Win32线程时,它会从库中剥离 std::threadstd::mutex . 通过使用 --enable-threads=posix 和winpthreads库,而不是让GCC尝试与Win32接口完全支持,我们让winpthreads充当粘合代码,为GCC提供正常的pthreads接口,并使用WINAPI函数实现pthreads库 .

    最后的说明

    您可以通过在 make 命令中添加 -jmJOBS=n 来加快这些编译速度 . -jm ,其中 m 是一个数字,表示同时构建 m 包 . JOBS=n ,其中 n 是一个数字,表示使用 n 进程构建 each 包 . 所以,实际上它们是相乘的,所以只选择 mn ,这样 m*n 最多不会超过你拥有的处理器核心数 . 例如 . 如果你有8个核心,那么 m=3n=4 就是正确的 .

    引文

    http://blog.worldofcoding.com/2014_05_01_archive.html#windows

  • 1

    如果您想要可移植性,请使用标准方法--C2的<thread>库 .

    如果你不能使用C 11,pthread可以解决,虽然VC无法编译它 .

    你想不要同时使用这两种吗?然后,只需编写抽象的线程层 . 例如,您可以像这样编写 class Thread .

    class Thread
    {
    public:
       explicit Thread(int (*pf)(void *arg));
       void run(void *arg);
       int join();
       void detach();
       ...
    

    然后,编写要支持的每个平台的实现 . 例如,

    +src
    |---thread.h
    |--+win
    |--|---thread.cpp
    |--+linux
    |--|---thread.cpp
    

    之后,配置您构建脚本以在Windows上编译 win/thread.cpp ,在Linux上编译 linux/thread.cpp .

  • 5

    你绝对应该使用Boost . 它真的很棒,做所有事情 .

    说真的,如果你不支持(例如 std::async ),请查看Boost库 . 当然它对此感到害怕,你将享受到Boost这样的所有优点作为交叉编译 .

    了解Boost.Thread和C 11线程here之间的差异 .

  • 0

    我认为当你需要选择多平台工具或工具集时,这是一个相当通用的注意事项列表,对于很多这些工具你可能已经有了答案;

    • 工具支持,如果某些东西不起作用,你将如何获得支持;社区和供应商有多强大?

    • 原生目标支持,该工具对目标平台的理解程度如何?

    • 优化潜力?

    • 图书馆支持(现在和将来)?
      如果需要,

    • Platform SDK支持?

    • 构建工具(尽管这里没有直接询问,它们是否适用于两个平台;大多数流行的工具都可以) .

    我看到的一件事似乎并未真正得到解决;

    目标应用程序的期望是什么?

    你提到你正在构建一个库,那么应用程序将使用它以及该应用程序所期望的是什么 .

    这里作为目标应用程序的约束决定了系统的最基本方面,即用于构建它的工具 . 应用程序如何使用该库;

    • 该应用程序需要什么API和什么样的API?

    • 您想提供哪种API(C风格,C类或组合)?

    • 它使用的是什么运行时,它是相同的,还是会有冲突?

    鉴于这些,以及目标应用可能仍然未知的可能事实;保持尽可能多的灵活性 . 在这种情况下,尽力保持与 gccmingw-w64msvc 的兼容性 . 它们都提供了广泛的语言支持(真实,有些比其他更多)并且通常由其他流行的库支持(即使现在不需要这些其他库) .

    我认为Hans Passant的评论......

    做什么先行

    ......真的适用于此 .

    既然你提到了它; mingw-builds for mingw-w64 支持 thread 等,在Windows上使用 posix build,64 bit32 bit .

相关问题