SatyrLee
文章80
标签21
分类7

一言

文章归档

某SWAT项目【0】编译问题

某SWAT项目【0】编译问题

Happy Pi Day!

SWAT模型,不必多说,分布式水文模型的老大,诸事不决SWAT!

由于研究需要,需要修改部分代码。

获取源码及工具

SWAT源代码托管于bitbucket,采用正常git软件即可进行下载。下载后源代码内有预先编译好的版本(迷惑行为:有682,681,674版本,没有最新的683)。但是没有编译指南

考虑到需要高效编译,故采用业界顶尖草蛋的CMake进行辅助编译。在一台电脑上使用了Intel oneAPI配置编译环境,另外一台电脑采用gcc进行编译。

基于大神脚本照猫画虎编写CmakeLists.txt如下:

1
2
3
4
5
6
7
8
9
10
11
CMakeLists.txt
cmake_minimum_required(VERSION 3.10)
project(SWAT_Snow VERSION 6.83.1)
enable_language(Fortran)

SET(CMAKE_BUILD_TYPE Debug)

set (source_directories "${PROJECT_SOURCE_DIR}/src")
file(GLOB SWAT_SRCS *.f *.f90)
add_executable(SWAT_Snow ${SWAT_SRCS})
install (TARGETS ${EXECUTABLES} RUNTIME DESTINATION "bin")

编译环境

编译环境

A

B

CPU

AMD R7 4800H

Intel i7 6700HQ

RAM

DDR4 8*2

DDR3 8*2

OS

Win 11 22000.376

Win 10 19044.1586

Compiler

gfortran 9.2.0

iFort Classic 2021.5.0

CMake

3.23.0-rc1

3.23.0-rc3

编译环境

问题 0

问题描述:CMake无法找到Fortran及CXX编译器

解决办法:指定编译器路径并将必要路径添加至PATH内。set(CMAKE_Fortran_COMPILER "$PATHTO/gfortran.exe" )

问题 1

问题描述:无法编译modparm.f

出现原因:Fortran默认编译器认为一行代码仅能出现72个字符,多余的会被丢弃。通过观察发现,wol_lp在编译器中被识别为wof_,因此可推断该超过72个字符代码行尾部被截断,与其他被截取变量重名,因此报错。

解决方法:

针对gfortran,加入编译器选项:set(CMAKE_Fortran_COMPILER "$PATHTO/gfortran.exe" "-ffixed-line-length-none")

针对oneAPI,加入编译器选项:add_compile_options(/4L132)

1
2
3
4
5
6
7
$PATH\src\modparm.f:77:72:

77 real*8 :: sbactrop, sbactrolp, sbactsedp, sbactsedlp, ep_max, wof_lp
1
Error: Symbol 'wof_' at (1) already has basic type of REAL
...
CMakeFiles\SWAT_Snow.dir\build.make:1490: recipe for target 'CMakeFiles/SWAT_Snow.dir/modparm.f.obj' failed

问题 2

问题描述:gfrotran编译报错

1
2
3
4
5
6
$PATH\src\HQDAV.f90:5:10:

5 USE PARM
1
Error: 'hqdav' of module 'parm', imported at (1), is also the name of the current program unit
CMakeFiles\SWAT_Snow.dir\build.make:73: recipe for target 'CMakeFiles/SWAT_Snow.dir/HQDAV.f90.obj' failed

解决方案:暂时放弃,换用iFort编译

问题 3

问题描述:使用iFort编译出exe后无法迁移到其他系统运行,显示错误为由于找不到libifcoremd.dll,无法继续执行代码问题。

出现原因:使用动态库编译而不是编译进可执行文件中,导致需要目标系统安装相关DLL。

解决方案:加入编译器选项:/libs:static /threads

问题 4

问题描述:编译后代码无法提取数据,数据仅有年值数据。(未复现)

解决方案:使用SWAT-CUP进行提取数据(暂时)

最终流程

1
2
3
4
5
6
7
git clone https://bitbucket.org/blacklandgrasslandmodels/swat_development.git  
mkdir ./src
mv ./swat_development/*.* ./src
mkdir ./build
cd ./build
cmake ../src
cmake --build .
1
2
3
4
5
6
7
8
9
10
11
12
13
14
CMakeLists.txt
cmake_minimum_required(VERSION 3.10)

project(SWAT_Snow VERSION 6.83.1)
enable_language(Fortran)

SET(CMAKE_BUILD_TYPE Debug)
add_compile_options(/4L132 /libs:static /threads /O2)
set (source_directories "${PROJECT_SOURCE_DIR}/src")
file(GLOB SWAT_SRCS *.f *.f90)

add_executable(SWAT_Snow ${SWAT_SRCS})

install (TARGETS ${EXECUTABLES} RUNTIME DESTINATION "bin")

本文作者:SatyrLee
本文链接:http://www.naive514.top/posts/cf29f6d5/
版权声明:本文采用 CC BY-NC-SA 4.0 CN 协议进行许可