Skip to content

Commit a8d58a9

Browse files
committed
auto-build HDF5-MPI if needed
1 parent 84e61d0 commit a8d58a9

File tree

8 files changed

+227
-167
lines changed

8 files changed

+227
-167
lines changed

CMakeLists.txt

Lines changed: 12 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -39,32 +39,21 @@ include(cmake/compilers.cmake)
3939

4040
# if HDF5-MPI, ensure all the pieces are working together at configure time.
4141
if(hdf5_parallel)
42+
find_package(MPI COMPONENTS C Fortran REQUIRED)
43+
include(cmake/check_mpi.cmake)
44+
check_mpi_version()
45+
4246
find_package(HDF5 COMPONENTS Fortran parallel)
4347

44-
if(MPI_FOUND)
45-
include(cmake/check_mpi.cmake)
46-
check_mpi_version()
47-
if(HDF5_FOUND)
48-
include(cmake/hdf5_compression.cmake)
49-
hdf5_compression_flag()
50-
endif()
48+
if(HDF5_FOUND)
49+
include(cmake/hdf5_compression.cmake)
50+
hdf5_compression_flag()
51+
else()
52+
include(cmake/hdf5.cmake)
5153
endif()
5254
else()
5355
find_package(HDF5 COMPONENTS Fortran)
54-
set(hdf5_parallel_compression .false.)
55-
endif()
56-
57-
if(NOT HDF5_FOUND)
58-
message(FATAL_ERROR "HDF5 not found or working on the system. First build HDF5 by:
59-
60-
cmake -S scripts -B scripts/build -DCMAKE_INSTALL_PREFIX=~/mylibs
61-
cmake --build scripts/build
62-
63-
Then build h5fortran:
64-
65-
cmake -B build -DCMAKE_PREFIX_PATH=~/mylibs
66-
cmake --build build
67-
")
56+
set(hdf5_parallel_compression ".false.")
6857
endif()
6958

7059
if(HDF5_VERSION VERSION_LESS 1.10.2)
@@ -115,3 +104,5 @@ DESTINATION cmake
115104
)
116105

117106
include(cmake/install.cmake)
107+
108+
file(GENERATE OUTPUT .gitignore CONTENT "*")

CMakePresets.json

Lines changed: 70 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
{
2-
"version": 3,
2+
"version": 6,
33

44
"configurePresets": [
55
{
@@ -21,7 +21,7 @@
2121
"description": "Build with code coverage enabled.",
2222
"cacheVariables": {
2323
"CMAKE_BUILD_TYPE": "Debug",
24-
"coverage": true
24+
"ENABLE_COVERAGE": true
2525
}
2626
}
2727
],
@@ -30,6 +30,21 @@
3030
"name": "default",
3131
"configurePreset": "default"
3232
},
33+
{
34+
"name": "explain",
35+
"configurePreset": "default",
36+
"nativeToolOptions": ["-d", "explain"]
37+
},
38+
{
39+
"name": "keep",
40+
"configurePreset": "default",
41+
"nativeToolOptions": ["-d", "keeprsp", "-d", "keepdepfile"]
42+
},
43+
{
44+
"name": "stats",
45+
"configurePreset": "default",
46+
"nativeToolOptions": ["-d", "stats"]
47+
},
3348
{
3449
"name": "release",
3550
"configurePreset": "multi",
@@ -87,5 +102,58 @@
87102
"configurePreset": "multi",
88103
"configuration": "Debug"
89104
}
105+
],
106+
"workflowPresets": [
107+
{
108+
"name": "default",
109+
"steps": [
110+
{
111+
"type": "configure",
112+
"name": "default"
113+
},
114+
{
115+
"type": "build",
116+
"name": "default"
117+
},
118+
{
119+
"type": "test",
120+
"name": "default"
121+
}
122+
]
123+
},
124+
{
125+
"name": "debug",
126+
"steps": [
127+
{
128+
"type": "configure",
129+
"name": "multi"
130+
},
131+
{
132+
"type": "build",
133+
"name": "debug"
134+
},
135+
{
136+
"type": "test",
137+
"name": "debug"
138+
}
139+
]
140+
},
141+
{
142+
"name": "release",
143+
"steps": [
144+
{
145+
"type": "configure",
146+
"name": "multi"
147+
},
148+
{
149+
"type": "build",
150+
"name": "release"
151+
},
152+
{
153+
"type": "test",
154+
"name": "release"
155+
}
156+
]
157+
}
90158
]
91159
}

cmake/ExtProj.cmake

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
# based on github.com/gemini3d/external
2+
3+
include_guard()
4+
5+
include(ExternalProject)
6+
7+
if(CMAKE_VERSION VERSION_LESS 3.19)
8+
message(FATAL_ERROR "CMake >= 3.19 required to use JSON")
9+
endif()
10+
11+
file(READ ${CMAKE_CURRENT_LIST_DIR}/libraries.json json)
12+
13+
14+
function(extproj name cmake_args byproducts depends)
15+
16+
# PREPEND so that user arguments can override these defaults
17+
list(PREPEND cmake_args
18+
-DCMAKE_INSTALL_PREFIX:PATH=${CMAKE_INSTALL_PREFIX}
19+
-DCMAKE_PREFIX_PATH:PATH=${CMAKE_INSTALL_PREFIX}
20+
-DBUILD_SHARED_LIBS:BOOL=${BUILD_SHARED_LIBS}
21+
-DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}
22+
-DBUILD_TESTING:BOOL=false
23+
-DCMAKE_C_COMPILER=${CMAKE_C_COMPILER}
24+
-DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER}
25+
-DCMAKE_Fortran_COMPILER=${CMAKE_Fortran_COMPILER}
26+
)
27+
if(CMAKE_TOOLCHAIN_FILE)
28+
list(APPEND cmake_args -DCMAKE_TOOLCHAIN_FILE:FILEPATH=${CMAKE_TOOLCHAIN_FILE})
29+
endif()
30+
31+
# builds each project in parallel, without needing to build all projects simultaneously in parallel.
32+
# this greatly aids debugging while maintaining speed of build overall.
33+
if(CMAKE_GENERATOR MATCHES "Makefiles" AND NOT DEFINED ENV{CMAKE_BUILD_PARALLEL_LEVEL})
34+
cmake_host_system_information(RESULT Ncpu QUERY NUMBER_OF_PHYSICAL_CORES)
35+
endif()
36+
set(build_parallel ${CMAKE_COMMAND} --build <BINARY_DIR> --parallel ${Ncpu})
37+
38+
string(JSON url GET ${json} ${name} url)
39+
if(url MATCHES ".git$")
40+
41+
string(JSON tag GET ${json} ${name} tag)
42+
43+
set(download_args
44+
GIT_REPOSITORY ${url}
45+
GIT_TAG ${tag}
46+
GIT_SHALLOW true
47+
GIT_PROGRESS true
48+
)
49+
50+
else()
51+
52+
set(download_args
53+
URL ${url}
54+
)
55+
56+
endif()
57+
58+
59+
# BUILD_BYPRODUCTS is vital for Ninja, else build-time error "missing and no known rule to make it"
60+
61+
ExternalProject_Add(${name}
62+
${download_args}
63+
BUILD_COMMAND ${build_parallel}
64+
TEST_COMMAND ""
65+
CMAKE_ARGS ${cmake_args}
66+
DEPENDS ${depends}
67+
BUILD_BYPRODUCTS ${byproducts}
68+
INACTIVITY_TIMEOUT 60
69+
CONFIGURE_HANDLED_BY_BUILD true
70+
USES_TERMINAL_DOWNLOAD true
71+
USES_TERMINAL_UPDATE true
72+
USES_TERMINAL_BUILD true
73+
USES_TERMINAL_INSTALL true
74+
USES_TERMINAL_TEST true
75+
)
76+
77+
endfunction(extproj)

cmake/FindHDF5.cmake

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -94,20 +94,6 @@ set(${outvar} ${_v} PARENT_SCOPE)
9494

9595
endfunction(pop_flag)
9696

97-
macro(find_mpi)
98-
# non-cache set by FindMPI are not visible outside function -- need macro just to see within that function
99-
set(mpi_comp C)
100-
if(Fortran IN_LIST HDF5_FIND_COMPONENTS)
101-
list(APPEND mpi_comp Fortran)
102-
endif()
103-
if(HDF5_FIND_REQUIRED)
104-
find_package(MPI COMPONENTS ${mpi_comp} REQUIRED)
105-
else()
106-
find_package(MPI COMPONENTS ${mpi_comp})
107-
endif()
108-
109-
endmacro(find_mpi)
110-
11197

11298
macro(detect_config)
11399

@@ -135,8 +121,8 @@ check_symbol_exists(H5_HAVE_PARALLEL ${h5_conf} HDF5_HAVE_PARALLEL)
135121
set(HDF5_parallel_FOUND false)
136122

137123
if(HDF5_HAVE_PARALLEL)
138-
find_mpi()
139124
if(NOT MPI_FOUND)
125+
message(WARNING "user CMakeLists.txt must do find_package(MPI) if using parallel HDF5")
140126
return()
141127
endif()
142128

@@ -656,7 +642,6 @@ list(INSERT CMAKE_REQUIRED_LIBRARIES 0 ${HDF5_C_LIBRARIES})
656642
set(CMAKE_REQUIRED_INCLUDES ${HDF5_C_INCLUDE_DIR})
657643

658644
if(HDF5_parallel_FOUND)
659-
find_mpi()
660645

661646
list(APPEND CMAKE_REQUIRED_INCLUDES ${MPI_C_INCLUDE_DIRS})
662647
list(APPEND CMAKE_REQUIRED_LIBRARIES ${MPI_C_LIBRARIES})
@@ -706,7 +691,6 @@ list(INSERT CMAKE_REQUIRED_LIBRARIES 0 ${HDF5_Fortran_LIBRARIES} ${HDF5_C_LIBRAR
706691
set(CMAKE_REQUIRED_INCLUDES ${HDF5_Fortran_INCLUDE_DIR} ${HDF5_C_INCLUDE_DIR})
707692

708693
if(HDF5_parallel_FOUND)
709-
find_mpi()
710694

711695
list(APPEND CMAKE_REQUIRED_INCLUDES ${MPI_Fortran_INCLUDE_DIRS})
712696
list(APPEND CMAKE_REQUIRED_LIBRARIES ${MPI_Fortran_LIBRARIES})

0 commit comments

Comments
 (0)