如何使用MinGW gfortran通过CMake构建/编译Fortran? [英] How do I build/compile Fortran with MinGW gfortran via CMake?

查看:3148
本文介绍了如何使用MinGW gfortran通过CMake构建/编译Fortran?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我还有更多的事情需要弄清楚CMake比只是下面的问题,但它是第一个也是最简单的一个,我仍然不能过去。我已经淘汰网络,甚至借用了朋友的掌握CMake 书,但我仍然有最难的时间...许多东西存在于在线,关于CMake,Fortran和MinGW,甚至两个组合在一次。



所有我想做的(在这一点上)是一个简单的Fortran程序,使用CMake在Windows上构建和编译,使用MinGW的gfortran编译器。



...我是一个CMake n00b。



我目前已经开始合作:



CMakeLists.txt:

 项目(cmake_test Fortran)
add_executable(testf test.f90)


$ b b

test.f90:

 程序测试
write(*,* )hello world
endprogram test



我有MinWorks的MSYS2版本,因为这是唯一的版本的代码,我最终要编译将在Windows上编译。 (即当我在MSYS2 shell中用我自己的Makefile编译它时,它会编译。)



我的Windows路径附加了 ; C:\ msys64\mingw64\bin 。 (我也试过; C:\msys64\usr\bin ,但它抱怨 sh.exe 在同一个目录,其他问题。)



然后我弹出打开CMake GUI,加载在CMakeLists上面,点击配置,指定生成器该项目为MinGW Makefiles,选择使用默认本地编译器,并获得以下输出:

  Fortran编译器标识是GNU 5.4.0 
检查Fortran编译器是否正常:C:/msys64/mingw64/bin/gfortran.exe
检查Fortran编译器是否正常:C:/msys64/mingw64/bin/gfortran.exe - works
检测Fortran编译器ABI info
检测Fortran编译器ABI info - done
检查C:/msys64/mingw64/bin/gfortran.exe是否支持Fortran 90
检查C:/msys64/mingw64/bin/gfortran.exe支持Fortran 90 - 是
配置完成

然后我再次单击配置并获取:

 配置已完成
pre>

然后生成:

 生成完成

在我的构建目录中有一个Makefile和一些其他文件和目录。



我尝试在MSYS2 shell中运行make,我得到这个:

  c / users / myself / desktop / dll_test / with_fortran_cmake / build 
$ make
Microsoft Windows [版本6.1.7601]
版权所有(c)2009 Microsoft Corporation。版权所有。

C:\users\myself\desktop\dll_test\with_fortran_cmake\build>

最后一行是提示。如果我键入像 make 的东西,似乎再次运行它,它只是在提示符内再次提出提示。如果我按Ctrl + C,它会杀死它,并返回正常的MSYS2提示符。



所以我不知道如何实际做,假设我甚至做CMake部分正确。



问题:我如何得到这个示例代码构建/编译/运行给定的约束我列出? strong>



(我真正想做的,一旦我越过这个部分,就可以使用Visual Studio 13,因为我有一个C ++项目构建与CMake(主要由别人,我有限的访问的问题和援助),从我想要能够调用我的Fortran一旦我得到Fortran到一个类库,这是可调用的C ++从Visual Studio,Fortran几乎只是作为一个预构建的库,我知道从VS编辑Fortran不是真的很有可能,我不感兴趣这样做。)



下面是生成的 Makefile 的内容(注意,当我复制代码时,这里):

 #CMAKE生成的文件:DO NOT EDIT! 
#由MinGW MakefilesGenerator生成,CMake版本3.5

#默认目标执行时没有给任何参数。
default_target:all

.PHONY:default_target

#一次只允许一个make -f Makefile2,但传递并行性。
。NOTPARALLEL:


#============================ =============================
#由cmake提供的特殊目标。

#禁用隐式规则,以便规范的目标可以工作。
.SUFFIXES:


#从gmake中删除一些规则,不会删除.SUFFIXES。
SUFFIXES =

.SUFFIXES:.hpux_make_needs_suffix_list


#禁止显示已执行的命令。
$(VERBOSE).SILENT:


#始终过期的目标。
cmake_force:

.PHONY:cmake_force

#======================= ==================================================== ====
#为构建设置环境变量。

SHELL = cmd.exe

#CMake可执行文件。
CMAKE_COMMAND =C:\Program Files(x86)\CMake\bin\cmake.exe

#删除文件的命令。
RM =C:\Program Files(x86)\CMake\bin\cmake.exe-E remove -f

#转义特殊字符。
EQUALS = =

#运行CMake的顶级源目录。
CMAKE_SOURCE_DIR = C:\Users\myself\Desktop\dll_test\with_fortran_cmake

#运行CMake的顶级构建目录。
CMAKE_BINARY_DIR = C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build

#=============== ==================================================== ============
#CMake全球提供的目标。

#目标的特殊规则edit_cache
edit_cache:
@ $(CMAKE_COMMAND)-E cmake_echo_color --switch = $(COLOR)--cyan运行CMake缓存编辑器。 ..
C:\Program Files(x86)\CMake\bin\cmake-gui.exe-H $(CMAKE_SOURCE_DIR)-B $(CMAKE_BINARY_DIR)
.PHONY: edit_cache

#目标的特殊规则edit_cache
edit_cache / fast:edit_cache

.PHONY:edit_cache / fast

#特殊规则对于目标rebuild_cache
rebuild_cache:
@ $(CMAKE_COMMAND)-E cmake_echo_color --switch = $(COLOR)--cyan运行CMake以重新生成构建系统...
C :\Program Files(x86)\CMake\bin\cmake.exe-H $(CMAKE_SOURCE_DIR)-B $(CMAKE_BINARY_DIR)
.PHONY:rebuild_cache

#特殊目标的规则rebuild_cache
rebuild_cache / fast:rebuild_cache

.PHONY:rebuild_cache / fast

#主要所有目标
all:cmake_check_build_system
$(CMAKE_COMMAND)-E cmake_progress_start C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build\CMakeFiles C:\Users \myself\Desktop\dll_test\with_fortran_cmake\\ \\build\CMakeFiles\progress.marks
$(MAKE)-f CMakeFiles\Makefile2 all
$(CMAKE_COMMAND)-E cmake_progress_start C:\Users \myself\Desktop\dll_test \with_fortran_cmake\build\CMakeFiles 0
.PHONY:all

#主干净目标
clean:
$(MAKE)-f CMakeFiles\ Makefile2 clean
.PHONY:clean

#主要清洁目标
clean / fast:clean

.PHONY:clean / fast

#准备安装的目标。
preinstall:all
$(MAKE)-f CMakeFiles\Makefile2 preinstall
.PHONY:preinstall

#准备安装目标。
preinstall / fast:
$(MAKE)-f CMakeFiles\Makefile2 preinstall
.PHONY:preinstall / fast

#clear depends
depend:
$(CMAKE_COMMAND)-H $(CMAKE_SOURCE_DIR)-B $(CMAKE_BINARY_DIR)--check-build-system CMakeFiles\Makefile.cmake 1
.PHONY:depend

#=============================================== ==========================
#目标规则为testf

#构建规则为目标。
testf:cmake_check_build_system
$(MAKE)-f CMakeFiles\Makefile2 testf
.PHONY:testf

#目标的快速构建规则。
testf / fast:
$(MAKE)-f CMakeFiles\testf.dir\build.make CMakeFiles / testf.dir / build
.PHONY:testf / fast

test.obj:test.f90.obj

.PHONY:test.obj

#target创建一个目标文件
test.f90。 obj:
$(MAKE)-f CMakeFiles\testf.dir\build.make CMakeFiles / testf.dir / test.f90.obj
.PHONY:test.f90.obj

test.i:test.f90.i

.PHONY:test.i

#target来预处理源文件
test.f90。 i:
$(MAKE)-f CMakeFiles\testf.dir\build.make CMakeFiles / testf.dir / test.f90.i
.PHONY:test.f90.i

test.s:test.f90.s

.PHONY:test.s

#target生成文件的装配
test.f90 .s:
$(MAKE)-f CMakeFiles\testf.dir\build.make CMakeFiles / testf.dir / test.f90.s
.PHONY:test.f90.s

#帮助目标
help:
@echo以下是此Makefile的一些有效目标:
@echo ... all(如果没有提供目标,则为默认值) )
@echo ... clean
@echo ... depend
@echo ... testf
@echo ... edit_cache
@echo ... rebuild_cache
@echo ... test.obj
@echo ... test.i
@echo ... test.s
.PHONY:help



#==================== ===================================
#清除操作的特殊目标使。

#运行CMake以检查构建系统完整性的特殊规则。
#取决于此的规则可以有来自listfiles
#的命令,因为它们可能被重新生成。
cmake_check_build_system:
$(CMAKE_COMMAND)-H $(CMAKE_SOURCE_DIR)-B $(CMAKE_BINARY_DIR)--check-build-system CMakeFiles\Makefile.cmake 0
.PHONY:cmake_check_build_system

版本信息




  • GNU Fortran(GCC)5.3.0

  • Windows 7 Enterprise

  • Cmake 3.5.2

  • MSYS2 - 我不知道如何找到此版本

  • MinGW - 我不知道如何找到此版本



我在搜索过程中经历了很多不同的网页,我没有打扰他们,但是这一个特别是一个我不断碰到,因为它似乎与标题非常相关,但实际问题和解决方案完全不是:




解决方案

p>这是一个快速shell会话,显示我是如何使用MSYS2,cmake,make和gfortran构建您的Fortran程序。你应该尝试运行我做的相同的命令,看看他们是否给出不同的输出,然后调查原因。



MSYSTEM变量尤其重要;它取决于在启动MSYS2时点击的快捷方式。

  $ echo $ MSYSTEM 
MINGW64

$ which cmake
/ mingw64 / bin / cmake

$ which gfortran
/ mingw64 / bin / gfortran

$ which make make b $ b / usr / bin / make

$ ls
CMakeLists.txt test.f90

$ cat CMakeLists.txt
project(cmake_test Fortran )
add_executable(testf test.f90)

$ cat test.f90
程序测试
write(*,*)hello world
endprogram test

$ mkdir build&&& cd build

$ cmake -GMSYS Makefiles..
- Fortran编译器标识是GNU 6.2.0
- 检查Fortran编译器是否正常:D: msys64 / mingw64 / bin / gfortran.exe
- 检查Fortran编译器是否正常:D:/msys64/mingw64/bin/gfortran.exe - works
- 检测Fortran编译器ABI信息
- 检测Fortran编译器ABI info - done
- 检查D:/msys64/mingw64/bin/gfortran.exe是否支持Fortran 90
- 检查D:/ msys64 / mingw64 / bin / gfortran.exe支持Fortran 90 - 是
- 配置完成
- 生成完成
- 构建文件已写入:C:/ Users / david / Documents / scraps / test_fortran / build

$ make
扫描目标testf的依赖关系
[50%]构建Fortran对象CMakeFiles / testf.dir / test.f90.obj
[100% ]链接Fortran可执行文件testf.exe
[100%]建立目标testf

$ ./testf.exe
hello world


I've got much more I've got to get figured out with CMake than just the following problem, but it's the first and simplest one which I still can't get past. I've scoured the interwebs and even borrowed the 'Mastering CMake' book from a friend, but I'm still having the hardest time... A lot of stuff exists online with regards to CMake, Fortran, and MinGW, and even combinations of two at a time. But all three together seem to be almost non-existent.

All I want to do (at this point) is get a simple Fortran program built and compiling using CMake on Windows, using MinGW's gfortran compiler.

...And I'm a CMake n00b.

This is what I've been working with so far:

CMakeLists.txt:

project(cmake_test Fortran)
add_executable(testf test.f90)

test.f90:

      program test
      write(*,*)"hello world"
      endprogram test

I've got the MSYS2 version of MinGW, since that's the only version that the code I'm eventually going to be compiling will compile with on Windows. (Ie. when I compile it with my own Makefile in the MSYS2 shell, it compiles.)

I've got my Windows Path appended with ;C:\msys64\mingw64\bin. (I've also tried ;C:\msys64\usr\bin, but it complains about sh.exe being in the same directory, among other issues.)

Then I pop open the CMake-GUI, load in the CMakeLists above, hit Configure, specify the generator for the project to be "MinGW Makefiles", select "Use default native compilers", and get the following output:

The Fortran compiler identification is GNU 5.4.0
Check for working Fortran compiler: C:/msys64/mingw64/bin/gfortran.exe
Check for working Fortran compiler: C:/msys64/mingw64/bin/gfortran.exe  -- works
Detecting Fortran compiler ABI info
Detecting Fortran compiler ABI info - done
Checking whether C:/msys64/mingw64/bin/gfortran.exe supports Fortran 90
Checking whether C:/msys64/mingw64/bin/gfortran.exe supports Fortran 90 -- yes
Configuring done

Then I click Configure again and get:

Configuring done

Then Generate:

Generating done

In my build directory there is then a Makefile and a number of other files and directories.

I try running make in the MSYS2 shell, and I get this:

myself@COMPUTER MSYS /c/users/myself/desktop/dll_test/with_fortran_cmake/build
$ make
Microsoft Windows [Version 6.1.7601]
Copyright (c) 2009 Microsoft Corporation.  All rights reserved.

C:\users\myself\desktop\dll_test\with_fortran_cmake\build>

That last line is a prompt. If I type stuff like make it seems to run it again and it just brings up the prompt again, within the prompt. If I hit Ctrl+C, it kills it and returns to the normal MSYS2 prompt.

So I can't figure out how to actually make it, assuming I'm even doing the CMake part right.

Question: How do I get this example code to build/compile/run given the constraints I've listed?

(What I'd actually rather do, once I get past this part, is get it to work with Visual Studio 13, since I have a C++ project being built with CMake (written mostly by someone else to whom I have limited access for questions and aid) from which I want to be able to call my Fortran. Once I get the Fortran into a library of some sort which is callable by the C++ from Visual Studio, the Fortran can pretty much just be left alone as a pre-built library. I know that editing Fortran from VS is not really much of a possibility, and I'm not interested in doing it.)

Here are the contents of the generated Makefile (note my editor replaced tabs with spaces when I copied it here):

# CMAKE generated file: DO NOT EDIT!
# Generated by "MinGW Makefiles" Generator, CMake Version 3.5

# Default target executed when no arguments are given to make.
default_target: all

.PHONY : default_target

# Allow only one "make -f Makefile2" at a time, but pass parallelism.
.NOTPARALLEL:


#=============================================================================
# Special targets provided by cmake.

# Disable implicit rules so canonical targets will work.
.SUFFIXES:


# Remove some rules from gmake that .SUFFIXES does not remove.
SUFFIXES =

.SUFFIXES: .hpux_make_needs_suffix_list


# Suppress display of executed commands.
$(VERBOSE).SILENT:


# A target that is always out of date.
cmake_force:

.PHONY : cmake_force

#=============================================================================
# Set environment variables for the build.

SHELL = cmd.exe

# The CMake executable.
CMAKE_COMMAND = "C:\Program Files (x86)\CMake\bin\cmake.exe"

# The command to remove a file.
RM = "C:\Program Files (x86)\CMake\bin\cmake.exe" -E remove -f

# Escaping for special characters.
EQUALS = =

# The top-level source directory on which CMake was run.
CMAKE_SOURCE_DIR = C:\Users\myself\Desktop\dll_test\with_fortran_cmake

# The top-level build directory on which CMake was run.
CMAKE_BINARY_DIR = C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build

#=============================================================================
# Targets provided globally by CMake.

# Special rule for the target edit_cache
edit_cache:
    @$(CMAKE_COMMAND) -E cmake_echo_color --switch=$(COLOR) --cyan "Running CMake cache editor..."
    "C:\Program Files (x86)\CMake\bin\cmake-gui.exe" -H$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
.PHONY : edit_cache

# Special rule for the target edit_cache
edit_cache/fast: edit_cache

.PHONY : edit_cache/fast

# Special rule for the target rebuild_cache
rebuild_cache:
    @$(CMAKE_COMMAND) -E cmake_echo_color --switch=$(COLOR) --cyan "Running CMake to regenerate build system..."
    "C:\Program Files (x86)\CMake\bin\cmake.exe" -H$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR)
.PHONY : rebuild_cache

# Special rule for the target rebuild_cache
rebuild_cache/fast: rebuild_cache

.PHONY : rebuild_cache/fast

# The main all target
all: cmake_check_build_system
    $(CMAKE_COMMAND) -E cmake_progress_start C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build\CMakeFiles C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build\CMakeFiles\progress.marks
    $(MAKE) -f CMakeFiles\Makefile2 all
    $(CMAKE_COMMAND) -E cmake_progress_start C:\Users\myself\Desktop\dll_test\with_fortran_cmake\build\CMakeFiles 0
.PHONY : all

# The main clean target
clean:
    $(MAKE) -f CMakeFiles\Makefile2 clean
.PHONY : clean

# The main clean target
clean/fast: clean

.PHONY : clean/fast

# Prepare targets for installation.
preinstall: all
    $(MAKE) -f CMakeFiles\Makefile2 preinstall
.PHONY : preinstall

# Prepare targets for installation.
preinstall/fast:
    $(MAKE) -f CMakeFiles\Makefile2 preinstall
.PHONY : preinstall/fast

# clear depends
depend:
    $(CMAKE_COMMAND) -H$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles\Makefile.cmake 1
.PHONY : depend

#=============================================================================
# Target rules for targets named testf

# Build rule for target.
testf: cmake_check_build_system
    $(MAKE) -f CMakeFiles\Makefile2 testf
.PHONY : testf

# fast build rule for target.
testf/fast:
    $(MAKE) -f CMakeFiles\testf.dir\build.make CMakeFiles/testf.dir/build
.PHONY : testf/fast

test.obj: test.f90.obj

.PHONY : test.obj

# target to build an object file
test.f90.obj:
    $(MAKE) -f CMakeFiles\testf.dir\build.make CMakeFiles/testf.dir/test.f90.obj
.PHONY : test.f90.obj

test.i: test.f90.i

.PHONY : test.i

# target to preprocess a source file
test.f90.i:
    $(MAKE) -f CMakeFiles\testf.dir\build.make CMakeFiles/testf.dir/test.f90.i
.PHONY : test.f90.i

test.s: test.f90.s

.PHONY : test.s

# target to generate assembly for a file
test.f90.s:
    $(MAKE) -f CMakeFiles\testf.dir\build.make CMakeFiles/testf.dir/test.f90.s
.PHONY : test.f90.s

# Help Target
help:
    @echo The following are some of the valid targets for this Makefile:
    @echo ... all (the default if no target is provided)
    @echo ... clean
    @echo ... depend
    @echo ... testf
    @echo ... edit_cache
    @echo ... rebuild_cache
    @echo ... test.obj
    @echo ... test.i
    @echo ... test.s
.PHONY : help



#=============================================================================
# Special targets to cleanup operation of make.

# Special rule to run CMake to check the build system integrity.
# No rule that depends on this can have commands that come from listfiles
# because they might be regenerated.
cmake_check_build_system:
    $(CMAKE_COMMAND) -H$(CMAKE_SOURCE_DIR) -B$(CMAKE_BINARY_DIR) --check-build-system CMakeFiles\Makefile.cmake 0
.PHONY : cmake_check_build_system

Version information:

  • GNU Fortran (GCC) 5.3.0
  • Windows 7 Enterprise
  • Cmake 3.5.2
  • MSYS2 - I'm not sure how to find the version for this
  • MinGW - I'm not sure how to find the version for this

I've been through a lot of different pages online during my search, and I didn't bother keeping track of them all, but this one in particular is one I keep coming across because it seems like it's very related from the title, but the actual issue and resolution are totally not:

解决方案

Here is a quick shell session showing how I was able to build your Fortran program using MSYS2, cmake, make, and gfortran. You should try running the same commands that I did and see if they give different outputs then investigate the reason.

The MSYSTEM variable is especially important; it is determined by what shortcut you click on when starting MSYS2.

$ echo $MSYSTEM
MINGW64

$ which cmake
/mingw64/bin/cmake

$ which gfortran
/mingw64/bin/gfortran

$ which make
/usr/bin/make

$ ls
CMakeLists.txt  test.f90

$ cat CMakeLists.txt
project(cmake_test Fortran)
add_executable(testf test.f90)

$ cat test.f90
      program test
      write(*,*)"hello world"
      endprogram test

$ mkdir build && cd build

$ cmake -G"MSYS Makefiles" ..
-- The Fortran compiler identification is GNU 6.2.0
-- Check for working Fortran compiler: D:/msys64/mingw64/bin/gfortran.exe
-- Check for working Fortran compiler: D:/msys64/mingw64/bin/gfortran.exe  -- works
-- Detecting Fortran compiler ABI info
-- Detecting Fortran compiler ABI info - done
-- Checking whether D:/msys64/mingw64/bin/gfortran.exe supports Fortran 90
-- Checking whether D:/msys64/mingw64/bin/gfortran.exe supports Fortran 90 -- yes
-- Configuring done
-- Generating done
-- Build files have been written to: C:/Users/david/Documents/scraps/test_fortran/build

$ make
Scanning dependencies of target testf
[ 50%] Building Fortran object CMakeFiles/testf.dir/test.f90.obj
[100%] Linking Fortran executable testf.exe
[100%] Built target testf

$ ./testf.exe
 hello world

这篇关于如何使用MinGW gfortran通过CMake构建/编译Fortran?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆