From 40b2e1145a77158ef097a07e9d2f969ce4fc5bc1 Mon Sep 17 00:00:00 2001 From: Aidan Heerdegen Date: Wed, 13 Nov 2024 14:52:36 +1100 Subject: [PATCH 01/32] Add cmake build copied from COSIMA/access-om3 --- cmake/CMakeLists.txt | 227 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 227 insertions(+) create mode 100644 cmake/CMakeLists.txt diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt new file mode 100644 index 000000000..04ca0f318 --- /dev/null +++ b/cmake/CMakeLists.txt @@ -0,0 +1,227 @@ +cmake_minimum_required(VERSION 3.18) +# CMake version compatibility + +#[==============================================================================[ +# Basic project definition # +#]==============================================================================] + +project(CICE6 DESCRIPTION "CICE6" LANGUAGES C Fortran) + +# Common compiler flags and definitions +if(CMAKE_Fortran_COMPILER_ID MATCHES "GNU") + set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -fbacktrace -fconvert=big-endian -ffree-line-length-none -ffixed-line-length-none") + if(${CMAKE_Fortran_COMPILER_VERSION} VERSION_GREATER_EQUAL 10) + set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -fallow-argument-mismatch") + endif() + set(CMAKE_Fortran_FLAGS_RELEASE "-O") + set(CMAKE_Fortran_FLAGS_DEBUG "-g -Wall -Og -ffpe-trap=zero,overflow -fcheck=bounds") +elseif(CMAKE_Fortran_COMPILER_ID MATCHES "Intel") + set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -qno-opt-dynamic-align -convert big_endian -assume byterecl -ftz -traceback -assume realloc_lhs -fp-model source") + set(CMAKE_Fortran_FLAGS_RELEASE "-O2 -debug minimal") + set(CMAKE_Fortran_FLAGS_DEBUG "-O0 -g -check uninit -check bounds -check pointers -fpe0 -check noarg_temp_created") +else() + message(WARNING "Fortran compiler with ID ${CMAKE_Fortran_COMPILER_ID} will be used with CMake default options") +endif() + +if(CMAKE_C_COMPILER_ID MATCHES "GNU") + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -std=gnu99") + set(CMAKE_C_FLAGS_RELEASE "-O") + set(CMAKE_C_FLAGS_DEBUG "-g -Wall -Og -fbacktrace -ffpe-trap=invalid,zero,overflow -fcheck=bounds") +elseif(CMAKE_C_COMPILER_ID MATCHES "Intel") + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -traceback -qno-opt-dynamic-align -fp-model precise -std=gnu99") + set(CMAKE_C_FLAGS_RELEASE "-O2 -debug minimal") + set(CMAKE_C_FLAGS_DEBUG "-O0 -g") +else() + message(WARNING "C compiler with ID ${CMAKE_C_COMPILER_ID} will be used with CMake default options") +endif() + +add_compile_definitions( + CESMCOUPLED +) + +### Targets + +## CICE library +add_fortran_library(OM3_cice mod STATIC) +add_library(AccessOM3::cice ALIAS OM3_cice) +target_compile_definitions(OM3_cice PRIVATE FORTRANUNDERSCORE ncdf) +if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") + target_compile_definitions(OM3_cice PRIVATE USE_NETCDF) +endif() +target_link_libraries(OM3_cice + PUBLIC esmf + PRIVATE AccessOM3::cdeps_common AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing +) +if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") + target_link_libraries(OM3_cice PRIVATE NetCDF::NetCDF_Fortran) + if(OM3_CICE_IO MATCHES "PIO") + target_link_libraries(OM3_cice PRIVATE PIO::PIO_Fortran) + endif() +endif() +if(OpenMP_Fortran_FOUND) + target_link_libraries(OM3_cice PRIVATE OpenMP::OpenMP_Fortran) +endif() + +target_sources(OM3_cice PRIVATE + # Shared List: + CICE/cicecore/shared/ice_arrays_column.F90 + CICE/cicecore/shared/ice_calendar.F90 + CICE/cicecore/shared/ice_constants.F90 + CICE/cicecore/shared/ice_domain_size.F90 + CICE/cicecore/shared/ice_fileunits.F90 + CICE/cicecore/shared/ice_init_column.F90 + CICE/cicecore/shared/ice_kinds_mod.F90 + CICE/cicecore/shared/ice_restart_column.F90 + CICE/cicecore/shared/ice_restart_shared.F90 + CICE/cicecore/shared/ice_spacecurve.F90 + + # Analysis + CICE/cicecore/cicedyn/analysis/ice_diagnostics.F90 + CICE/cicecore/cicedyn/analysis/ice_diagnostics_bgc.F90 + CICE/cicecore/cicedyn/analysis/ice_history.F90 + CICE/cicecore/cicedyn/analysis/ice_history_bgc.F90 + CICE/cicecore/cicedyn/analysis/ice_history_drag.F90 + CICE/cicecore/cicedyn/analysis/ice_history_fsd.F90 + CICE/cicecore/cicedyn/analysis/ice_history_mechred.F90 + CICE/cicecore/cicedyn/analysis/ice_history_pond.F90 + CICE/cicecore/cicedyn/analysis/ice_history_shared.F90 + CICE/cicecore/cicedyn/analysis/ice_history_snow.F90 + + # Dynamics + CICE/cicecore/cicedyn/dynamics/ice_dyn_core1d.F90 + CICE/cicecore/cicedyn/dynamics/ice_dyn_eap.F90 + CICE/cicecore/cicedyn/dynamics/ice_dyn_evp.F90 + CICE/cicecore/cicedyn/dynamics/ice_dyn_evp1d.F90 + CICE/cicecore/cicedyn/dynamics/ice_dyn_shared.F90 + CICE/cicecore/cicedyn/dynamics/ice_dyn_vp.F90 + CICE/cicecore/cicedyn/dynamics/ice_transport_driver.F90 + CICE/cicecore/cicedyn/dynamics/ice_transport_remap.F90 + + # General + CICE/cicecore/cicedyn/general/ice_flux.F90 + CICE/cicecore/cicedyn/general/ice_flux_bgc.F90 + CICE/cicecore/cicedyn/general/ice_forcing.F90 + CICE/cicecore/cicedyn/general/ice_forcing_bgc.F90 + CICE/cicecore/cicedyn/general/ice_state.F90 + CICE/cicecore/cicedyn/general/ice_step_mod.F90 + + # Infrastructure + CICE/cicecore/cicedyn/infrastructure/ice_blocks.F90 + CICE/cicecore/cicedyn/infrastructure/ice_grid.F90 + CICE/cicecore/cicedyn/infrastructure/ice_memusage.F90 + CICE/cicecore/cicedyn/infrastructure/ice_memusage_gptl.c + CICE/cicecore/cicedyn/infrastructure/ice_read_write.F90 + CICE/cicecore/cicedyn/infrastructure/ice_restart_driver.F90 + CICE/cicecore/cicedyn/infrastructure/ice_restoring.F90 + + # Icepack + CICE/icepack/columnphysics/icepack_aerosol.F90 + CICE/icepack/columnphysics/icepack_age.F90 + CICE/icepack/columnphysics/icepack_algae.F90 + CICE/icepack/columnphysics/icepack_atmo.F90 + CICE/icepack/columnphysics/icepack_brine.F90 + CICE/icepack/columnphysics/icepack_firstyear.F90 + CICE/icepack/columnphysics/icepack_flux.F90 + CICE/icepack/columnphysics/icepack_fsd.F90 + CICE/icepack/columnphysics/icepack_intfc.F90 + CICE/icepack/columnphysics/icepack_isotope.F90 + CICE/icepack/columnphysics/icepack_itd.F90 + CICE/icepack/columnphysics/icepack_kinds.F90 + CICE/icepack/columnphysics/icepack_mechred.F90 + CICE/icepack/columnphysics/icepack_meltpond_lvl.F90 + CICE/icepack/columnphysics/icepack_meltpond_topo.F90 + CICE/icepack/columnphysics/icepack_mushy_physics.F90 + CICE/icepack/columnphysics/icepack_ocean.F90 + CICE/icepack/columnphysics/icepack_orbital.F90 + CICE/icepack/columnphysics/icepack_parameters.F90 + CICE/icepack/columnphysics/icepack_shortwave_data.F90 + CICE/icepack/columnphysics/icepack_shortwave.F90 + CICE/icepack/columnphysics/icepack_snow.F90 + CICE/icepack/columnphysics/icepack_therm_bl99.F90 + CICE/icepack/columnphysics/icepack_therm_itd.F90 + CICE/icepack/columnphysics/icepack_therm_mushy.F90 + CICE/icepack/columnphysics/icepack_therm_shared.F90 + CICE/icepack/columnphysics/icepack_therm_vertical.F90 + CICE/icepack/columnphysics/icepack_tracers.F90 + CICE/icepack/columnphysics/icepack_warnings.F90 + CICE/icepack/columnphysics/icepack_wavefracspec.F90 + CICE/icepack/columnphysics/icepack_zbgc.F90 + CICE/icepack/columnphysics/icepack_zbgc_shared.F90 + + # Shared C + CICE/cicecore/cicedyn/infrastructure/ice_shr_reprosum86.c + + # MPI + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_boundary.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_broadcast.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_communicate.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_exit.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_gather_scatter.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_global_reductions.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_reprosum.F90 + CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_timers.F90 + + # NUOPC CMEPS driver + CICE/cicecore/drivers/nuopc/cmeps/CICE_FinalMod.F90 + CICE/cicecore/drivers/nuopc/cmeps/CICE_InitMod.F90 + CICE/cicecore/drivers/nuopc/cmeps/CICE_RunMod.F90 + CICE/cicecore/drivers/nuopc/cmeps/cice_wrapper_mod.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_comp_nuopc.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_import_export.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_mesh_mod.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_prescribed_mod.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_scam.F90 + CICE/cicecore/drivers/nuopc/cmeps/ice_shr_methods.F90 +) + +# Select IO source files based on CICE_IO +if(OM3_CICE_IO MATCHES "NetCDF") + target_sources(OM3_cice PRIVATE + CICE/cicecore/cicedyn/infrastructure/io/io_netcdf/ice_history_write.F90 + CICE/cicecore/cicedyn/infrastructure/io/io_netcdf/ice_restart.F90 + ) +elseif(OM3_CICE_IO MATCHES "PIO") + target_sources(OM3_cice PRIVATE + CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_history_write.F90 + CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_pio.F90 + CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_restart.F90 + ) +elseif(OM3_CICE_IO MATCHES "Binary") + target_sources(OM3_cice PRIVATE + CICE/cicecore/cicedyn/infrastructure/io/io_binary/ice_history_write.F90 + CICE/cicecore/cicedyn/infrastructure/io/io_binary/ice_restart.F90 + ) +endif() + +add_patched_source(OM3_cice CICE/cicecore/cicedyn/infrastructure/ice_domain.F90) +add_patched_source(OM3_cice CICE/cicecore/shared/ice_distribution.F90) +add_patched_source(OM3_cice CICE/cicecore/cicedyn/general/ice_init.F90) + +### Install and Export + +## Library +if(OM3_LIB_INSTALL) + set_target_properties(OM3_cice PROPERTIES + OUTPUT_NAME access-cice + EXPORT_NAME cice + ) + install(TARGETS OM3_cice + EXPORT AccessOM3cice_Targets + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_RunTime NAMELINK_COMPONENT AccessOM3_Development + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_Development + ) + # Fortran module files are a special case, as currently there is no standard + # way of handling them in CMake + target_include_directories(OM3_cice PUBLIC "$") + get_target_property(cice_moddir OM3_cice Fortran_MODULE_DIRECTORY) + install(FILES ${cice_moddir}/ice_comp_nuopc.mod + DESTINATION ${CMAKE_INSTALL_MODULEDIR}/access-cice + COMPONENT AccessOM3_Development + ) + install(EXPORT AccessOM3cice_Targets + FILE AccessOM3ciceTargets.cmake + NAMESPACE AccessOM3:: + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessOM3 + ) + +endif() From 296f623a67d6504d58d59dfde668ea93c4a96cdc Mon Sep 17 00:00:00 2001 From: Aidan Heerdegen Date: Wed, 13 Nov 2024 15:50:49 +1100 Subject: [PATCH 02/32] Change source paths to remove leading CICE directory --- cmake/CMakeLists.txt | 207 ++++++++++++++++++++++--------------------- 1 file changed, 105 insertions(+), 102 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 04ca0f318..cb75e0e94 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -62,140 +62,143 @@ if(OpenMP_Fortran_FOUND) target_link_libraries(OM3_cice PRIVATE OpenMP::OpenMP_Fortran) endif() +set(CICE_CORE "${SRC_DIR}/cicecore/") +set(ICEPACK "${SRC_DIR}/icepack/") + target_sources(OM3_cice PRIVATE # Shared List: - CICE/cicecore/shared/ice_arrays_column.F90 - CICE/cicecore/shared/ice_calendar.F90 - CICE/cicecore/shared/ice_constants.F90 - CICE/cicecore/shared/ice_domain_size.F90 - CICE/cicecore/shared/ice_fileunits.F90 - CICE/cicecore/shared/ice_init_column.F90 - CICE/cicecore/shared/ice_kinds_mod.F90 - CICE/cicecore/shared/ice_restart_column.F90 - CICE/cicecore/shared/ice_restart_shared.F90 - CICE/cicecore/shared/ice_spacecurve.F90 + ${CICE_CORE}/shared/ice_arrays_column.F90 + ${CICE_CORE}/shared/ice_calendar.F90 + ${CICE_CORE}/shared/ice_constants.F90 + ${CICE_CORE}/shared/ice_domain_size.F90 + ${CICE_CORE}/shared/ice_fileunits.F90 + ${CICE_CORE}/shared/ice_init_column.F90 + ${CICE_CORE}/shared/ice_kinds_mod.F90 + ${CICE_CORE}/shared/ice_restart_column.F90 + ${CICE_CORE}/shared/ice_restart_shared.F90 + ${CICE_CORE}/shared/ice_spacecurve.F90 # Analysis - CICE/cicecore/cicedyn/analysis/ice_diagnostics.F90 - CICE/cicecore/cicedyn/analysis/ice_diagnostics_bgc.F90 - CICE/cicecore/cicedyn/analysis/ice_history.F90 - CICE/cicecore/cicedyn/analysis/ice_history_bgc.F90 - CICE/cicecore/cicedyn/analysis/ice_history_drag.F90 - CICE/cicecore/cicedyn/analysis/ice_history_fsd.F90 - CICE/cicecore/cicedyn/analysis/ice_history_mechred.F90 - CICE/cicecore/cicedyn/analysis/ice_history_pond.F90 - CICE/cicecore/cicedyn/analysis/ice_history_shared.F90 - CICE/cicecore/cicedyn/analysis/ice_history_snow.F90 + ${CICE_CORE}/cicedyn/analysis/ice_diagnostics.F90 + ${CICE_CORE}/cicedyn/analysis/ice_diagnostics_bgc.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_bgc.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_drag.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_fsd.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_mechred.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_pond.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_shared.F90 + ${CICE_CORE}/cicedyn/analysis/ice_history_snow.F90 # Dynamics - CICE/cicecore/cicedyn/dynamics/ice_dyn_core1d.F90 - CICE/cicecore/cicedyn/dynamics/ice_dyn_eap.F90 - CICE/cicecore/cicedyn/dynamics/ice_dyn_evp.F90 - CICE/cicecore/cicedyn/dynamics/ice_dyn_evp1d.F90 - CICE/cicecore/cicedyn/dynamics/ice_dyn_shared.F90 - CICE/cicecore/cicedyn/dynamics/ice_dyn_vp.F90 - CICE/cicecore/cicedyn/dynamics/ice_transport_driver.F90 - CICE/cicecore/cicedyn/dynamics/ice_transport_remap.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_core1d.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_eap.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_evp.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_evp1d.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_shared.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_dyn_vp.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_transport_driver.F90 + ${CICE_CORE}/cicedyn/dynamics/ice_transport_remap.F90 # General - CICE/cicecore/cicedyn/general/ice_flux.F90 - CICE/cicecore/cicedyn/general/ice_flux_bgc.F90 - CICE/cicecore/cicedyn/general/ice_forcing.F90 - CICE/cicecore/cicedyn/general/ice_forcing_bgc.F90 - CICE/cicecore/cicedyn/general/ice_state.F90 - CICE/cicecore/cicedyn/general/ice_step_mod.F90 + ${CICE_CORE}/cicedyn/general/ice_flux.F90 + ${CICE_CORE}/cicedyn/general/ice_flux_bgc.F90 + ${CICE_CORE}/cicedyn/general/ice_forcing.F90 + ${CICE_CORE}/cicedyn/general/ice_forcing_bgc.F90 + ${CICE_CORE}/cicedyn/general/ice_state.F90 + ${CICE_CORE}/cicedyn/general/ice_step_mod.F90 # Infrastructure - CICE/cicecore/cicedyn/infrastructure/ice_blocks.F90 - CICE/cicecore/cicedyn/infrastructure/ice_grid.F90 - CICE/cicecore/cicedyn/infrastructure/ice_memusage.F90 - CICE/cicecore/cicedyn/infrastructure/ice_memusage_gptl.c - CICE/cicecore/cicedyn/infrastructure/ice_read_write.F90 - CICE/cicecore/cicedyn/infrastructure/ice_restart_driver.F90 - CICE/cicecore/cicedyn/infrastructure/ice_restoring.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_blocks.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_grid.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_memusage.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_memusage_gptl.c + ${CICE_CORE}/cicedyn/infrastructure/ice_read_write.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_restart_driver.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_restoring.F90 # Icepack - CICE/icepack/columnphysics/icepack_aerosol.F90 - CICE/icepack/columnphysics/icepack_age.F90 - CICE/icepack/columnphysics/icepack_algae.F90 - CICE/icepack/columnphysics/icepack_atmo.F90 - CICE/icepack/columnphysics/icepack_brine.F90 - CICE/icepack/columnphysics/icepack_firstyear.F90 - CICE/icepack/columnphysics/icepack_flux.F90 - CICE/icepack/columnphysics/icepack_fsd.F90 - CICE/icepack/columnphysics/icepack_intfc.F90 - CICE/icepack/columnphysics/icepack_isotope.F90 - CICE/icepack/columnphysics/icepack_itd.F90 - CICE/icepack/columnphysics/icepack_kinds.F90 - CICE/icepack/columnphysics/icepack_mechred.F90 - CICE/icepack/columnphysics/icepack_meltpond_lvl.F90 - CICE/icepack/columnphysics/icepack_meltpond_topo.F90 - CICE/icepack/columnphysics/icepack_mushy_physics.F90 - CICE/icepack/columnphysics/icepack_ocean.F90 - CICE/icepack/columnphysics/icepack_orbital.F90 - CICE/icepack/columnphysics/icepack_parameters.F90 - CICE/icepack/columnphysics/icepack_shortwave_data.F90 - CICE/icepack/columnphysics/icepack_shortwave.F90 - CICE/icepack/columnphysics/icepack_snow.F90 - CICE/icepack/columnphysics/icepack_therm_bl99.F90 - CICE/icepack/columnphysics/icepack_therm_itd.F90 - CICE/icepack/columnphysics/icepack_therm_mushy.F90 - CICE/icepack/columnphysics/icepack_therm_shared.F90 - CICE/icepack/columnphysics/icepack_therm_vertical.F90 - CICE/icepack/columnphysics/icepack_tracers.F90 - CICE/icepack/columnphysics/icepack_warnings.F90 - CICE/icepack/columnphysics/icepack_wavefracspec.F90 - CICE/icepack/columnphysics/icepack_zbgc.F90 - CICE/icepack/columnphysics/icepack_zbgc_shared.F90 + ${ICEPACK}/columnphysics/icepack_aerosol.F90 + ${ICEPACK}/columnphysics/icepack_age.F90 + ${ICEPACK}/columnphysics/icepack_algae.F90 + ${ICEPACK}/columnphysics/icepack_atmo.F90 + ${ICEPACK}/columnphysics/icepack_brine.F90 + ${ICEPACK}/columnphysics/icepack_firstyear.F90 + ${ICEPACK}/columnphysics/icepack_flux.F90 + ${ICEPACK}/columnphysics/icepack_fsd.F90 + ${ICEPACK}/columnphysics/icepack_intfc.F90 + ${ICEPACK}/columnphysics/icepack_isotope.F90 + ${ICEPACK}/columnphysics/icepack_itd.F90 + ${ICEPACK}/columnphysics/icepack_kinds.F90 + ${ICEPACK}/columnphysics/icepack_mechred.F90 + ${ICEPACK}/columnphysics/icepack_meltpond_lvl.F90 + ${ICEPACK}/columnphysics/icepack_meltpond_topo.F90 + ${ICEPACK}/columnphysics/icepack_mushy_physics.F90 + ${ICEPACK}/columnphysics/icepack_ocean.F90 + ${ICEPACK}/columnphysics/icepack_orbital.F90 + ${ICEPACK}/columnphysics/icepack_parameters.F90 + ${ICEPACK}/columnphysics/icepack_shortwave_data.F90 + ${ICEPACK}/columnphysics/icepack_shortwave.F90 + ${ICEPACK}/columnphysics/icepack_snow.F90 + ${ICEPACK}/columnphysics/icepack_therm_bl99.F90 + ${ICEPACK}/columnphysics/icepack_therm_itd.F90 + ${ICEPACK}/columnphysics/icepack_therm_mushy.F90 + ${ICEPACK}/columnphysics/icepack_therm_shared.F90 + ${ICEPACK}/columnphysics/icepack_therm_vertical.F90 + ${ICEPACK}/columnphysics/icepack_tracers.F90 + ${ICEPACK}/columnphysics/icepack_warnings.F90 + ${ICEPACK}/columnphysics/icepack_wavefracspec.F90 + ${ICEPACK}/columnphysics/icepack_zbgc.F90 + ${ICEPACK}/columnphysics/icepack_zbgc_shared.F90 # Shared C - CICE/cicecore/cicedyn/infrastructure/ice_shr_reprosum86.c + ${CICE_CORE}/cicedyn/infrastructure/ice_shr_reprosum86.c # MPI - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_boundary.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_broadcast.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_communicate.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_exit.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_gather_scatter.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_global_reductions.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_reprosum.F90 - CICE/cicecore/cicedyn/infrastructure/comm/mpi/ice_timers.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_boundary.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_broadcast.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_communicate.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_exit.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_gather_scatter.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_global_reductions.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_reprosum.F90 + ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_timers.F90 # NUOPC CMEPS driver - CICE/cicecore/drivers/nuopc/cmeps/CICE_FinalMod.F90 - CICE/cicecore/drivers/nuopc/cmeps/CICE_InitMod.F90 - CICE/cicecore/drivers/nuopc/cmeps/CICE_RunMod.F90 - CICE/cicecore/drivers/nuopc/cmeps/cice_wrapper_mod.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_comp_nuopc.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_import_export.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_mesh_mod.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_prescribed_mod.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_scam.F90 - CICE/cicecore/drivers/nuopc/cmeps/ice_shr_methods.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_InitMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_RunMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/cice_wrapper_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_comp_nuopc.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_import_export.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_mesh_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_prescribed_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_scam.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_shr_methods.F90 ) # Select IO source files based on CICE_IO if(OM3_CICE_IO MATCHES "NetCDF") target_sources(OM3_cice PRIVATE - CICE/cicecore/cicedyn/infrastructure/io/io_netcdf/ice_history_write.F90 - CICE/cicecore/cicedyn/infrastructure/io/io_netcdf/ice_restart.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_history_write.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_restart.F90 ) elseif(OM3_CICE_IO MATCHES "PIO") target_sources(OM3_cice PRIVATE - CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_history_write.F90 - CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_pio.F90 - CICE/cicecore/cicedyn/infrastructure/io/io_pio2/ice_restart.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_history_write.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_pio.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_restart.F90 ) elseif(OM3_CICE_IO MATCHES "Binary") target_sources(OM3_cice PRIVATE - CICE/cicecore/cicedyn/infrastructure/io/io_binary/ice_history_write.F90 - CICE/cicecore/cicedyn/infrastructure/io/io_binary/ice_restart.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_history_write.F90 + ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_restart.F90 ) endif() -add_patched_source(OM3_cice CICE/cicecore/cicedyn/infrastructure/ice_domain.F90) -add_patched_source(OM3_cice CICE/cicecore/shared/ice_distribution.F90) -add_patched_source(OM3_cice CICE/cicecore/cicedyn/general/ice_init.F90) +add_patched_source(OM3_cice ${CICE_CORE}/cicedyn/infrastructure/ice_domain.F90) +add_patched_source(OM3_cice ${CICE_CORE}/shared/ice_distribution.F90) +add_patched_source(OM3_cice ${CICE_CORE}/cicedyn/general/ice_init.F90) ### Install and Export From 677113b6eb7c1662ea54f3234c00a34afc6cf492 Mon Sep 17 00:00:00 2001 From: Aidan Heerdegen Date: Wed, 13 Nov 2024 15:51:48 +1100 Subject: [PATCH 03/32] Add Fortran library cmake function --- cmake/FortranLib.cmake | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 cmake/FortranLib.cmake diff --git a/cmake/FortranLib.cmake b/cmake/FortranLib.cmake new file mode 100644 index 000000000..08bcccbf8 --- /dev/null +++ b/cmake/FortranLib.cmake @@ -0,0 +1,8 @@ +function(add_fortran_library LIB MOD_DIR) + add_library(${LIB} ${ARGN}) + + get_target_property(LIB_DIR ${LIB} BINARY_DIR) + set_target_properties(${LIB} PROPERTIES Fortran_MODULE_DIRECTORY ${LIB_DIR}/${MOD_DIR}) + + target_include_directories(${LIB} INTERFACE "$") + endfunction(add_fortran_library) From 432d562f2f52e1c6aeb165aa12442687a233e628 Mon Sep 17 00:00:00 2001 From: Aidan Heerdegen Date: Wed, 13 Nov 2024 16:03:47 +1100 Subject: [PATCH 04/32] Remove source code patching --- cmake/CMakeLists.txt | 4 ---- 1 file changed, 4 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index cb75e0e94..09fe31f56 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -196,10 +196,6 @@ elseif(OM3_CICE_IO MATCHES "Binary") ) endif() -add_patched_source(OM3_cice ${CICE_CORE}/cicedyn/infrastructure/ice_domain.F90) -add_patched_source(OM3_cice ${CICE_CORE}/shared/ice_distribution.F90) -add_patched_source(OM3_cice ${CICE_CORE}/cicedyn/general/ice_init.F90) - ### Install and Export ## Library From d48a342d5b219408d9d9b046b60e04a1b3866cc5 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Wed, 13 Nov 2024 16:49:27 +1100 Subject: [PATCH 05/32] hacks to fix paths & add_fortran_library --- cmake/CMakeLists.txt | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 09fe31f56..4801d2a97 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -1,6 +1,17 @@ cmake_minimum_required(VERSION 3.18) # CMake version compatibility +#function to put somewhere neater +function(add_fortran_library LIB MOD_DIR) + add_library(${LIB} ${ARGN}) + + get_target_property(LIB_DIR ${LIB} BINARY_DIR) + set_target_properties(${LIB} PROPERTIES Fortran_MODULE_DIRECTORY ${LIB_DIR}/${MOD_DIR}) + + target_include_directories(${LIB} INTERFACE "$") + endfunction(add_fortran_library) + + #[==============================================================================[ # Basic project definition # #]==============================================================================] @@ -62,8 +73,8 @@ if(OpenMP_Fortran_FOUND) target_link_libraries(OM3_cice PRIVATE OpenMP::OpenMP_Fortran) endif() -set(CICE_CORE "${SRC_DIR}/cicecore/") -set(ICEPACK "${SRC_DIR}/icepack/") +set(CICE_CORE "${CMAKE_SOURCE_DIR}/../cicecore") +set(ICEPACK "${CMAKE_SOURCE_DIR}/../icepack") target_sources(OM3_cice PRIVATE # Shared List: From 07b4ea2e8575a40eea7117f978ad3ac3dd283661 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Mon, 18 Nov 2024 16:52:26 +1100 Subject: [PATCH 06/32] messing around with building libraries --- cmake/CMakeLists.txt | 65 ++++---- cmake/FindFoX.cmake | 56 +++++++ cmake/FindNetCDF.cmake | 337 +++++++++++++++++++++++++++++++++++++++++ cmake/FindPIO.cmake | 209 +++++++++++++++++++++++++ 4 files changed, 640 insertions(+), 27 deletions(-) create mode 100644 cmake/FindFoX.cmake create mode 100644 cmake/FindNetCDF.cmake create mode 100644 cmake/FindPIO.cmake diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 4801d2a97..0c94c45a9 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -1,16 +1,4 @@ cmake_minimum_required(VERSION 3.18) -# CMake version compatibility - -#function to put somewhere neater -function(add_fortran_library LIB MOD_DIR) - add_library(${LIB} ${ARGN}) - - get_target_property(LIB_DIR ${LIB} BINARY_DIR) - set_target_properties(${LIB} PROPERTIES Fortran_MODULE_DIRECTORY ${LIB_DIR}/${MOD_DIR}) - - target_include_directories(${LIB} INTERFACE "$") - endfunction(add_fortran_library) - #[==============================================================================[ # Basic project definition # @@ -18,6 +6,11 @@ function(add_fortran_library LIB MOD_DIR) project(CICE6 DESCRIPTION "CICE6" LANGUAGES C Fortran) +list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}) +include(GNUInstallDirs) +include(FortranLib) + + # Common compiler flags and definitions if(CMAKE_Fortran_COMPILER_ID MATCHES "GNU") set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -fbacktrace -fconvert=big-endian -ffree-line-length-none -ffixed-line-length-none") @@ -50,6 +43,17 @@ add_compile_definitions( CESMCOUPLED ) +## Fortran modules path; currently this is simply set to be the include dir +set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} + CACHE STRING + "Fortran module installation path (Not a cmake native variable)" +) + +find_package(Access3Share) +find_package(FoX 4.1.2 REQUIRED) +find_package(NetCDF 4.7.3 REQUIRED Fortran) +find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) + ### Targets ## CICE library @@ -61,7 +65,7 @@ if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") endif() target_link_libraries(OM3_cice PUBLIC esmf - PRIVATE AccessOM3::cdeps_common AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing + PRIVATE AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing AccessOM3::cdeps-common ) if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") target_link_libraries(OM3_cice PRIVATE NetCDF::NetCDF_Fortran) @@ -88,6 +92,7 @@ target_sources(OM3_cice PRIVATE ${CICE_CORE}/shared/ice_restart_column.F90 ${CICE_CORE}/shared/ice_restart_shared.F90 ${CICE_CORE}/shared/ice_spacecurve.F90 + ${CICE_CORE}/shared/ice_distribution.F90 # Analysis ${CICE_CORE}/cicedyn/analysis/ice_diagnostics.F90 @@ -112,6 +117,7 @@ target_sources(OM3_cice PRIVATE ${CICE_CORE}/cicedyn/dynamics/ice_transport_remap.F90 # General + ${CICE_CORE}/cicedyn/general/ice_init.F90 ${CICE_CORE}/cicedyn/general/ice_flux.F90 ${CICE_CORE}/cicedyn/general/ice_flux_bgc.F90 ${CICE_CORE}/cicedyn/general/ice_forcing.F90 @@ -127,6 +133,7 @@ target_sources(OM3_cice PRIVATE ${CICE_CORE}/cicedyn/infrastructure/ice_read_write.F90 ${CICE_CORE}/cicedyn/infrastructure/ice_restart_driver.F90 ${CICE_CORE}/cicedyn/infrastructure/ice_restoring.F90 + ${CICE_CORE}/cicedyn/infrastructure/ice_domain.F90 # Icepack ${ICEPACK}/columnphysics/icepack_aerosol.F90 @@ -174,20 +181,24 @@ target_sources(OM3_cice PRIVATE ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_global_reductions.F90 ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_reprosum.F90 ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_timers.F90 - - # NUOPC CMEPS driver - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_InitMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_RunMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/cice_wrapper_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_comp_nuopc.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_import_export.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_mesh_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_prescribed_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_scam.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_shr_methods.F90 ) +if(OM3_LIB_INSTALL) + target_sources(OM3_cice PRIVATE + # NUOPC CMEPS driver + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_InitMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/CICE_RunMod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/cice_wrapper_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_comp_nuopc.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_import_export.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_mesh_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_prescribed_mod.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_scam.F90 + ${CICE_CORE}/drivers/nuopc/cmeps/ice_shr_methods.F90 + ) +endif() + # Select IO source files based on CICE_IO if(OM3_CICE_IO MATCHES "NetCDF") target_sources(OM3_cice PRIVATE @@ -225,13 +236,13 @@ if(OM3_LIB_INSTALL) target_include_directories(OM3_cice PUBLIC "$") get_target_property(cice_moddir OM3_cice Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod - DESTINATION ${CMAKE_INSTALL_MODULEDIR}/access-cice + DESTINATION ${CMAKE_INSTALL_MODULEDIR}/CICE COMPONENT AccessOM3_Development ) install(EXPORT AccessOM3cice_Targets FILE AccessOM3ciceTargets.cmake NAMESPACE AccessOM3:: - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessOM3 + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/CICE ) endif() diff --git a/cmake/FindFoX.cmake b/cmake/FindFoX.cmake new file mode 100644 index 000000000..b09bb35c9 --- /dev/null +++ b/cmake/FindFoX.cmake @@ -0,0 +1,56 @@ +# We will use pkgconfig to find the library +find_package(PkgConfig REQUIRED) + +## Prepare arguments to pass to pkg_search_module + +# QUIET +set(_quiet_arg) +if (FoX_FIND_QUIETLY) + list(APPEND _quiet_arg QUIET) +endif () + +# REQUIRED +set(_required_arg) +if (FoX_FIND_REQUIRED) + list(APPEND _required_arg REQUIRED) +endif () + +# Construct the moduleSpec to search for +if (DEFINED FoX_FIND_VERSION_RANGE) + # Can only parse the minimum requirement + list(APPEND PKG_MODULE_SPECS "fox>=${FoX_FIND_VERSION_MIN}") +elseif ({FoX_FIND_VERSION_EXACT) + # Requesting exact version + list(APPEND PKG_MODULE_SPECS "fox=${FoX_FIND_VERSION}") +elseif (DEFINED FoX_FIND_VERSION) + # Otherwise treat the request as minimum requirement + list(APPEND PKG_MODULE_SPECS "fox>=${FoX_FIND_VERSION}") +else () + # Fallthrough if no version is required + list(APPEND PKG_MODULE_SPECS "fox") +endif () + +## Call pkg-config +if (CMAKE_VERSION VERSION_LESS 3.28) + # https://gitlab.kitware.com/cmake/cmake/-/issues/25228 + set(ENV{PKG_CONFIG_ALLOW_SYSTEM_CFLAGS} 1) +endif () +if (CMAKE_VERSION VERSION_LESS 3.22) + # Back-porting + # https://gitlab.kitware.com/cmake/cmake/-/merge_requests/6345 + set(ENV{PKG_CONFIG_ALLOW_SYSTEM_LIBS} 1) +endif () +pkg_search_module(FoX + ${_required_arg} ${_quiet_arg} + IMPORTED_TARGET + ${PKG_MODULE_SPECS}) + +## Create alias if package was found by pkg-config +if (FoX_FOUND) + add_library(FoX::FoX ALIAS PkgConfig::FoX) +endif () + +# Sanitize local variables +set(PKG_MODULE_SPECS) +set(_quiet_arg) +set(_required_arg) diff --git a/cmake/FindNetCDF.cmake b/cmake/FindNetCDF.cmake new file mode 100644 index 000000000..1439ae848 --- /dev/null +++ b/cmake/FindNetCDF.cmake @@ -0,0 +1,337 @@ +# (C) Copyright 2011- ECMWF. +# +# This software is licensed under the terms of the Apache Licence Version 2.0 +# which can be obtained at http://www.apache.org/licenses/LICENSE-2.0. +# In applying this licence, ECMWF does not waive the privileges and immunities +# granted to it by virtue of its status as an intergovernmental organisation nor +# does it submit to any jurisdiction. + +# Try to find NetCDF includes and library. +# Supports static and shared libaries and allows each component to be found in sepearte prefixes. +# +# This module defines +# +# - NetCDF_FOUND - System has NetCDF +# - NetCDF_INCLUDE_DIRS - the NetCDF include directories +# - NetCDF_VERSION - the version of NetCDF +# - NetCDF_CONFIG_EXECUTABLE - the netcdf-config executable if found +# - NetCDF_PARALLEL - Boolean True if NetCDF4 has parallel IO support via hdf5 and/or pnetcdf +# - NetCDF_HAS_PNETCDF - Boolean True if NetCDF4 has pnetcdf support +# +# Deprecated Defines +# - NetCDF_LIBRARIES - [Deprecated] Use NetCDF::NetCDF_ targets instead. +# +# +# Following components are available: +# +# - C - C interface to NetCDF (netcdf) +# - CXX - CXX4 interface to NetCDF (netcdf_c++4) +# - Fortran - Fortran interface to NetCDF (netcdff) +# +# For each component the following are defined: +# +# - NetCDF__FOUND - whether the component is found +# - NetCDF__LIBRARIES - the libraries for the component +# - NetCDF__LIBRARY_SHARED - Boolean is true if libraries for component are shared +# - NetCDF__INCLUDE_DIRS - the include directories for specified component +# - NetCDF::NetCDF_ - target of component to be used with target_link_libraries() +# +# The following paths will be searched in order if set in CMake (first priority) or environment (second priority) +# +# - NetCDF_ROOT - root of NetCDF installation +# - NetCDF_PATH - root of NetCDF installation +# +# The search process begins with locating NetCDF Include headers. If these are in a non-standard location, +# set one of the following CMake or environment variables to point to the location: +# +# - NetCDF_INCLUDE_DIR or NetCDF_${comp}_INCLUDE_DIR +# - NetCDF_INCLUDE_DIRS or NetCDF_${comp}_INCLUDE_DIR +# +# Notes: +# +# - Use "NetCDF::NetCDF_" targets only. NetCDF_LIBRARIES exists for backwards compatibility and should not be used. +# - These targets have all the knowledge of include directories and library search directories, and a single +# call to target_link_libraries will provide all these transitive properties to your target. Normally all that is +# needed to build and link against NetCDF is, e.g.: +# target_link_libraries(my_c_tgt PUBLIC NetCDF::NetCDF_C) +# - "NetCDF" is always the preferred naming for this package, its targets, variables, and environment variables +# - For compatibility, some variables are also set/checked using alternate names NetCDF4, NETCDF, or NETCDF4 +# - Environments relying on these older environment variable names should move to using a "NetCDF_ROOT" environment variable +# - Preferred component capitalization follows the CMake LANGUAGES variables: i.e., C, Fortran, CXX +# - For compatibility, alternate capitalizations are supported but should not be used. +# - If no components are defined, all components will be searched +# + +list( APPEND _possible_components C CXX Fortran ) + +## Include names for each component +set( NetCDF_C_INCLUDE_NAME netcdf.h ) +set( NetCDF_CXX_INCLUDE_NAME netcdf ) +set( NetCDF_Fortran_INCLUDE_NAME netcdf.mod ) + +## Library names for each component +set( NetCDF_C_LIBRARY_NAME netcdf ) +set( NetCDF_CXX_LIBRARY_NAME netcdf_c++4 ) +set( NetCDF_Fortran_LIBRARY_NAME netcdff ) + +## Enumerate search components +foreach( _comp ${_possible_components} ) + string( TOUPPER "${_comp}" _COMP ) + set( _arg_${_COMP} ${_comp} ) + set( _name_${_COMP} ${_comp} ) +endforeach() + +set( _search_components C) +foreach( _comp ${${CMAKE_FIND_PACKAGE_NAME}_FIND_COMPONENTS} ) + string( TOUPPER "${_comp}" _COMP ) + set( _arg_${_COMP} ${_comp} ) + list( APPEND _search_components ${_name_${_COMP}} ) + if( NOT _name_${_COMP} ) + message(SEND_ERROR "Find${CMAKE_FIND_PACKAGE_NAME}: COMPONENT ${_comp} is not a valid component. Valid components: ${_possible_components}" ) + endif() +endforeach() +list( REMOVE_DUPLICATES _search_components ) + +## Search hints for finding include directories and libraries +foreach( _comp IN ITEMS "_" "_C_" "_Fortran_" "_CXX_" ) + foreach( _name IN ITEMS NetCDF4 NetCDF NETCDF4 NETCDF ) + foreach( _var IN ITEMS ROOT PATH ) + list(APPEND _search_hints ${${_name}${_comp}${_var}} $ENV{${_name}${_comp}${_var}} ) + list(APPEND _include_search_hints + ${${_name}${_comp}INCLUDE_DIR} $ENV{${_name}${_comp}INCLUDE_DIR} + ${${_name}${_comp}INCLUDE_DIRS} $ENV{${_name}${_comp}INCLUDE_DIRS} ) + endforeach() + endforeach() +endforeach() +#Old-school HPC module env variable names +foreach( _name IN ITEMS NetCDF4 NetCDF NETCDF4 NETCDF ) + foreach( _comp IN ITEMS "_C" "_Fortran" "_CXX" ) + list(APPEND _search_hints ${${_name}} $ENV{${_name}}) + list(APPEND _search_hints ${${_name}${_comp}} $ENV{${_name}${_comp}}) + endforeach() +endforeach() + +## Find headers for each component +set(NetCDF_INCLUDE_DIRS) +set(_new_search_components) +foreach( _comp IN LISTS _search_components ) + if(NOT ${PROJECT_NAME}_NetCDF_${_comp}_FOUND) + list(APPEND _new_search_components ${_comp}) + endif() + find_file(NetCDF_${_comp}_INCLUDE_FILE + NAMES ${NetCDF_${_comp}_INCLUDE_NAME} + DOC "NetCDF ${_comp} include directory" + HINTS ${_include_search_hints} ${_search_hints} + PATH_SUFFIXES include include/netcdf + ) + mark_as_advanced(NetCDF_${_comp}_INCLUDE_FILE) + message(DEBUG "NetCDF_${_comp}_INCLUDE_FILE: ${NetCDF_${_comp}_INCLUDE_FILE}") + if( NetCDF_${_comp}_INCLUDE_FILE ) + get_filename_component(NetCDF_${_comp}_INCLUDE_FILE ${NetCDF_${_comp}_INCLUDE_FILE} ABSOLUTE) + get_filename_component(NetCDF_${_comp}_INCLUDE_DIR ${NetCDF_${_comp}_INCLUDE_FILE} DIRECTORY) + list(APPEND NetCDF_INCLUDE_DIRS ${NetCDF_${_comp}_INCLUDE_DIR}) + endif() +endforeach() +if(NetCDF_INCLUDE_DIRS) + list(REMOVE_DUPLICATES NetCDF_INCLUDE_DIRS) +endif() +set(NetCDF_INCLUDE_DIRS "${NetCDF_INCLUDE_DIRS}" CACHE STRING "NetCDF Include directory paths" FORCE) + +## Find n*-config executables for search components +foreach( _comp IN LISTS _search_components ) + if( _comp MATCHES "^(C)$" ) + set(_conf "c") + elseif( _comp MATCHES "^(Fortran)$" ) + set(_conf "f") + elseif( _comp MATCHES "^(CXX)$" ) + set(_conf "cxx4") + endif() + find_program( NetCDF_${_comp}_CONFIG_EXECUTABLE + NAMES n${_conf}-config + HINTS ${NetCDF_INCLUDE_DIRS} ${_include_search_hints} ${_search_hints} + PATH_SUFFIXES bin Bin ../bin ../../bin + DOC "NetCDF n${_conf}-config helper" ) + message(DEBUG "NetCDF_${_comp}_CONFIG_EXECUTABLE: ${NetCDF_${_comp}_CONFIG_EXECUTABLE}") +endforeach() + +set(_C_libs_flag --libs) +set(_Fortran_libs_flag --flibs) +set(_CXX_libs_flag --libs) +set(_C_includes_flag --includedir) +set(_Fortran_includes_flag --includedir) +set(_CXX_includes_flag --includedir) +function(netcdf_config exec flag output_var) + set(${output_var} False PARENT_SCOPE) + if( exec ) + execute_process( COMMAND ${exec} ${flag} RESULT_VARIABLE _ret OUTPUT_VARIABLE _val) + if( _ret EQUAL 0 ) + string( STRIP ${_val} _val ) + set( ${output_var} ${_val} PARENT_SCOPE ) + endif() + endif() +endfunction() + +## Find libraries for each component +set( NetCDF_LIBRARIES ) +foreach( _comp IN LISTS _search_components ) + string( TOUPPER "${_comp}" _COMP ) + + find_library( NetCDF_${_comp}_LIBRARY + NAMES ${NetCDF_${_comp}_LIBRARY_NAME} + DOC "NetCDF ${_comp} library" + HINTS ${NetCDF_${_comp}_INCLUDE_DIRS} ${_search_hints} + PATH_SUFFIXES lib64 lib ../lib64 ../lib ../../lib64 ../../lib ) + mark_as_advanced( NetCDF_${_comp}_LIBRARY ) + get_filename_component(NetCDF_${_comp}_LIBRARY ${NetCDF_${_comp}_LIBRARY} ABSOLUTE) + set(NetCDF_${_comp}_LIBRARY ${NetCDF_${_comp}_LIBRARY} CACHE STRING "NetCDF ${_comp} library" FORCE) + message(DEBUG "NetCDF_${_comp}_LIBRARY: ${NetCDF_${_comp}_LIBRARY}") + + if( NetCDF_${_comp}_LIBRARY ) + if( NetCDF_${_comp}_LIBRARY MATCHES ".a$" ) + set( NetCDF_${_comp}_LIBRARY_SHARED FALSE ) + set( _library_type STATIC) + else() + list( APPEND NetCDF_LIBRARIES ${NetCDF_${_comp}_LIBRARY} ) + set( NetCDF_${_comp}_LIBRARY_SHARED TRUE ) + set( _library_type SHARED) + endif() + endif() + + #Use nc-config to set per-component LIBRARIES variable if possible + netcdf_config( ${NetCDF_${_comp}_CONFIG_EXECUTABLE} ${_${_comp}_libs_flag} _val ) + if( _val ) + set( NetCDF_${_comp}_LIBRARIES ${_val} ) + if(NOT NetCDF_${_comp}_LIBRARY_SHARED AND NOT NetCDF_${_comp}_FOUND) #Static targets should use nc_config to get a proper link line with all necessary static targets. + list( APPEND NetCDF_LIBRARIES ${NetCDF_${_comp}_LIBRARIES} ) + endif() + else() + set( NetCDF_${_comp}_LIBRARIES ${NetCDF_${_comp}_LIBRARY} ) + if(NOT NetCDF_${_comp}_LIBRARY_SHARED) + message(SEND_ERROR "Unable to properly find NetCDF. Found static libraries at: ${NetCDF_${_comp}_LIBRARY} but could not run nc-config: ${NetCDF_CONFIG_EXECUTABLE}") + endif() + endif() + + #Use nc-config to set per-component INCLUDE_DIRS variable if possible + netcdf_config( ${NetCDF_${_comp}_CONFIG_EXECUTABLE} ${_${_comp}_includes_flag} _val ) + if( _val ) + string( REPLACE " " ";" _val ${_val} ) + set( NetCDF_${_comp}_INCLUDE_DIRS ${_val} ) + else() + set( NetCDF_${_comp}_INCLUDE_DIRS ${NetCDF_${_comp}_INCLUDE_DIR} ) + endif() + + if( NetCDF_${_comp}_LIBRARIES AND NetCDF_${_comp}_INCLUDE_DIRS ) + set( ${CMAKE_FIND_PACKAGE_NAME}_${_arg_${_COMP}}_FOUND TRUE ) + if (NOT TARGET NetCDF::NetCDF_${_comp}) + add_library(NetCDF::NetCDF_${_comp} ${_library_type} IMPORTED) + set_target_properties(NetCDF::NetCDF_${_comp} PROPERTIES + IMPORTED_LOCATION ${NetCDF_${_comp}_LIBRARY} + INTERFACE_INCLUDE_DIRECTORIES "${NetCDF_${_comp}_INCLUDE_DIRS}" + INTERFACE_LINK_LIBRARIES ${NetCDF_${_comp}_LIBRARIES} ) + endif() + endif() +endforeach() +if(NetCDF_LIBRARIES AND NetCDF_${_comp}_LIBRARY_SHARED) + list(REMOVE_DUPLICATES NetCDF_LIBRARIES) +endif() +set(NetCDF_LIBRARIES "${NetCDF_LIBRARIES}" CACHE STRING "NetCDF library targets" FORCE) + +## Find version via netcdf-config if possible +if (NetCDF_INCLUDE_DIRS) + if( NetCDF_C_CONFIG_EXECUTABLE ) + netcdf_config( ${NetCDF_C_CONFIG_EXECUTABLE} --version _vers ) + if( _vers ) + string(REGEX REPLACE ".* ((([0-9]+)\\.)+([0-9]+)).*" "\\1" NetCDF_VERSION "${_vers}" ) + endif() + else() + foreach( _dir IN LISTS NetCDF_INCLUDE_DIRS) + if( EXISTS "${_dir}/netcdf_meta.h" ) + file(STRINGS "${_dir}/netcdf_meta.h" _netcdf_version_lines + REGEX "#define[ \t]+NC_VERSION_(MAJOR|MINOR|PATCH|NOTE)") + string(REGEX REPLACE ".*NC_VERSION_MAJOR *\([0-9]*\).*" "\\1" _netcdf_version_major "${_netcdf_version_lines}") + string(REGEX REPLACE ".*NC_VERSION_MINOR *\([0-9]*\).*" "\\1" _netcdf_version_minor "${_netcdf_version_lines}") + string(REGEX REPLACE ".*NC_VERSION_PATCH *\([0-9]*\).*" "\\1" _netcdf_version_patch "${_netcdf_version_lines}") + string(REGEX REPLACE ".*NC_VERSION_NOTE *\"\([^\"]*\)\".*" "\\1" _netcdf_version_note "${_netcdf_version_lines}") + set(NetCDF_VERSION "${_netcdf_version_major}.${_netcdf_version_minor}.${_netcdf_version_patch}${_netcdf_version_note}") + unset(_netcdf_version_major) + unset(_netcdf_version_minor) + unset(_netcdf_version_patch) + unset(_netcdf_version_note) + unset(_netcdf_version_lines) + endif() + endforeach() + endif() +endif () + +## Detect additional package properties +netcdf_config(${NetCDF_C_CONFIG_EXECUTABLE} --has-parallel4 _val) +if( NOT _val MATCHES "^(yes|no)$" ) + netcdf_config(${NetCDF_C_CONFIG_EXECUTABLE} --has-parallel _val) +endif() +if( _val MATCHES "^(yes)$" ) + set(NetCDF_PARALLEL TRUE CACHE STRING "NetCDF has parallel IO capability via pnetcdf or hdf5." FORCE) +else() + set(NetCDF_PARALLEL FALSE CACHE STRING "NetCDF has no parallel IO capability." FORCE) +endif() + +## Finalize find_package +include(FindPackageHandleStandardArgs) + +if(NOT NetCDF_FOUND OR _new_search_components) + find_package_handle_standard_args( ${CMAKE_FIND_PACKAGE_NAME} + REQUIRED_VARS NetCDF_INCLUDE_DIRS NetCDF_LIBRARIES + VERSION_VAR NetCDF_VERSION + HANDLE_COMPONENTS ) +endif() + +foreach( _comp IN LISTS _search_components ) + if( NetCDF_${_comp}_FOUND ) + #Record found components to avoid duplication in NetCDF_LIBRARIES for static libraries + set(NetCDF_${_comp}_FOUND ${NetCDF_${_comp}_FOUND} CACHE BOOL "NetCDF ${_comp} Found" FORCE) + #Set a per-package, per-component found variable to communicate between multiple calls to find_package() + set(${PROJECT_NAME}_NetCDF_${_comp}_FOUND True) + endif() +endforeach() + +if( ${CMAKE_FIND_PACKAGE_NAME}_FOUND AND NOT ${CMAKE_FIND_PACKAGE_NAME}_FIND_QUIETLY AND _new_search_components) + message( STATUS "Find${CMAKE_FIND_PACKAGE_NAME} defines targets:" ) + message( STATUS " - NetCDF_VERSION [${NetCDF_VERSION}]") + message( STATUS " - NetCDF_PARALLEL [${NetCDF_PARALLEL}]") + foreach( _comp IN LISTS _new_search_components ) + string( TOUPPER "${_comp}" _COMP ) + message( STATUS " - NetCDF_${_comp}_CONFIG_EXECUTABLE [${NetCDF_${_comp}_CONFIG_EXECUTABLE}]") + if( ${CMAKE_FIND_PACKAGE_NAME}_${_arg_${_COMP}}_FOUND ) + get_filename_component(_root ${NetCDF_${_comp}_INCLUDE_DIR}/.. ABSOLUTE) + if( NetCDF_${_comp}_LIBRARY_SHARED ) + message( STATUS " - NetCDF::NetCDF_${_comp} [SHARED] [Root: ${_root}] Lib: ${NetCDF_${_comp}_LIBRARY} ") + else() + message( STATUS " - NetCDF::NetCDF_${_comp} [STATIC] [Root: ${_root}] Lib: ${NetCDF_${_comp}_LIBRARY} ") + endif() + endif() + endforeach() +endif() + +foreach( _prefix NetCDF NetCDF4 NETCDF NETCDF4 ${CMAKE_FIND_PACKAGE_NAME} ) + set( ${_prefix}_INCLUDE_DIRS ${NetCDF_INCLUDE_DIRS} ) + set( ${_prefix}_LIBRARIES ${NetCDF_LIBRARIES}) + set( ${_prefix}_VERSION ${NetCDF_VERSION} ) + set( ${_prefix}_FOUND ${${CMAKE_FIND_PACKAGE_NAME}_FOUND} ) + set( ${_prefix}_CONFIG_EXECUTABLE ${NetCDF_CONFIG_EXECUTABLE} ) + set( ${_prefix}_PARALLEL ${NetCDF_PARALLEL} ) + + foreach( _comp ${_search_components} ) + string( TOUPPER "${_comp}" _COMP ) + set( _arg_comp ${_arg_${_COMP}} ) + set( ${_prefix}_${_comp}_FOUND ${${CMAKE_FIND_PACKAGE_NAME}_${_arg_comp}_FOUND} ) + set( ${_prefix}_${_COMP}_FOUND ${${CMAKE_FIND_PACKAGE_NAME}_${_arg_comp}_FOUND} ) + set( ${_prefix}_${_arg_comp}_FOUND ${${CMAKE_FIND_PACKAGE_NAME}_${_arg_comp}_FOUND} ) + + set( ${_prefix}_${_comp}_LIBRARIES ${NetCDF_${_comp}_LIBRARIES} ) + set( ${_prefix}_${_COMP}_LIBRARIES ${NetCDF_${_comp}_LIBRARIES} ) + set( ${_prefix}_${_arg_comp}_LIBRARIES ${NetCDF_${_comp}_LIBRARIES} ) + + set( ${_prefix}_${_comp}_INCLUDE_DIRS ${NetCDF_${_comp}_INCLUDE_DIRS} ) + set( ${_prefix}_${_COMP}_INCLUDE_DIRS ${NetCDF_${_comp}_INCLUDE_DIRS} ) + set( ${_prefix}_${_arg_comp}_INCLUDE_DIRS ${NetCDF_${_comp}_INCLUDE_DIRS} ) + endforeach() +endforeach() diff --git a/cmake/FindPIO.cmake b/cmake/FindPIO.cmake new file mode 100644 index 000000000..37d6d31f4 --- /dev/null +++ b/cmake/FindPIO.cmake @@ -0,0 +1,209 @@ +# FindPIO.cmake +# +# Copyright UCAR 2020 +# Copyright NOAA/NWS/NCEP/EMC 2020 +# +# Find PIO: A high-level Parallel I/O Library for structured grid applications +# https://github.com/NCAR/ParallelIO +# +# Components available for query: +# C - Has C support +# Fortran - Has Fortran support +# SHARED - Has shared targets +# STATIC - Has static targets +# +# Variables provided: +# PIO_FOUND - True if PIO was found +# PIO_C_FOUND - True if PIO C support was found +# PIO_Fortran_FOUND - True if PIO Fortran support was found +# PIO_VERSION - Version of installed PIO +# +# Targets provided: +# PIO::PIO_C - C interface target aliased to SHARED|STATIC as requested or to shared libraries if available else static libraries +# PIO::PIO_Fortran - Fortran interface target aliases to SHARED|STATIC as requested or to shared libraries if available else static libraries +# +# To control finding of this package, set PIO_ROOT environment variable to the full path to the prefix +# under which PIO was installed (e.g., /usr/local) + +set( _search_components ) +set( _search_library_type ) +foreach( _comp ${${CMAKE_FIND_PACKAGE_NAME}_FIND_COMPONENTS} ) + if( _comp MATCHES "^(STATIC|SHARED)$" ) + list( APPEND _search_library_type ${_comp} ) + else() + list( APPEND _search_components ${_comp} ) + endif() +endforeach() +set( ${CMAKE_FIND_PACKAGE_NAME}_FIND_COMPONENTS ${_search_components} ) + +# If no COMPONENTS are requested, seach both C and Fortran +if( NOT _search_components ) + list( APPEND _search_components C Fortran ) +endif() + +# Ensure there is only one type of library being requested +if( _search_library_type ) + list( LENGTH _search_library_type _len) + if( _len GREATER 1 ) + message(FATAL_ERROR "User requesting both STATIC and SHARED is not permissible") + endif() + unset(_len) +endif() + +## Find libraries and paths, and determine found components +find_path(PIO_INCLUDE_DIR NAMES pio.h HINTS "${PIO_PREFIX}" PATH_SUFFIXES include include/pio) +if(PIO_INCLUDE_DIR) + string(REGEX REPLACE "/include(/.+)?" "" PIO_PREFIX ${PIO_INCLUDE_DIR}) + set(PIO_PREFIX ${PIO_PREFIX} CACHE STRING "") + find_path(PIO_MODULE_DIR NAMES pio.mod PATHS "${PIO_PREFIX}" + PATH_SUFFIXES include include/pio lib/pio/module module module/pio NO_DEFAULT_PATH) + if(APPLE) + set(_SHARED_LIB_EXT dylib) + else() + set(_SHARED_LIB_EXT so) + endif() + find_library(PIO_C_STATIC_LIB libpioc.a PATHS "${PIO_PREFIX}" PATH_SUFFIXES lib lib64 NO_DEFAULT_PATH) + find_library(PIO_C_SHARED_LIB libpioc.${_SHARED_LIB_EXT} PATHS "${PIO_PREFIX}" PATH_SUFFIXES lib lib64 NO_DEFAULT_PATH) + find_library(PIO_Fortran_STATIC_LIB libpiof.a PATHS "${PIO_PREFIX}" PATH_SUFFIXES lib lib64 NO_DEFAULT_PATH) + find_library(PIO_Fortran_SHARED_LIB libpiof.${_SHARED_LIB_EXT} PATHS "${PIO_PREFIX}" PATH_SUFFIXES lib lib64 NO_DEFAULT_PATH) + unset(_SHARED_LIB_EXT) + #Check for Fortran components + if(PIO_MODULE_DIR) + if(PIO_Fortran_STATIC_LIB) + set(PIO_Fortran_STATIC_FOUND 1) + endif() + if(PIO_Fortran_SHARED_LIB) + set(PIO_Fortran_SHARED_FOUND 1) + endif() + endif() + #Check for C components + if(PIO_C_STATIC_LIB) + set(PIO_C_STATIC_FOUND 1) + endif() + if(PIO_C_SHARED_LIB) + set(PIO_C_SHARED_FOUND 1) + endif() +endif() +## Debugging output +message(DEBUG "[FindPIO] PIO_INCLUDE_DIR: ${PIO_INCLUDE_DIR}") +message(DEBUG "[FindPIO] PIO_PREFIX: ${PIO_PREFIX}") +message(DEBUG "[FindPIO] PIO_MODULE_DIR: ${PIO_MODULE_DIR}") +message(DEBUG "[FindPIO] PIO_C_STATIC_LIB: ${PIO_C_STATIC_LIB}") +message(DEBUG "[FindPIO] PIO_C_SHARED_LIB: ${PIO_C_SHARED_LIB}") +message(DEBUG "[FindPIO] PIO_C_SHARED_FOUND: ${PIO_C_SHARED_FOUND}") +message(DEBUG "[FindPIO] PIO_C_STATIC_FOUND: ${PIO_C_STATIC_FOUND}") +message(DEBUG "[FindPIO] PIO_Fortran_STATIC_LIB: ${PIO_Fortran_STATIC_LIB}") +message(DEBUG "[FindPIO] PIO_Fortran_SHARED_LIB: ${PIO_Fortran_SHARED_LIB}") +message(DEBUG "[FindPIO] PIO_Fortran_SHARED_FOUND: ${PIO_Fortran_SHARED_FOUND}") +message(DEBUG "[FindPIO] PIO_Fortran_STATIC_FOUND: ${PIO_Fortran_STATIC_FOUND}") + +## Create targets +set(_new_components) +# PIO_C_STATIC imported interface target +if(PIO_C_STATIC_FOUND AND NOT TARGET PIO_C_STATIC) + add_library(PIO_C_STATIC INTERFACE IMPORTED) + set_target_properties(PIO_C_STATIC PROPERTIES + INTERFACE_INCLUDE_DIRECTORIES ${PIO_INCLUDE_DIR} + INTERFACE_LINK_LIBRARIES ${PIO_C_STATIC_LIB} + IMPORTED_GLOBAL True ) + set(_new_components 1) +endif() +# PIO_C_SHARED imported interface target +if(PIO_C_SHARED_FOUND AND NOT TARGET PIO_C_SHARED) + add_library(PIO_C_SHARED INTERFACE IMPORTED) + set_target_properties(PIO_C_SHARED PROPERTIES + INTERFACE_INCLUDE_DIRECTORIES ${PIO_INCLUDE_DIR} + INTERFACE_LINK_LIBRARIES ${PIO_C_SHARED_LIB} + IMPORTED_GLOBAL True ) + set(_new_components 1) +endif() +# PIO_Fortran_STATIC imported interface target +if(PIO_Fortran_STATIC_FOUND AND NOT TARGET PIO_Fortran_STATIC) + add_library(PIO_Fortran_STATIC INTERFACE IMPORTED) + set_target_properties(PIO_Fortran_STATIC PROPERTIES + INTERFACE_INCLUDE_DIRECTORIES ${PIO_INCLUDE_DIR} + INTERFACE_LINK_LIBRARIES ${PIO_Fortran_STATIC_LIB} + IMPORTED_GLOBAL True ) + if(PIO_MODULE_DIR AND NOT PIO_MODULE_DIR STREQUAL PIO_INCLUDE_DIR ) + set_property(TARGET PIO_Fortran_STATIC APPEND PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${PIO_MODULE_DIR}) + endif() + set(_new_components 1) + target_link_libraries(PIO_Fortran_STATIC INTERFACE PIO_C_STATIC) +endif() +# PIO_Fortran_SHARED imported interface target +if(PIO_Fortran_SHARED_FOUND AND NOT TARGET PIO_Fortran_SHARED) + add_library(PIO_Fortran_SHARED INTERFACE IMPORTED) + set_target_properties(PIO_Fortran_SHARED PROPERTIES + INTERFACE_INCLUDE_DIRECTORIES ${PIO_INCLUDE_DIR} + INTERFACE_LINK_LIBRARIES ${PIO_Fortran_SHARED_LIB} + IMPORTED_GLOBAL True ) + if(PIO_MODULE_DIR AND NOT PIO_MODULE_DIR STREQUAL PIO_INCLUDE_DIR ) + set_property(TARGET PIO_Fortran_SHARED APPEND PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${PIO_MODULE_DIR}) + endif() + target_link_libraries(PIO_Fortran_SHARED INTERFACE PIO_C_SHARED) + set(_new_components 1) +endif() + +if( _search_library_type MATCHES "^(SHARED)$" ) + if( TARGET PIO_C_SHARED ) + add_library(PIO::PIO_C ALIAS PIO_C_SHARED) + set(PIO_C_FOUND 1) + endif() + if( TARGET PIO_Fortran_SHARED ) + add_library(PIO::PIO_Fortran ALIAS PIO_Fortran_SHARED) + set(PIO_Fortran_FOUND 1) + endif() +elseif( _search_library_type MATCHES "^(STATIC)$" ) + if( TARGET PIO_C_STATIC ) + add_library(PIO::PIO_C ALIAS PIO_C_STATIC) + set(PIO_C_FOUND 1) + endif() + if( TARGET PIO_Fortran_STATIC ) + add_library(PIO::PIO_Fortran ALIAS PIO_Fortran_STATIC) + set(PIO_Fortran_FOUND 1) + endif() +else() + if( TARGET PIO_C_SHARED ) + add_library(PIO::PIO_C ALIAS PIO_C_SHARED) + set(PIO_C_FOUND 1) + elseif( TARGET PIO_C_STATIC ) + add_library(PIO::PIO_C ALIAS PIO_C_STATIC) + set(PIO_C_FOUND 1) + endif() + if( TARGET PIO_Fortran_SHARED ) + add_library(PIO::PIO_Fortran ALIAS PIO_Fortran_SHARED) + set(PIO_Fortran_FOUND 1) + elseif( TARGET PIO_Fortran_STATIC ) + add_library(PIO::PIO_Fortran ALIAS PIO_Fortran_STATIC) + set(PIO_Fortran_FOUND 1) + endif() +endif() + +## Check package has been found correctly +include(FindPackageHandleStandardArgs) +find_package_handle_standard_args( + PIO + REQUIRED_VARS + PIO_PREFIX + PIO_INCLUDE_DIR + HANDLE_COMPONENTS +) +message(DEBUG "[FindPIO] PIO_FOUND: ${PIO_FOUND}") + +## Print status +if(${CMAKE_FIND_PACKAGE_NAME}_FOUND AND NOT ${CMAKE_FIND_PACKAGE_NAME}_FIND_QUIETLY AND _new_components) + message( STATUS "Find${CMAKE_FIND_PACKAGE_NAME}:" ) + message( STATUS " - ${CMAKE_FIND_PACKAGE_NAME}_PREFIX [${${CMAKE_FIND_PACKAGE_NAME}_PREFIX}]") + set(_found_comps) + foreach( _comp ${_search_components} ) + if( ${CMAKE_FIND_PACKAGE_NAME}_${_comp}_FOUND ) + list(APPEND _found_comps ${_comp}) + endif() + endforeach() + message( STATUS " - ${CMAKE_FIND_PACKAGE_NAME} Components Found: ${_found_comps}") + unset(_found_comps) +endif() +unset(_new_components) +unset(_search_components) +unset(_search_library_type) +unset(_library_type) From b1b3f825f5ff6e1044d636cfaf93327d5373f611 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 6 Dec 2024 11:37:04 +1100 Subject: [PATCH 07/32] rm OM3 names --- cmake/CMakeLists.txt | 43 ++++++++++++++++++++++--------------------- 1 file changed, 22 insertions(+), 21 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 0c94c45a9..6f8891cbd 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -39,9 +39,11 @@ else() message(WARNING "C compiler with ID ${CMAKE_C_COMPILER_ID} will be used with CMake default options") endif() -add_compile_definitions( - CESMCOUPLED -) +if (CESMCOUPLED) + add_compile_definitions( + CESMCOUPLED + ) +endif() ## Fortran modules path; currently this is simply set to be the include dir set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} @@ -57,30 +59,29 @@ find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) ### Targets ## CICE library -add_fortran_library(OM3_cice mod STATIC) -add_library(AccessOM3::cice ALIAS OM3_cice) -target_compile_definitions(OM3_cice PRIVATE FORTRANUNDERSCORE ncdf) -if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") - target_compile_definitions(OM3_cice PRIVATE USE_NETCDF) +add_fortran_library(cicelib mod STATIC) +target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) +if(CICE6_IO MATCHES "^(NetCDF|PIO)$") + target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() -target_link_libraries(OM3_cice +target_link_libraries(cicelib PUBLIC esmf PRIVATE AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing AccessOM3::cdeps-common ) if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") - target_link_libraries(OM3_cice PRIVATE NetCDF::NetCDF_Fortran) + target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) if(OM3_CICE_IO MATCHES "PIO") - target_link_libraries(OM3_cice PRIVATE PIO::PIO_Fortran) + target_link_libraries(cicelib PRIVATE PIO::PIO_Fortran) endif() endif() if(OpenMP_Fortran_FOUND) - target_link_libraries(OM3_cice PRIVATE OpenMP::OpenMP_Fortran) + target_link_libraries(cicelib PRIVATE OpenMP::OpenMP_Fortran) endif() set(CICE_CORE "${CMAKE_SOURCE_DIR}/../cicecore") set(ICEPACK "${CMAKE_SOURCE_DIR}/../icepack") -target_sources(OM3_cice PRIVATE +target_sources(cicelib PRIVATE # Shared List: ${CICE_CORE}/shared/ice_arrays_column.F90 ${CICE_CORE}/shared/ice_calendar.F90 @@ -184,7 +185,7 @@ target_sources(OM3_cice PRIVATE ) if(OM3_LIB_INSTALL) - target_sources(OM3_cice PRIVATE + target_sources(cicelib PRIVATE # NUOPC CMEPS driver ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 ${CICE_CORE}/drivers/nuopc/cmeps/CICE_InitMod.F90 @@ -201,18 +202,18 @@ endif() # Select IO source files based on CICE_IO if(OM3_CICE_IO MATCHES "NetCDF") - target_sources(OM3_cice PRIVATE + target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_restart.F90 ) elseif(OM3_CICE_IO MATCHES "PIO") - target_sources(OM3_cice PRIVATE + target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_pio.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_restart.F90 ) elseif(OM3_CICE_IO MATCHES "Binary") - target_sources(OM3_cice PRIVATE + target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_restart.F90 ) @@ -222,19 +223,19 @@ endif() ## Library if(OM3_LIB_INSTALL) - set_target_properties(OM3_cice PROPERTIES + set_target_properties(cicelib PROPERTIES OUTPUT_NAME access-cice EXPORT_NAME cice ) - install(TARGETS OM3_cice + install(TARGETS cicelib EXPORT AccessOM3cice_Targets LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_RunTime NAMELINK_COMPONENT AccessOM3_Development ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_Development ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake - target_include_directories(OM3_cice PUBLIC "$") - get_target_property(cice_moddir OM3_cice Fortran_MODULE_DIRECTORY) + target_include_directories(cicelib PUBLIC "$") + get_target_property(cice_moddir cicelib Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod DESTINATION ${CMAKE_INSTALL_MODULEDIR}/CICE COMPONENT AccessOM3_Development From f258a4caeab3e3205f187598211c69e945786f04 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 6 Dec 2024 14:28:53 +1100 Subject: [PATCH 08/32] only find PIO when needed --- cmake/CMakeLists.txt | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 6f8891cbd..8665492e4 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -54,23 +54,24 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} find_package(Access3Share) find_package(FoX 4.1.2 REQUIRED) find_package(NetCDF 4.7.3 REQUIRED Fortran) -find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) - +if(CICE_IO MATCHES "PIO") + find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) +endif() ### Targets ## CICE library add_fortran_library(cicelib mod STATIC) target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) -if(CICE6_IO MATCHES "^(NetCDF|PIO)$") +if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() target_link_libraries(cicelib PUBLIC esmf PRIVATE AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing AccessOM3::cdeps-common ) -if(OM3_CICE_IO MATCHES "^(NetCDF|PIO)$") +if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) - if(OM3_CICE_IO MATCHES "PIO") + if(CICE_IO MATCHES "PIO") target_link_libraries(cicelib PRIVATE PIO::PIO_Fortran) endif() endif() @@ -201,18 +202,18 @@ if(OM3_LIB_INSTALL) endif() # Select IO source files based on CICE_IO -if(OM3_CICE_IO MATCHES "NetCDF") +if(CICE_IO MATCHES "NetCDF") target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_netcdf/ice_restart.F90 ) -elseif(OM3_CICE_IO MATCHES "PIO") +elseif(CICE_IO MATCHES "PIO") target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_pio.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_pio2/ice_restart.F90 ) -elseif(OM3_CICE_IO MATCHES "Binary") +elseif(CICE_IO MATCHES "Binary") target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_history_write.F90 ${CICE_CORE}/cicedyn/infrastructure/io/io_binary/ice_restart.F90 @@ -222,7 +223,7 @@ endif() ### Install and Export ## Library -if(OM3_LIB_INSTALL) +if(ACCESS3_LIB_INSTALL) set_target_properties(cicelib PROPERTIES OUTPUT_NAME access-cice EXPORT_NAME cice From f6d3e81c58df33cd86b6819904a498ce4e2017ee Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 6 Dec 2024 14:35:24 +1100 Subject: [PATCH 09/32] only find deps when needed --- cmake/CMakeLists.txt | 28 ++++++++++++++++------------ 1 file changed, 16 insertions(+), 12 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 8665492e4..e968aaaeb 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -51,9 +51,13 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} "Fortran module installation path (Not a cmake native variable)" ) -find_package(Access3Share) -find_package(FoX 4.1.2 REQUIRED) -find_package(NetCDF 4.7.3 REQUIRED Fortran) +if(ACCESS3_LIB_INSTALL) + find_package(Access3Share) + find_package(FoX 4.1.2 REQUIRED) +endif() +if(CICE_IO MATCHES "^(NetCDF|PIO)$") + find_package(NetCDF 4.7.3 REQUIRED Fortran) +endif() if(CICE_IO MATCHES "PIO") find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) endif() @@ -67,7 +71,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") endif() target_link_libraries(cicelib PUBLIC esmf - PRIVATE AccessOM3::nuopc_cap_share AccessOM3::share AccessOM3::timing AccessOM3::cdeps-common + PRIVATE Access3::nuopc_cap_share Access3::share Access3::timing Access3::cdeps-common ) if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) @@ -185,7 +189,7 @@ target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_timers.F90 ) -if(OM3_LIB_INSTALL) +if(ACCESS3_LIB_INSTALL) target_sources(cicelib PRIVATE # NUOPC CMEPS driver ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 @@ -229,9 +233,9 @@ if(ACCESS3_LIB_INSTALL) EXPORT_NAME cice ) install(TARGETS cicelib - EXPORT AccessOM3cice_Targets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_RunTime NAMELINK_COMPONENT AccessOM3_Development - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessOM3_Development + EXPORT Access3cice_Targets + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT Access3_RunTime NAMELINK_COMPONENT Access3_Development + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT Access3_Development ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake @@ -239,11 +243,11 @@ if(ACCESS3_LIB_INSTALL) get_target_property(cice_moddir cicelib Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod DESTINATION ${CMAKE_INSTALL_MODULEDIR}/CICE - COMPONENT AccessOM3_Development + COMPONENT Access3_Development ) - install(EXPORT AccessOM3cice_Targets - FILE AccessOM3ciceTargets.cmake - NAMESPACE AccessOM3:: + install(EXPORT Access3cice_Targets + FILE Access3ciceTargets.cmake + NAMESPACE Access3:: DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/CICE ) From 6448d7596323957c2261e5250161114f5c024784 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 6 Dec 2024 16:17:50 +1100 Subject: [PATCH 10/32] rm more deps from standalone build --- cmake/CMakeLists.txt | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index e968aaaeb..19102b09f 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -69,10 +69,12 @@ target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() -target_link_libraries(cicelib - PUBLIC esmf - PRIVATE Access3::nuopc_cap_share Access3::share Access3::timing Access3::cdeps-common -) +if(ACCESS3_LIB_INSTALL) + target_link_libraries(cicelib + PUBLIC esmf + PRIVATE Access3Share::nuopc_cap_share Access3Share::share Access3Share::timing Access3Share::cdeps-common + ) +endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) if(CICE_IO MATCHES "PIO") From 1b751813708bed7759d4f5b7f64a05d8c4d81cf8 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Mon, 13 Jan 2025 14:52:56 +1100 Subject: [PATCH 11/32] building access cice library --- cmake/AccessCiceCmeps.cmake.in | 9 +++ cmake/CMakeLists.txt | 107 +++++++++++++++++++++----- cmake/FindESMF.cmake | 135 +++++++++++++++++++++++++++++++++ cmake/FindFoX.cmake | 56 -------------- 4 files changed, 233 insertions(+), 74 deletions(-) create mode 100644 cmake/AccessCiceCmeps.cmake.in create mode 100755 cmake/FindESMF.cmake delete mode 100644 cmake/FindFoX.cmake diff --git a/cmake/AccessCiceCmeps.cmake.in b/cmake/AccessCiceCmeps.cmake.in new file mode 100644 index 000000000..dabecdd91 --- /dev/null +++ b/cmake/AccessCiceCmeps.cmake.in @@ -0,0 +1,9 @@ +@PACKAGE_INIT@ + + +find_package(NetCDF 4.7.3 REQUIRED Fortran) +find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) + +include("${CMAKE_CURRENT_LIST_DIR}/AccessCiceCmepsTargets.cmake") + +check_required_components(AccessCiceCmeps) \ No newline at end of file diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 19102b09f..70db3deaf 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -4,13 +4,35 @@ cmake_minimum_required(VERSION 3.18) # Basic project definition # #]==============================================================================] -project(CICE6 DESCRIPTION "CICE6" LANGUAGES C Fortran) +project(CICE + DESCRIPTION "CICE Sea Ice Model" + HOMEPAGE_URL https://github.com/ciCE-Consortium/cice + LANGUAGES C Fortran) + +#[==============================================================================[ +# Options # +#]==============================================================================] + +# Build options +option(ACCESS3_LIB_INSTALL "Instal ACCESS3 libraries" OFF) +option(CICE_IO "CICE IO Method" "Binary") +option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) +# openmp ? + +message(STATUS "Build options") +message(STATUS " - ACCESS3_LIB_INSTALL ${ACCESS3_LIB_INSTALL}") +message(STATUS " - CICE_IO ${CICE_IO}") +message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") + +#[==============================================================================[ +# Project configuration # +#]==============================================================================] list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}) +include(CMakePackageConfigHelpers) include(GNUInstallDirs) include(FortranLib) - # Common compiler flags and definitions if(CMAKE_Fortran_COMPILER_ID MATCHES "GNU") set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -fbacktrace -fconvert=big-endian -ffree-line-length-none -ffixed-line-length-none") @@ -51,22 +73,36 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} "Fortran module installation path (Not a cmake native variable)" ) +#[==============================================================================[ +# External packages # +#]==============================================================================] + if(ACCESS3_LIB_INSTALL) - find_package(Access3Share) - find_package(FoX 4.1.2 REQUIRED) + find_package(Access3Share) #should this have a REQUIRED? + find_package(ESMF 8.3.0 MODULE REQUIRED) +else() + find_package(MPI REQUIRED) endif() + if(CICE_IO MATCHES "^(NetCDF|PIO)$") find_package(NetCDF 4.7.3 REQUIRED Fortran) endif() if(CICE_IO MATCHES "PIO") find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) endif() + +#[==============================================================================[ +# Main definitions # +#]==============================================================================] + ### Targets ## CICE library add_fortran_library(cicelib mod STATIC) -target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) + if(CICE_IO MATCHES "^(NetCDF|PIO)$") + # which is this not just an "add_compile_definitions?" + target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() if(ACCESS3_LIB_INSTALL) @@ -81,6 +117,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_link_libraries(cicelib PRIVATE PIO::PIO_Fortran) endif() endif() + if(OpenMP_Fortran_FOUND) target_link_libraries(cicelib PRIVATE OpenMP::OpenMP_Fortran) endif() @@ -205,6 +242,13 @@ if(ACCESS3_LIB_INSTALL) ${CICE_CORE}/drivers/nuopc/cmeps/ice_scam.F90 ${CICE_CORE}/drivers/nuopc/cmeps/ice_shr_methods.F90 ) +else() + target_sources(cicelib PRIVATE + # CICE standalone + ${CICE_CORE}/drivers/standalone/cice/CICE_FinalMod.F90 + ${CICE_CORE}/drivers/standalone/cice/CICE_InitMod.F90 + ${CICE_CORE}/drivers/standalone/cice/CICE_RunMod.F90 + ) endif() # Select IO source files based on CICE_IO @@ -226,31 +270,58 @@ elseif(CICE_IO MATCHES "Binary") ) endif() -### Install and Export +#[==============================================================================[ +# Install or Export # +#]==============================================================================] -## Library if(ACCESS3_LIB_INSTALL) + ## Library set_target_properties(cicelib PROPERTIES - OUTPUT_NAME access-cice - EXPORT_NAME cice + OUTPUT_NAME access-cice-cmeps + EXPORT_NAME cice-cmeps ) install(TARGETS cicelib - EXPORT Access3cice_Targets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT Access3_RunTime NAMELINK_COMPONENT Access3_Development - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT Access3_Development + EXPORT AccessCiceCmepsTargets + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake target_include_directories(cicelib PUBLIC "$") get_target_property(cice_moddir cicelib Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod - DESTINATION ${CMAKE_INSTALL_MODULEDIR}/CICE - COMPONENT Access3_Development + DESTINATION ${CMAKE_INSTALL_MODULEDIR}/access-cice ) - install(EXPORT Access3cice_Targets - FILE Access3ciceTargets.cmake - NAMESPACE Access3:: - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/CICE + + # Make sure the dependencies get exported too + configure_package_config_file( + AccessCiceCmeps.cmake.in + "${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake" + INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps + ) + install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake ${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps + COMPONENT AccessCiceCmeps + ) + # install(EXPORT AccessCiceCmepsTargets + # FILE AccessCiceCmepsTargets.cmake + # NAMESPACE AccessCiceCmeps:: + # DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps + # ) +else() + set_target_properties(cicelib PROPERTIES + OUTPUT_NAME cicelib-standalone + EXPORT_NAME cicelib + ) + add_executable(CICE ${CICE_CORE}/drivers/standalone/cice/CICE.F90) + target_link_libraries(CICE PRIVATE cicelib) + + set_target_properties(CICE PROPERTIES + LINKER_LANGUAGE Fortran + OUTPUT_NAME cice ) + install(TARGETS CICE + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} + ) endif() diff --git a/cmake/FindESMF.cmake b/cmake/FindESMF.cmake new file mode 100755 index 000000000..5ba7003bd --- /dev/null +++ b/cmake/FindESMF.cmake @@ -0,0 +1,135 @@ +# - Try to find ESMF +# +# Requires setting ESMFMKFILE to the filepath of esmf.mk. If this is NOT set, +# then ESMF_FOUND will always be FALSE. If ESMFMKFILE exists, then ESMF_FOUND=TRUE +# and all ESMF makefile variables will be set in the global scope. Optionally, +# set ESMF_MKGLOBALS to a string list to filter makefile variables. For example, +# to globally scope only ESMF_LIBSDIR and ESMF_APPSDIR variables, use this CMake +# command in CMakeLists.txt: +# +# set(ESMF_MKGLOBALS "LIBSDIR" "APPSDIR") + + +# Add the ESMFMKFILE path to the cache if defined as system env variable +if(DEFINED ENV{ESMFMKFILE} AND NOT DEFINED ESMFMKFILE) + set(ESMFMKFILE $ENV{ESMFMKFILE} CACHE FILEPATH "Path to ESMF mk file") +endif() + +# If it's not explicitly set try to find esmf.mk file in default locations (ESMF_ROOT, CMAKE_PREFIX_PATH, etc) +if(NOT DEFINED ESMFMKFILE) + find_path(ESMFMKFILE_PATH esmf.mk PATH_SUFFIXES lib lib64) + if(ESMFMKFILE_PATH) + set(ESMFMKFILE ${ESMFMKFILE_PATH}/esmf.mk) + message(STATUS "Found esmf.mk file ${ESMFMKFILE}") + else() + message(STATUS "ESMFMKFILE not defined. This is the path to esmf.mk file. \ +Without this filepath, ESMF_FOUND will always be FALSE.") + endif() +endif() + +# Only parse the mk file if it is found +if(EXISTS ${ESMFMKFILE}) + # Read the mk file + file(STRINGS "${ESMFMKFILE}" esmfmkfile_contents) + # Parse each line in the mk file + foreach(str ${esmfmkfile_contents}) + # Only consider uncommented lines + string(REGEX MATCH "^[^#]" def ${str}) + # Line is not commented + if(def) + # Extract the variable name + string(REGEX MATCH "^[^=]+" esmf_varname ${str}) + # Extract the variable's value + string(REGEX MATCH "=.+$" esmf_vardef ${str}) + # Only for variables with a defined value + if(esmf_vardef) + # Get rid of the assignment string + string(SUBSTRING ${esmf_vardef} 1 -1 esmf_vardef) + # Remove whitespace + string(STRIP ${esmf_vardef} esmf_vardef) + # A string or single-valued list + if(NOT DEFINED ESMF_MKGLOBALS) + # Set in global scope + set(${esmf_varname} ${esmf_vardef}) + # Don't display by default in GUI + mark_as_advanced(esmf_varname) + else() # Need to filter global promotion + foreach(m ${ESMF_MKGLOBALS}) + string(FIND ${esmf_varname} ${m} match) + # Found the string + if(NOT ${match} EQUAL -1) + # Promote to global scope + set(${esmf_varname} ${esmf_vardef}) + # Don't display by default in the GUI + mark_as_advanced(esmf_varname) + # No need to search for the current string filter + break() + endif() + endforeach() + endif() + endif() + endif() + endforeach() + + # Construct ESMF_VERSION from ESMF_VERSION_STRING_GIT + # ESMF_VERSION_MAJOR and ESMF_VERSION_MINOR are defined in ESMFMKFILE + set(ESMF_VERSION 0) + set(ESMF_VERSION_PATCH ${ESMF_VERSION_REVISION}) + set(ESMF_BETA_RELEASE FALSE) + if(ESMF_VERSION_BETASNAPSHOT MATCHES "^('T')$") + set(ESMF_BETA_RELEASE TRUE) + string(REGEX REPLACE ".*beta_snapshot_*\([0-9]*\).*" "\\1" ESMF_BETA_SNAPSHOT "${ESMF_VERSION_STRING_GIT}") + message(STATUS "Detected ESMF Beta snapshot ${ESMF_BETA_SNAPSHOT}") + endif() + set(ESMF_VERSION "${ESMF_VERSION_MAJOR}.${ESMF_VERSION_MINOR}.${ESMF_VERSION_PATCH}") + + separate_arguments(ESMF_F90COMPILEPATHS NATIVE_COMMAND ${ESMF_F90COMPILEPATHS}) + foreach(ITEM ${ESMF_F90COMPILEPATHS}) + string(REGEX REPLACE "^-I" "" ITEM "${ITEM}") + list(APPEND tmp ${ITEM}) + endforeach() + set(ESMF_F90COMPILEPATHS ${tmp}) + + # Look for static library, if not found try dynamic library + find_library(esmf_lib NAMES libesmf.a PATHS ${ESMF_LIBSDIR}) + if(esmf_lib MATCHES "esmf_lib-NOTFOUND") + unset(esmf_lib) + message(STATUS "Static ESMF library not found, searching for dynamic library instead") + find_library(esmf_lib NAMES esmf_fullylinked libesmf.so PATHS ${ESMF_LIBSDIR}) + if(esmf_lib MATCHES "esmf_lib-NOTFOUND") + unset(esmf_lib) + message(STATUS "Neither the dynamic nor the static ESMF library was found") + else() + set(_library_type SHARED) + endif() + else() + set(_library_type STATIC) + endif() + + string(STRIP "${ESMF_F90ESMFLINKRPATHS} ${ESMF_F90ESMFLINKPATHS} ${ESMF_F90LINKPATHS} ${ESMF_F90LINKLIBS} ${ESMF_F90LINKOPTS}" ESMF_INTERFACE_LINK_LIBRARIES) + set(ESMF_LIBRARY_LOCATION ${esmf_lib}) + +else() + + message(WARNING "ESMFMKFILE ${ESMFMKFILE} does not exist") + +endif() + +## Finalize find_package +include(FindPackageHandleStandardArgs) + +find_package_handle_standard_args( + ${CMAKE_FIND_PACKAGE_NAME} + REQUIRED_VARS ESMF_LIBRARY_LOCATION + ESMF_INTERFACE_LINK_LIBRARIES + ESMF_F90COMPILEPATHS + VERSION_VAR ESMF_VERSION) + +## If ESMF is found create imported library target +if(ESMF_FOUND) + add_library(esmf ${_library_type} IMPORTED) + set_target_properties(esmf PROPERTIES + IMPORTED_LOCATION "${ESMF_LIBRARY_LOCATION}" + INTERFACE_INCLUDE_DIRECTORIES "${ESMF_F90COMPILEPATHS}" + INTERFACE_LINK_LIBRARIES "${ESMF_INTERFACE_LINK_LIBRARIES}") +endif() diff --git a/cmake/FindFoX.cmake b/cmake/FindFoX.cmake deleted file mode 100644 index b09bb35c9..000000000 --- a/cmake/FindFoX.cmake +++ /dev/null @@ -1,56 +0,0 @@ -# We will use pkgconfig to find the library -find_package(PkgConfig REQUIRED) - -## Prepare arguments to pass to pkg_search_module - -# QUIET -set(_quiet_arg) -if (FoX_FIND_QUIETLY) - list(APPEND _quiet_arg QUIET) -endif () - -# REQUIRED -set(_required_arg) -if (FoX_FIND_REQUIRED) - list(APPEND _required_arg REQUIRED) -endif () - -# Construct the moduleSpec to search for -if (DEFINED FoX_FIND_VERSION_RANGE) - # Can only parse the minimum requirement - list(APPEND PKG_MODULE_SPECS "fox>=${FoX_FIND_VERSION_MIN}") -elseif ({FoX_FIND_VERSION_EXACT) - # Requesting exact version - list(APPEND PKG_MODULE_SPECS "fox=${FoX_FIND_VERSION}") -elseif (DEFINED FoX_FIND_VERSION) - # Otherwise treat the request as minimum requirement - list(APPEND PKG_MODULE_SPECS "fox>=${FoX_FIND_VERSION}") -else () - # Fallthrough if no version is required - list(APPEND PKG_MODULE_SPECS "fox") -endif () - -## Call pkg-config -if (CMAKE_VERSION VERSION_LESS 3.28) - # https://gitlab.kitware.com/cmake/cmake/-/issues/25228 - set(ENV{PKG_CONFIG_ALLOW_SYSTEM_CFLAGS} 1) -endif () -if (CMAKE_VERSION VERSION_LESS 3.22) - # Back-porting - # https://gitlab.kitware.com/cmake/cmake/-/merge_requests/6345 - set(ENV{PKG_CONFIG_ALLOW_SYSTEM_LIBS} 1) -endif () -pkg_search_module(FoX - ${_required_arg} ${_quiet_arg} - IMPORTED_TARGET - ${PKG_MODULE_SPECS}) - -## Create alias if package was found by pkg-config -if (FoX_FOUND) - add_library(FoX::FoX ALIAS PkgConfig::FoX) -endif () - -# Sanitize local variables -set(PKG_MODULE_SPECS) -set(_quiet_arg) -set(_required_arg) From 6a784806a11c87f7c3ee6b5a008c088477a76173 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Mon, 13 Jan 2025 15:26:26 +1100 Subject: [PATCH 12/32] some tweaks --- cmake/AccessCiceCmeps.cmake.in | 5 +++-- cmake/CMakeLists.txt | 18 ++++++++++-------- 2 files changed, 13 insertions(+), 10 deletions(-) diff --git a/cmake/AccessCiceCmeps.cmake.in b/cmake/AccessCiceCmeps.cmake.in index dabecdd91..37ae4dfb6 100644 --- a/cmake/AccessCiceCmeps.cmake.in +++ b/cmake/AccessCiceCmeps.cmake.in @@ -1,8 +1,9 @@ @PACKAGE_INIT@ +include(CMakeFindDependencyMacro) -find_package(NetCDF 4.7.3 REQUIRED Fortran) -find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) +find_dependency(NetCDF) +find_dependency(PIO) include("${CMAKE_CURRENT_LIST_DIR}/AccessCiceCmepsTargets.cmake") diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 70db3deaf..572f26fc4 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -78,7 +78,7 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} #]==============================================================================] if(ACCESS3_LIB_INSTALL) - find_package(Access3Share) #should this have a REQUIRED? + find_package(Access3Share REQUIRED cdeps timing share nuopc_cap_share) find_package(ESMF 8.3.0 MODULE REQUIRED) else() find_package(MPI REQUIRED) @@ -299,15 +299,17 @@ if(ACCESS3_LIB_INSTALL) "${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake" INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps ) - install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake ${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake + + install(EXPORT AccessCiceCmepsTargets + FILE AccessCiceCmepsTargets.cmake + NAMESPACE AccessCiceCmeps:: DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps - COMPONENT AccessCiceCmeps ) - # install(EXPORT AccessCiceCmepsTargets - # FILE AccessCiceCmepsTargets.cmake - # NAMESPACE AccessCiceCmeps:: - # DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps - # ) + install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake ${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps + COMPONENT AccessCiceCmeps + ) + else() set_target_properties(cicelib PROPERTIES OUTPUT_NAME cicelib-standalone From 3bb7b8473918746f778aad86cfc8fe153bfe6eb2 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Tue, 14 Jan 2025 13:12:25 +1100 Subject: [PATCH 13/32] tweaks --- cmake/AccessCiceCmeps.cmake.in | 10 -------- cmake/CMakeLists.txt | 45 +++++++++++++++++----------------- cmake/CicelibConfig.cmake.in | 25 +++++++++++++++++++ 3 files changed, 48 insertions(+), 32 deletions(-) delete mode 100644 cmake/AccessCiceCmeps.cmake.in create mode 100644 cmake/CicelibConfig.cmake.in diff --git a/cmake/AccessCiceCmeps.cmake.in b/cmake/AccessCiceCmeps.cmake.in deleted file mode 100644 index 37ae4dfb6..000000000 --- a/cmake/AccessCiceCmeps.cmake.in +++ /dev/null @@ -1,10 +0,0 @@ -@PACKAGE_INIT@ - -include(CMakeFindDependencyMacro) - -find_dependency(NetCDF) -find_dependency(PIO) - -include("${CMAKE_CURRENT_LIST_DIR}/AccessCiceCmepsTargets.cmake") - -check_required_components(AccessCiceCmeps) \ No newline at end of file diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 572f26fc4..1c0699e03 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -112,14 +112,14 @@ if(ACCESS3_LIB_INSTALL) ) endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$") - target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) + target_link_libraries(cicelib PUBLIC NetCDF::NetCDF_Fortran) if(CICE_IO MATCHES "PIO") - target_link_libraries(cicelib PRIVATE PIO::PIO_Fortran) + target_link_libraries(cicelib PUBLIC PIO::PIO_Fortran) endif() endif() if(OpenMP_Fortran_FOUND) - target_link_libraries(cicelib PRIVATE OpenMP::OpenMP_Fortran) + target_link_libraries(cicelib PUBLIC OpenMP::OpenMP_Fortran) endif() set(CICE_CORE "${CMAKE_SOURCE_DIR}/../cicecore") @@ -277,37 +277,38 @@ endif() if(ACCESS3_LIB_INSTALL) ## Library set_target_properties(cicelib PROPERTIES - OUTPUT_NAME access-cice-cmeps - EXPORT_NAME cice-cmeps + OUTPUT_NAME access-cicelib + EXPORT_NAME cicelib ) install(TARGETS cicelib - EXPORT AccessCiceCmepsTargets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} + EXPORT CicelibTargets + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCiceCmeps ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake - target_include_directories(cicelib PUBLIC "$") + target_include_directories(cicelib PUBLIC "$") get_target_property(cice_moddir cicelib Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod - DESTINATION ${CMAKE_INSTALL_MODULEDIR}/access-cice + DESTINATION ${CMAKE_INSTALL_MODULEDIR}/cicelib + COMPONENT AccessCiceCmeps + ) + install(EXPORT CicelibTargets + FILE CicelibTargets.cmake + NAMESPACE Cicelib:: + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib ) # Make sure the dependencies get exported too configure_package_config_file( - AccessCiceCmeps.cmake.in - "${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake" - INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps - ) - - install(EXPORT AccessCiceCmepsTargets - FILE AccessCiceCmepsTargets.cmake - NAMESPACE AccessCiceCmeps:: - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps + CicelibConfig.cmake.in + "${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake" + INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib ) - install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake ${CMAKE_CURRENT_BINARY_DIR}/AccessCiceCmepsConfig.cmake - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/AccessCiceCmeps - COMPONENT AccessCiceCmeps + + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib + COMPONENT AccessCiceCmeps ) else() @@ -322,8 +323,8 @@ else() LINKER_LANGUAGE Fortran OUTPUT_NAME cice ) - install(TARGETS CICE RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} + COMPONENT IO_${CICE_IO} ) endif() diff --git a/cmake/CicelibConfig.cmake.in b/cmake/CicelibConfig.cmake.in new file mode 100644 index 000000000..e2ba97ab1 --- /dev/null +++ b/cmake/CicelibConfig.cmake.in @@ -0,0 +1,25 @@ +@PACKAGE_INIT@ + +include(CMakeFindDependencyMacro) + +# Available components +# set(_supported_components AccessCiceCmeps IO_PIO IO_NetCDF IO_Binary) + +set(_required_components ${Cicelib_FIND_COMPONENTS}) + +#if (IO_PIO IN_LIST _required_components) + # find_dependency(PIO) + # find_dependency(NetCDF) +#endif() + +if (IO_NetCDF IN_LIST _required_components) + find_dependency(NetCDF) +endif() + +list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) + +include("${CMAKE_CURRENT_LIST_DIR}/CicelibTargets.cmake") + +list(REMOVE_ITEM CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) + +# check_required_components(Cicelib) \ No newline at end of file From 93bafd54ccea1ef468b5cd533eebf06bdf6a4967 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Tue, 14 Jan 2025 14:41:34 +1100 Subject: [PATCH 14/32] Fix dependencies --- cmake/CMakeLists.txt | 18 +++++++++++++++--- cmake/CicelibConfig.cmake.in | 20 +++++++++++--------- 2 files changed, 26 insertions(+), 12 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 1c0699e03..a76e49140 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -112,9 +112,9 @@ if(ACCESS3_LIB_INSTALL) ) endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$") - target_link_libraries(cicelib PUBLIC NetCDF::NetCDF_Fortran) + target_link_libraries(cicelib PRIVATE NetCDF::NetCDF_Fortran) if(CICE_IO MATCHES "PIO") - target_link_libraries(cicelib PUBLIC PIO::PIO_Fortran) + target_link_libraries(cicelib PRIVATE PIO::PIO_Fortran) endif() endif() @@ -306,11 +306,23 @@ if(ACCESS3_LIB_INSTALL) INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib ) - install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib COMPONENT AccessCiceCmeps ) + if(CICE_IO MATCHES "NetCDF") + install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib + COMPONENT IO_NetCDF + ) + elseif(CICE_IO MATCHES "PIO") + install(FILES ${CMAKE_SOURCE_DIR}/FindNetCDF.cmake ${CMAKE_SOURCE_DIR}/FindPIO.cmake + DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib + COMPONENT IO_PIO + ) + endif() + else() set_target_properties(cicelib PROPERTIES OUTPUT_NAME cicelib-standalone diff --git a/cmake/CicelibConfig.cmake.in b/cmake/CicelibConfig.cmake.in index e2ba97ab1..1a73a8e6a 100644 --- a/cmake/CicelibConfig.cmake.in +++ b/cmake/CicelibConfig.cmake.in @@ -3,23 +3,25 @@ include(CMakeFindDependencyMacro) # Available components -# set(_supported_components AccessCiceCmeps IO_PIO IO_NetCDF IO_Binary) +# set(_supported_components AccessCiceCmeps IO_PIO IO_NetCDF) +# Request components set(_required_components ${Cicelib_FIND_COMPONENTS}) -#if (IO_PIO IN_LIST _required_components) - # find_dependency(PIO) - # find_dependency(NetCDF) -#endif() +# Check indirect dependencies +if (IO_PIO IN_LIST _required_components) + find_dependency(PIO REQUIRED COMPONENTS C Fortran) + find_dependency(NetCDF REQUIRED Fortran) +endif() if (IO_NetCDF IN_LIST _required_components) - find_dependency(NetCDF) + find_dependency(NetCDF REQUIRED Fortran) endif() +# Run the normal Targets.cmake list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) - include("${CMAKE_CURRENT_LIST_DIR}/CicelibTargets.cmake") - list(REMOVE_ITEM CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) -# check_required_components(Cicelib) \ No newline at end of file +# Check the requested components are valid +check_required_components(_required_components) \ No newline at end of file From e99c87d18b475e68028b94b1c40ab9152e62c49f Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 17 Jan 2025 15:09:43 +1100 Subject: [PATCH 15/32] tweak names --- cmake/CMakeLists.txt | 36 ++++++++++++++++++++++-------------- 1 file changed, 22 insertions(+), 14 deletions(-) diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index a76e49140..9ba9d42c3 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -13,16 +13,24 @@ project(CICE # Options # #]==============================================================================] -# Build options -option(ACCESS3_LIB_INSTALL "Instal ACCESS3 libraries" OFF) +message(STATUS "Build options") + option(CICE_IO "CICE IO Method" "Binary") -option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) -# openmp ? +if(NOT CICE_IO MATCHES "^(NetCDF|PIO|Binary)$") + message(FATAL_ERROR " CICE_IO ${CICE_IO} not valid, choose NetCDF|PIO|Binary") +else() + message(STATUS " - CICE_IO ${CICE_IO}") +endif() -message(STATUS "Build options") -message(STATUS " - ACCESS3_LIB_INSTALL ${ACCESS3_LIB_INSTALL}") -message(STATUS " - CICE_IO ${CICE_IO}") -message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") +option(ACCESS3_CICE "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) +message(STATUS " - ACCESS3_CICE ${ACCESS3_CICE}") + +if (ACCESS3_CICE) + option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) + message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") +endif() + +# openmp ? #[==============================================================================[ # Project configuration # @@ -77,7 +85,7 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} # External packages # #]==============================================================================] -if(ACCESS3_LIB_INSTALL) +if(ACCESS3_CICE) find_package(Access3Share REQUIRED cdeps timing share nuopc_cap_share) find_package(ESMF 8.3.0 MODULE REQUIRED) else() @@ -105,10 +113,10 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() -if(ACCESS3_LIB_INSTALL) +if(ACCESS3_CICE) target_link_libraries(cicelib PUBLIC esmf - PRIVATE Access3Share::nuopc_cap_share Access3Share::share Access3Share::timing Access3Share::cdeps-common + PRIVATE Access3::nuopc_cap_share Access3::share Access3::timing Access3::cdeps-common ) endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$") @@ -228,7 +236,7 @@ target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_timers.F90 ) -if(ACCESS3_LIB_INSTALL) +if(ACCESS3_CICE) target_sources(cicelib PRIVATE # NUOPC CMEPS driver ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 @@ -274,7 +282,7 @@ endif() # Install or Export # #]==============================================================================] -if(ACCESS3_LIB_INSTALL) +if(ACCESS3_CICE) ## Library set_target_properties(cicelib PROPERTIES OUTPUT_NAME access-cicelib @@ -295,7 +303,7 @@ if(ACCESS3_LIB_INSTALL) ) install(EXPORT CicelibTargets FILE CicelibTargets.cmake - NAMESPACE Cicelib:: + NAMESPACE Access3:: DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib ) From 06b34dd785ca75b5a70df48fe97752d3f6b2e2cc Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Wed, 22 Jan 2025 16:17:23 +1100 Subject: [PATCH 16/32] move cmake to configuration/scripts --- {cmake => configuration/scripts/cmake}/CMakeLists.txt | 4 ++-- {cmake => configuration/scripts/cmake}/CicelibConfig.cmake.in | 0 {cmake => configuration/scripts/cmake}/FindESMF.cmake | 0 {cmake => configuration/scripts/cmake}/FindNetCDF.cmake | 0 {cmake => configuration/scripts/cmake}/FindPIO.cmake | 0 {cmake => configuration/scripts/cmake}/FortranLib.cmake | 0 6 files changed, 2 insertions(+), 2 deletions(-) rename {cmake => configuration/scripts/cmake}/CMakeLists.txt (99%) rename {cmake => configuration/scripts/cmake}/CicelibConfig.cmake.in (100%) rename {cmake => configuration/scripts/cmake}/FindESMF.cmake (100%) rename {cmake => configuration/scripts/cmake}/FindNetCDF.cmake (100%) rename {cmake => configuration/scripts/cmake}/FindPIO.cmake (100%) rename {cmake => configuration/scripts/cmake}/FortranLib.cmake (100%) diff --git a/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt similarity index 99% rename from cmake/CMakeLists.txt rename to configuration/scripts/cmake/CMakeLists.txt index 9ba9d42c3..cde95ac57 100644 --- a/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -130,8 +130,8 @@ if(OpenMP_Fortran_FOUND) target_link_libraries(cicelib PUBLIC OpenMP::OpenMP_Fortran) endif() -set(CICE_CORE "${CMAKE_SOURCE_DIR}/../cicecore") -set(ICEPACK "${CMAKE_SOURCE_DIR}/../icepack") +set(CICE_CORE "${CMAKE_SOURCE_DIR}/../../../cicecore") +set(ICEPACK "${CMAKE_SOURCE_DIR}/../../../icepack") target_sources(cicelib PRIVATE # Shared List: diff --git a/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in similarity index 100% rename from cmake/CicelibConfig.cmake.in rename to configuration/scripts/cmake/CicelibConfig.cmake.in diff --git a/cmake/FindESMF.cmake b/configuration/scripts/cmake/FindESMF.cmake similarity index 100% rename from cmake/FindESMF.cmake rename to configuration/scripts/cmake/FindESMF.cmake diff --git a/cmake/FindNetCDF.cmake b/configuration/scripts/cmake/FindNetCDF.cmake similarity index 100% rename from cmake/FindNetCDF.cmake rename to configuration/scripts/cmake/FindNetCDF.cmake diff --git a/cmake/FindPIO.cmake b/configuration/scripts/cmake/FindPIO.cmake similarity index 100% rename from cmake/FindPIO.cmake rename to configuration/scripts/cmake/FindPIO.cmake diff --git a/cmake/FortranLib.cmake b/configuration/scripts/cmake/FortranLib.cmake similarity index 100% rename from cmake/FortranLib.cmake rename to configuration/scripts/cmake/FortranLib.cmake From 26ce3b044075e17a770ffe746913b89a9d755694 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 23 Jan 2025 15:38:49 +1100 Subject: [PATCH 17/32] seperate runtime and Development components --- configuration/scripts/cmake/CMakeLists.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index cde95ac57..6fec694a6 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -290,8 +290,8 @@ if(ACCESS3_CICE) ) install(TARGETS cicelib EXPORT CicelibTargets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCiceCmeps - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCiceCmeps_runtime NAMELINK_COMPONENT AccessCiceCmeps_Development + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} AccessCiceCmeps_Development ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake @@ -316,7 +316,7 @@ if(ACCESS3_CICE) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib - COMPONENT AccessCiceCmeps + COMPONENT AccessCiceCmeps_Development ) if(CICE_IO MATCHES "NetCDF") From 73f172098b51555d47fef5d14ac5dd4385ae4a2d Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 23 Jan 2025 16:10:19 +1100 Subject: [PATCH 18/32] fix names and IO dependency finding --- configuration/scripts/cmake/CMakeLists.txt | 8 ++++---- .../scripts/cmake/CicelibConfig.cmake.in | 17 ++++++++--------- 2 files changed, 12 insertions(+), 13 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 6fec694a6..be217aa16 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -290,8 +290,8 @@ if(ACCESS3_CICE) ) install(TARGETS cicelib EXPORT CicelibTargets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCiceCmeps_runtime NAMELINK_COMPONENT AccessCiceCmeps_Development - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} AccessCiceCmeps_Development + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICECmeps_runtime NAMELINK_COMPONENT AccessCICECmeps_Development + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICECmeps_Development ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake @@ -299,7 +299,7 @@ if(ACCESS3_CICE) get_target_property(cice_moddir cicelib Fortran_MODULE_DIRECTORY) install(FILES ${cice_moddir}/ice_comp_nuopc.mod DESTINATION ${CMAKE_INSTALL_MODULEDIR}/cicelib - COMPONENT AccessCiceCmeps + COMPONENT AccessCICECmeps_Development ) install(EXPORT CicelibTargets FILE CicelibTargets.cmake @@ -316,7 +316,7 @@ if(ACCESS3_CICE) install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib - COMPONENT AccessCiceCmeps_Development + COMPONENT AccessCICECmeps_Development ) if(CICE_IO MATCHES "NetCDF") diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index 1a73a8e6a..8d2f5c33a 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -1,22 +1,21 @@ @PACKAGE_INIT@ -include(CMakeFindDependencyMacro) - -# Available components -# set(_supported_components AccessCiceCmeps IO_PIO IO_NetCDF) - # Request components set(_required_components ${Cicelib_FIND_COMPONENTS}) + # Check indirect dependencies -if (IO_PIO IN_LIST _required_components) +set(CICE_IO @CICE_IO@) + +if(CICE_IO MATCHES "NetCDF") + find_dependency(NetCDF REQUIRED Fortran) +elseif(CICE_IO MATCHES "PIO") find_dependency(PIO REQUIRED COMPONENTS C Fortran) find_dependency(NetCDF REQUIRED Fortran) endif() -if (IO_NetCDF IN_LIST _required_components) - find_dependency(NetCDF REQUIRED Fortran) -endif() +# Request components +set(_required_components ${Cicelib_FIND_COMPONENTS}) # Run the normal Targets.cmake list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) From 13291168a636d83e09b7e116fae885aebf92a1a1 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 6 Feb 2025 10:12:47 +1100 Subject: [PATCH 19/32] possible better deps handling and allow CICE_DRIVER to be specified --- configuration/scripts/cmake/CMakeLists.txt | 52 ++++++++++++------- .../scripts/cmake/CicelibConfig.cmake.in | 4 +- 2 files changed, 37 insertions(+), 19 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index be217aa16..368cf4914 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -15,7 +15,10 @@ project(CICE message(STATUS "Build options") -option(CICE_IO "CICE IO Method" "Binary") +option(CICE_IO "CICE IO Method" OFF) +if (NOT CICE_IO) + set(CICE_IO "Binary") #set a default +endif() if(NOT CICE_IO MATCHES "^(NetCDF|PIO|Binary)$") message(FATAL_ERROR " CICE_IO ${CICE_IO} not valid, choose NetCDF|PIO|Binary") else() @@ -25,7 +28,18 @@ endif() option(ACCESS3_CICE "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) message(STATUS " - ACCESS3_CICE ${ACCESS3_CICE}") -if (ACCESS3_CICE) +#placeholder CICE_DRIVER option to allow for a nuopc/access driver in the future +option(CICE_DRIVER "CICE driver code to use" OFF) +if(NOT CICE_DRIVER) + if(ACCESS3_CICE) + set(CICE_DRIVER "nuopc/cmeps") + else() + set(CICE_DRIVER "standalone/cice") + endif() +endif() +message(STATUS " - CICE_DRIVER ${CICE_DRIVER}") + +if(ACCESS3_CICE) option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") endif() @@ -95,7 +109,7 @@ endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$") find_package(NetCDF 4.7.3 REQUIRED Fortran) endif() -if(CICE_IO MATCHES "PIO") +if(CICE_IO MATCHES "PIO" AND NOT TARGET PIO::PIO_Fortran) find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) endif() @@ -236,27 +250,29 @@ target_sources(cicelib PRIVATE ${CICE_CORE}/cicedyn/infrastructure/comm/mpi/ice_timers.F90 ) -if(ACCESS3_CICE) +if(CICE_DRIVER MATCHES "nuopc/cmeps") target_sources(cicelib PRIVATE # NUOPC CMEPS driver - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_FinalMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_InitMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/CICE_RunMod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/cice_wrapper_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_comp_nuopc.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_import_export.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_mesh_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_prescribed_mod.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_scam.F90 - ${CICE_CORE}/drivers/nuopc/cmeps/ice_shr_methods.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_FinalMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_InitMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_RunMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/cice_wrapper_mod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_comp_nuopc.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_import_export.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_mesh_mod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_prescribed_mod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_scam.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/ice_shr_methods.F90 ) -else() +elseif(CICE_DRIVER MATCHES "standalone/cice") target_sources(cicelib PRIVATE # CICE standalone - ${CICE_CORE}/drivers/standalone/cice/CICE_FinalMod.F90 - ${CICE_CORE}/drivers/standalone/cice/CICE_InitMod.F90 - ${CICE_CORE}/drivers/standalone/cice/CICE_RunMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_FinalMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_InitMod.F90 + ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_RunMod.F90 ) +else() + message(FATAL_ERROR "CICE_DRIVER: ${CICE_DRIVER} not supported, add to cmake") endif() # Select IO source files based on CICE_IO diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index 8d2f5c33a..fbf267814 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -10,7 +10,9 @@ set(CICE_IO @CICE_IO@) if(CICE_IO MATCHES "NetCDF") find_dependency(NetCDF REQUIRED Fortran) elseif(CICE_IO MATCHES "PIO") - find_dependency(PIO REQUIRED COMPONENTS C Fortran) + if (NOT TARGET PIO::PIO_Fortran) + find_dependency(PIO REQUIRED COMPONENTS C Fortran) + endif() find_dependency(NetCDF REQUIRED Fortran) endif() From 34539733f270ba9603653f6e615e823ffbc7ed97 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 13 Mar 2025 16:14:43 +1100 Subject: [PATCH 20/32] fp-model precise and rm duplicate line --- configuration/scripts/cmake/CMakeLists.txt | 2 +- configuration/scripts/cmake/CicelibConfig.cmake.in | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 368cf4914..8e4cda2d4 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -64,7 +64,7 @@ if(CMAKE_Fortran_COMPILER_ID MATCHES "GNU") set(CMAKE_Fortran_FLAGS_RELEASE "-O") set(CMAKE_Fortran_FLAGS_DEBUG "-g -Wall -Og -ffpe-trap=zero,overflow -fcheck=bounds") elseif(CMAKE_Fortran_COMPILER_ID MATCHES "Intel") - set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -qno-opt-dynamic-align -convert big_endian -assume byterecl -ftz -traceback -assume realloc_lhs -fp-model source") + set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS} -qno-opt-dynamic-align -convert big_endian -assume byterecl -ftz -traceback -assume realloc_lhs -fp-model precise") set(CMAKE_Fortran_FLAGS_RELEASE "-O2 -debug minimal") set(CMAKE_Fortran_FLAGS_DEBUG "-O0 -g -check uninit -check bounds -check pointers -fpe0 -check noarg_temp_created") else() diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index fbf267814..f81b32a7b 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -16,8 +16,6 @@ elseif(CICE_IO MATCHES "PIO") find_dependency(NetCDF REQUIRED Fortran) endif() -# Request components -set(_required_components ${Cicelib_FIND_COMPONENTS}) # Run the normal Targets.cmake list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) From 63ce71bf355a341f3adac751c8e236e17095277f Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 14 Mar 2025 17:10:08 +1100 Subject: [PATCH 21/32] openmp --- configuration/scripts/cmake/CMakeLists.txt | 19 +++++++++++++------ .../scripts/cmake/CicelibConfig.cmake.in | 3 +++ 2 files changed, 16 insertions(+), 6 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 8e4cda2d4..2cbe58c32 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -25,8 +25,10 @@ else() message(STATUS " - CICE_IO ${CICE_IO}") endif() -option(ACCESS3_CICE "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) +option(ACCESS3_CICE "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) +option(OPENMP "Enable OpenMP threading" OFF) message(STATUS " - ACCESS3_CICE ${ACCESS3_CICE}") +message(STATUS " - OPENMP ${OPENMP}") #placeholder CICE_DRIVER option to allow for a nuopc/access driver in the future option(CICE_DRIVER "CICE driver code to use" OFF) @@ -44,8 +46,6 @@ if(ACCESS3_CICE) message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") endif() -# openmp ? - #[==============================================================================[ # Project configuration # #]==============================================================================] @@ -106,6 +106,10 @@ else() find_package(MPI REQUIRED) endif() +if(OPENMP) + find_package(OpenMP REQUIRED COMPONENTS Fortran) +endif() + if(CICE_IO MATCHES "^(NetCDF|PIO)$") find_package(NetCDF 4.7.3 REQUIRED Fortran) endif() @@ -120,6 +124,10 @@ endif() ### Targets ## CICE library + +set(CICE_CORE "${CMAKE_SOURCE_DIR}/../../../cicecore") +set(ICEPACK "${CMAKE_SOURCE_DIR}/../../../icepack") + add_fortran_library(cicelib mod STATIC) if(CICE_IO MATCHES "^(NetCDF|PIO)$") @@ -140,12 +148,11 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") endif() endif() -if(OpenMP_Fortran_FOUND) +if(OPENMP) target_link_libraries(cicelib PUBLIC OpenMP::OpenMP_Fortran) endif() -set(CICE_CORE "${CMAKE_SOURCE_DIR}/../../../cicecore") -set(ICEPACK "${CMAKE_SOURCE_DIR}/../../../icepack") + target_sources(cicelib PRIVATE # Shared List: diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index f81b32a7b..de71c2ab3 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -16,6 +16,9 @@ elseif(CICE_IO MATCHES "PIO") find_dependency(NetCDF REQUIRED Fortran) endif() +if(@OPENMP@) + find_package(OpenMP REQUIRED) +endif() # Run the normal Targets.cmake list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}) From 1ab3709639811b222c922b1aa8550ea6c1bdf8e3 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Tue, 18 Mar 2025 11:37:25 +1100 Subject: [PATCH 22/32] explicitly link MPI in exe --- configuration/scripts/cmake/CMakeLists.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 2cbe58c32..3e2326be8 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -44,6 +44,8 @@ message(STATUS " - CICE_DRIVER ${CICE_DRIVER}") if(ACCESS3_CICE) option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") +elseif(CESMCOUPLED) + message(FATAL_ERROR "CESMCOUPLED not supported when ACCESS3_CICE=OFF") endif() #[==============================================================================[ @@ -360,7 +362,7 @@ else() EXPORT_NAME cicelib ) add_executable(CICE ${CICE_CORE}/drivers/standalone/cice/CICE.F90) - target_link_libraries(CICE PRIVATE cicelib) + target_link_libraries(CICE PRIVATE cicelib MPI::MPI_Fortran) set_target_properties(CICE PROPERTIES LINKER_LANGUAGE Fortran From 49d39780c1c68d857cc24d5824d2ce223413335f Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Tue, 18 Mar 2025 13:51:51 +1100 Subject: [PATCH 23/32] license --- configuration/scripts/cmake/CMakeLists.txt | 2 ++ configuration/scripts/cmake/CicelibConfig.cmake.in | 2 ++ configuration/scripts/cmake/FortranLib.cmake | 2 ++ 3 files changed, 6 insertions(+) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 3e2326be8..184ec9d6f 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -1,3 +1,5 @@ +# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. + cmake_minimum_required(VERSION 3.18) #[==============================================================================[ diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index de71c2ab3..adfa92631 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -1,3 +1,5 @@ +# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. + @PACKAGE_INIT@ # Request components diff --git a/configuration/scripts/cmake/FortranLib.cmake b/configuration/scripts/cmake/FortranLib.cmake index 08bcccbf8..7aaca6a66 100644 --- a/configuration/scripts/cmake/FortranLib.cmake +++ b/configuration/scripts/cmake/FortranLib.cmake @@ -1,3 +1,5 @@ +# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. + function(add_fortran_library LIB MOD_DIR) add_library(${LIB} ${ARGN}) From 73128cb4152a877ab84332863bf7dc6076a9fb62 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Tue, 18 Mar 2025 14:55:53 +1100 Subject: [PATCH 24/32] license --- configuration/scripts/cmake/CMakeLists.txt | 2 +- configuration/scripts/cmake/CicelibConfig.cmake.in | 2 +- configuration/scripts/cmake/FortranLib.cmake | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 184ec9d6f..f640e6b22 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. +# Copyright ACCESS-NRI and contributors. See the top-level LICENSE file for details. cmake_minimum_required(VERSION 3.18) diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index adfa92631..3605d5bca 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -1,4 +1,4 @@ -# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. +# Copyright ACCESS-NRI and contributors. See the top-level LICENSE file for details. @PACKAGE_INIT@ diff --git a/configuration/scripts/cmake/FortranLib.cmake b/configuration/scripts/cmake/FortranLib.cmake index 7aaca6a66..6eaec978b 100644 --- a/configuration/scripts/cmake/FortranLib.cmake +++ b/configuration/scripts/cmake/FortranLib.cmake @@ -1,4 +1,4 @@ -# Copyright ACCESS-NRI and contributors. See the top-level COPYRIGHT file for details. +# Copyright ACCESS-NRI and contributors. See the top-level LICENSE file for details. function(add_fortran_library LIB MOD_DIR) add_library(${LIB} ${ARGN}) From 87a1ec0d26bfd5ace24a5e76eab9fbe856196983 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Wed, 19 Mar 2025 15:09:49 +1100 Subject: [PATCH 25/32] updated FindESMF.cmake --- configuration/scripts/cmake/FindESMF.cmake | 181 ++++++++++++++------- 1 file changed, 120 insertions(+), 61 deletions(-) diff --git a/configuration/scripts/cmake/FindESMF.cmake b/configuration/scripts/cmake/FindESMF.cmake index 5ba7003bd..8dfb926ce 100755 --- a/configuration/scripts/cmake/FindESMF.cmake +++ b/configuration/scripts/cmake/FindESMF.cmake @@ -1,34 +1,81 @@ +# Earth System Modeling Framework + +# Copyright (c) 2002-2025 University Corporation for Atmospheric Research, +# Massachusetts Institute of Technology, Geophysical Fluid Dynamics Laboratory, +# University of Michigan, National Centers for Environmental Prediction, +# Los Alamos National Laboratory, Argonne National Laboratory, +# NASA Goddard Space Flight Center. +# All rights reserved. + +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to +# deal with the Software without restriction, including without limitation the +# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +# sell copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# 1. Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimers. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimers in the +# documentation and/or other materials provided with the distribution. +# 3. Neither the names of the organizations developing this software, nor +# the names of its contributors may be used to endorse or promote products +# derived from this Software without specific prior written permission. + +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS +# WITH THE SOFTWARE. + # - Try to find ESMF # -# Requires setting ESMFMKFILE to the filepath of esmf.mk. If this is NOT set, -# then ESMF_FOUND will always be FALSE. If ESMFMKFILE exists, then ESMF_FOUND=TRUE -# and all ESMF makefile variables will be set in the global scope. Optionally, -# set ESMF_MKGLOBALS to a string list to filter makefile variables. For example, -# to globally scope only ESMF_LIBSDIR and ESMF_APPSDIR variables, use this CMake -# command in CMakeLists.txt: +# Uses ESMFMKFILE to find the filepath of esmf.mk. If this is NOT set, then this +# module will attempt to find esmf.mk. If ESMFMKFILE exists, then +# ESMF_FOUND=TRUE and all ESMF makefile variables will be set in the global +# scope. Optionally, set ESMF_MKGLOBALS to a string list to filter makefile +# variables. For example, to globally scope only ESMF_LIBSDIR and ESMF_APPSDIR +# variables, use this CMake command in CMakeLists.txt: # # set(ESMF_MKGLOBALS "LIBSDIR" "APPSDIR") +# Set ESMFMKFILE as defined by system env variable. If it's not explicitly set +# try to find esmf.mk file in default locations (ESMF_ROOT, CMAKE_PREFIX_PATH, +# etc) -# Add the ESMFMKFILE path to the cache if defined as system env variable -if(DEFINED ENV{ESMFMKFILE} AND NOT DEFINED ESMFMKFILE) - set(ESMFMKFILE $ENV{ESMFMKFILE} CACHE FILEPATH "Path to ESMF mk file") -endif() +# - Common Usage +# +# Where to look for this FindESMF.cmake file +# list(APPEND CMAKE_MODULE_PATH "") +# is to be replaced with the directory for this file +# +# How to locate ESMF libraries and create target +# find_package(ESMF MODULE REQUIRED) +# is to be replaced with the minimum version required +# +# How to link targets +# target_link_libraries( PUBLIC ESMF::ESMF) +# is to be replaced with your CMake target -# If it's not explicitly set try to find esmf.mk file in default locations (ESMF_ROOT, CMAKE_PREFIX_PATH, etc) if(NOT DEFINED ESMFMKFILE) - find_path(ESMFMKFILE_PATH esmf.mk PATH_SUFFIXES lib lib64) - if(ESMFMKFILE_PATH) - set(ESMFMKFILE ${ESMFMKFILE_PATH}/esmf.mk) - message(STATUS "Found esmf.mk file ${ESMFMKFILE}") + if(NOT DEFINED ENV{ESMFMKFILE}) + find_path(ESMFMKFILE_PATH esmf.mk PATH_SUFFIXES lib lib64) + if(ESMFMKFILE_PATH) + set(ESMFMKFILE ${ESMFMKFILE_PATH}/esmf.mk) + message(STATUS "Found esmf.mk file ${ESMFMKFILE}") + endif() else() - message(STATUS "ESMFMKFILE not defined. This is the path to esmf.mk file. \ -Without this filepath, ESMF_FOUND will always be FALSE.") + set(ESMFMKFILE $ENV{ESMFMKFILE}) endif() endif() # Only parse the mk file if it is found if(EXISTS ${ESMFMKFILE}) + set(ESMFMKFILE ${ESMFMKFILE} CACHE FILEPATH "Path to esmf.mk file") + set(ESMF_FOUND TRUE CACHE BOOL "esmf.mk file found" FORCE) + # Read the mk file file(STRINGS "${ESMFMKFILE}" esmfmkfile_contents) # Parse each line in the mk file @@ -78,58 +125,70 @@ if(EXISTS ${ESMFMKFILE}) set(ESMF_BETA_RELEASE FALSE) if(ESMF_VERSION_BETASNAPSHOT MATCHES "^('T')$") set(ESMF_BETA_RELEASE TRUE) - string(REGEX REPLACE ".*beta_snapshot_*\([0-9]*\).*" "\\1" ESMF_BETA_SNAPSHOT "${ESMF_VERSION_STRING_GIT}") - message(STATUS "Detected ESMF Beta snapshot ${ESMF_BETA_SNAPSHOT}") + if(ESMF_VERSION_STRING_GIT MATCHES "^ESMF.*beta_snapshot") + set(ESMF_BETA_SNAPSHOT ${ESMF_VERSION_STRING_GIT}) + elseif(ESMF_VERSION_STRING_GIT MATCHES "^v.\..\..b") + set(ESMF_BETA_SNAPSHOT ${ESMF_VERSION_STRING_GIT}) + else() + set(ESMF_BETA_SNAPSHOT 0) + endif() + message(STATUS "Detected ESMF Beta snapshot: ${ESMF_BETA_SNAPSHOT}") endif() set(ESMF_VERSION "${ESMF_VERSION_MAJOR}.${ESMF_VERSION_MINOR}.${ESMF_VERSION_PATCH}") - separate_arguments(ESMF_F90COMPILEPATHS NATIVE_COMMAND ${ESMF_F90COMPILEPATHS}) - foreach(ITEM ${ESMF_F90COMPILEPATHS}) - string(REGEX REPLACE "^-I" "" ITEM "${ITEM}") - list(APPEND tmp ${ITEM}) - endforeach() - set(ESMF_F90COMPILEPATHS ${tmp}) - - # Look for static library, if not found try dynamic library - find_library(esmf_lib NAMES libesmf.a PATHS ${ESMF_LIBSDIR}) - if(esmf_lib MATCHES "esmf_lib-NOTFOUND") - unset(esmf_lib) - message(STATUS "Static ESMF library not found, searching for dynamic library instead") - find_library(esmf_lib NAMES esmf_fullylinked libesmf.so PATHS ${ESMF_LIBSDIR}) - if(esmf_lib MATCHES "esmf_lib-NOTFOUND") - unset(esmf_lib) - message(STATUS "Neither the dynamic nor the static ESMF library was found") - else() - set(_library_type SHARED) + # Find the ESMF library + if(USE_ESMF_STATIC_LIBS) + find_library(ESMF_LIBRARY_LOCATION NAMES libesmf.a PATHS ${ESMF_LIBSDIR} NO_DEFAULT_PATH) + if(ESMF_LIBRARY_LOCATION MATCHES "ESMF_LIBRARY_LOCATION-NOTFOUND") + message(WARNING "Static ESMF library (libesmf.a) not found in \ + ${ESMF_LIBSDIR}. Try setting USE_ESMF_STATIC_LIBS=OFF") + endif() + if(NOT TARGET ESMF::ESMF) + add_library(ESMF::ESMF STATIC IMPORTED) endif() else() - set(_library_type STATIC) + find_library(ESMF_LIBRARY_LOCATION NAMES esmf PATHS ${ESMF_LIBSDIR} NO_DEFAULT_PATH) + if(ESMF_LIBRARY_LOCATION MATCHES "ESMF_LIBRARY_LOCATION-NOTFOUND") + message(WARNING "ESMF library not found in ${ESMF_LIBSDIR}.") + endif() + if(NOT TARGET ESMF::ESMF) + add_library(ESMF::ESMF UNKNOWN IMPORTED) + endif() endif() - string(STRIP "${ESMF_F90ESMFLINKRPATHS} ${ESMF_F90ESMFLINKPATHS} ${ESMF_F90LINKPATHS} ${ESMF_F90LINKLIBS} ${ESMF_F90LINKOPTS}" ESMF_INTERFACE_LINK_LIBRARIES) - set(ESMF_LIBRARY_LOCATION ${esmf_lib}) + # Add ESMF as an alias to ESMF::ESMF for backward compatibility + if(NOT TARGET ESMF) + add_library(ESMF ALIAS ESMF::ESMF) + endif() -else() + # Add ESMF include directories + set(ESMF_INCLUDE_DIRECTORIES "") + separate_arguments(_ESMF_F90COMPILEPATHS UNIX_COMMAND ${ESMF_F90COMPILEPATHS}) + foreach(_ITEM ${_ESMF_F90COMPILEPATHS}) + string(REGEX REPLACE "^-I" "" _ITEM "${_ITEM}") + list(APPEND ESMF_INCLUDE_DIRECTORIES ${_ITEM}) + endforeach() - message(WARNING "ESMFMKFILE ${ESMFMKFILE} does not exist") + # Add ESMF link libraries + string(STRIP "${ESMF_F90LINKRPATHS} ${ESMF_F90ESMFLINKRPATHS} ${ESMF_F90ESMFLINKPATHS} ${ESMF_F90LINKPATHS} ${ESMF_F90LINKLIBS} ${ESMF_F90LINKOPTS}" ESMF_INTERFACE_LINK_LIBRARIES) -endif() + # Finalize find_package + include(FindPackageHandleStandardArgs) -## Finalize find_package -include(FindPackageHandleStandardArgs) - -find_package_handle_standard_args( - ${CMAKE_FIND_PACKAGE_NAME} - REQUIRED_VARS ESMF_LIBRARY_LOCATION - ESMF_INTERFACE_LINK_LIBRARIES - ESMF_F90COMPILEPATHS - VERSION_VAR ESMF_VERSION) - -## If ESMF is found create imported library target -if(ESMF_FOUND) - add_library(esmf ${_library_type} IMPORTED) - set_target_properties(esmf PROPERTIES - IMPORTED_LOCATION "${ESMF_LIBRARY_LOCATION}" - INTERFACE_INCLUDE_DIRECTORIES "${ESMF_F90COMPILEPATHS}" - INTERFACE_LINK_LIBRARIES "${ESMF_INTERFACE_LINK_LIBRARIES}") -endif() + find_package_handle_standard_args( + ${CMAKE_FIND_PACKAGE_NAME} + REQUIRED_VARS ESMF_LIBRARY_LOCATION + ESMF_INTERFACE_LINK_LIBRARIES + ESMF_F90COMPILEPATHS + VERSION_VAR ESMF_VERSION) + + set_target_properties(ESMF::ESMF PROPERTIES + IMPORTED_LOCATION "${ESMF_LIBRARY_LOCATION}" + INTERFACE_INCLUDE_DIRECTORIES "${ESMF_INCLUDE_DIRECTORIES}" + INTERFACE_LINK_LIBRARIES "${ESMF_INTERFACE_LINK_LIBRARIES}") + +else() + set(ESMF_FOUND FALSE CACHE BOOL "esmf.mk file NOT found" FORCE) + message(WARNING "ESMFMKFILE ${ESMFMKFILE} not found. Try setting ESMFMKFILE \ + to esmf.mk location.") +endif() \ No newline at end of file From c43a89f0e22ded3a65b7420f58563d2190622d77 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 20 Mar 2025 12:12:28 +1100 Subject: [PATCH 26/32] use deps from access3-share where possible --- configuration/scripts/cmake/CMakeLists.txt | 10 +- configuration/scripts/cmake/FindESMF.cmake | 194 --------------------- 2 files changed, 6 insertions(+), 198 deletions(-) delete mode 100755 configuration/scripts/cmake/FindESMF.cmake diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index f640e6b22..da69837b6 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -105,7 +105,9 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} if(ACCESS3_CICE) find_package(Access3Share REQUIRED cdeps timing share nuopc_cap_share) - find_package(ESMF 8.3.0 MODULE REQUIRED) + if(NOT TARGET ESMF::ESMF) #Access3Share probably already has ESMF with PUBLIC interface + message(FATAL_ERROR "ESMF interface missing from Access3Share package") + endif() else() find_package(MPI REQUIRED) endif() @@ -114,11 +116,11 @@ if(OPENMP) find_package(OpenMP REQUIRED COMPONENTS Fortran) endif() -if(CICE_IO MATCHES "^(NetCDF|PIO)$") +if(CICE_IO MATCHES "^(NetCDF|PIO)$" AND NOT TARGET NetCDF::NetCDF_Fortran) find_package(NetCDF 4.7.3 REQUIRED Fortran) endif() if(CICE_IO MATCHES "PIO" AND NOT TARGET PIO::PIO_Fortran) - find_package(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) + find_package(PIO 2.5.3 REQUIRED COMPONENTS Fortran) endif() #[==============================================================================[ @@ -141,7 +143,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") endif() if(ACCESS3_CICE) target_link_libraries(cicelib - PUBLIC esmf + PUBLIC ESMF::ESMF PRIVATE Access3::nuopc_cap_share Access3::share Access3::timing Access3::cdeps-common ) endif() diff --git a/configuration/scripts/cmake/FindESMF.cmake b/configuration/scripts/cmake/FindESMF.cmake deleted file mode 100755 index 8dfb926ce..000000000 --- a/configuration/scripts/cmake/FindESMF.cmake +++ /dev/null @@ -1,194 +0,0 @@ -# Earth System Modeling Framework - -# Copyright (c) 2002-2025 University Corporation for Atmospheric Research, -# Massachusetts Institute of Technology, Geophysical Fluid Dynamics Laboratory, -# University of Michigan, National Centers for Environmental Prediction, -# Los Alamos National Laboratory, Argonne National Laboratory, -# NASA Goddard Space Flight Center. -# All rights reserved. - -# Permission is hereby granted, free of charge, to any person obtaining a copy -# of this software and associated documentation files (the "Software"), to -# deal with the Software without restriction, including without limitation the -# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or -# sell copies of the Software, and to permit persons to whom the Software is -# furnished to do so, subject to the following conditions: -# 1. Redistributions of source code must retain the above copyright notice, -# this list of conditions and the following disclaimers. -# 2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimers in the -# documentation and/or other materials provided with the distribution. -# 3. Neither the names of the organizations developing this software, nor -# the names of its contributors may be used to endorse or promote products -# derived from this Software without specific prior written permission. - -# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -# CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS -# WITH THE SOFTWARE. - -# - Try to find ESMF -# -# Uses ESMFMKFILE to find the filepath of esmf.mk. If this is NOT set, then this -# module will attempt to find esmf.mk. If ESMFMKFILE exists, then -# ESMF_FOUND=TRUE and all ESMF makefile variables will be set in the global -# scope. Optionally, set ESMF_MKGLOBALS to a string list to filter makefile -# variables. For example, to globally scope only ESMF_LIBSDIR and ESMF_APPSDIR -# variables, use this CMake command in CMakeLists.txt: -# -# set(ESMF_MKGLOBALS "LIBSDIR" "APPSDIR") - -# Set ESMFMKFILE as defined by system env variable. If it's not explicitly set -# try to find esmf.mk file in default locations (ESMF_ROOT, CMAKE_PREFIX_PATH, -# etc) - -# - Common Usage -# -# Where to look for this FindESMF.cmake file -# list(APPEND CMAKE_MODULE_PATH "") -# is to be replaced with the directory for this file -# -# How to locate ESMF libraries and create target -# find_package(ESMF MODULE REQUIRED) -# is to be replaced with the minimum version required -# -# How to link targets -# target_link_libraries( PUBLIC ESMF::ESMF) -# is to be replaced with your CMake target - -if(NOT DEFINED ESMFMKFILE) - if(NOT DEFINED ENV{ESMFMKFILE}) - find_path(ESMFMKFILE_PATH esmf.mk PATH_SUFFIXES lib lib64) - if(ESMFMKFILE_PATH) - set(ESMFMKFILE ${ESMFMKFILE_PATH}/esmf.mk) - message(STATUS "Found esmf.mk file ${ESMFMKFILE}") - endif() - else() - set(ESMFMKFILE $ENV{ESMFMKFILE}) - endif() -endif() - -# Only parse the mk file if it is found -if(EXISTS ${ESMFMKFILE}) - set(ESMFMKFILE ${ESMFMKFILE} CACHE FILEPATH "Path to esmf.mk file") - set(ESMF_FOUND TRUE CACHE BOOL "esmf.mk file found" FORCE) - - # Read the mk file - file(STRINGS "${ESMFMKFILE}" esmfmkfile_contents) - # Parse each line in the mk file - foreach(str ${esmfmkfile_contents}) - # Only consider uncommented lines - string(REGEX MATCH "^[^#]" def ${str}) - # Line is not commented - if(def) - # Extract the variable name - string(REGEX MATCH "^[^=]+" esmf_varname ${str}) - # Extract the variable's value - string(REGEX MATCH "=.+$" esmf_vardef ${str}) - # Only for variables with a defined value - if(esmf_vardef) - # Get rid of the assignment string - string(SUBSTRING ${esmf_vardef} 1 -1 esmf_vardef) - # Remove whitespace - string(STRIP ${esmf_vardef} esmf_vardef) - # A string or single-valued list - if(NOT DEFINED ESMF_MKGLOBALS) - # Set in global scope - set(${esmf_varname} ${esmf_vardef}) - # Don't display by default in GUI - mark_as_advanced(esmf_varname) - else() # Need to filter global promotion - foreach(m ${ESMF_MKGLOBALS}) - string(FIND ${esmf_varname} ${m} match) - # Found the string - if(NOT ${match} EQUAL -1) - # Promote to global scope - set(${esmf_varname} ${esmf_vardef}) - # Don't display by default in the GUI - mark_as_advanced(esmf_varname) - # No need to search for the current string filter - break() - endif() - endforeach() - endif() - endif() - endif() - endforeach() - - # Construct ESMF_VERSION from ESMF_VERSION_STRING_GIT - # ESMF_VERSION_MAJOR and ESMF_VERSION_MINOR are defined in ESMFMKFILE - set(ESMF_VERSION 0) - set(ESMF_VERSION_PATCH ${ESMF_VERSION_REVISION}) - set(ESMF_BETA_RELEASE FALSE) - if(ESMF_VERSION_BETASNAPSHOT MATCHES "^('T')$") - set(ESMF_BETA_RELEASE TRUE) - if(ESMF_VERSION_STRING_GIT MATCHES "^ESMF.*beta_snapshot") - set(ESMF_BETA_SNAPSHOT ${ESMF_VERSION_STRING_GIT}) - elseif(ESMF_VERSION_STRING_GIT MATCHES "^v.\..\..b") - set(ESMF_BETA_SNAPSHOT ${ESMF_VERSION_STRING_GIT}) - else() - set(ESMF_BETA_SNAPSHOT 0) - endif() - message(STATUS "Detected ESMF Beta snapshot: ${ESMF_BETA_SNAPSHOT}") - endif() - set(ESMF_VERSION "${ESMF_VERSION_MAJOR}.${ESMF_VERSION_MINOR}.${ESMF_VERSION_PATCH}") - - # Find the ESMF library - if(USE_ESMF_STATIC_LIBS) - find_library(ESMF_LIBRARY_LOCATION NAMES libesmf.a PATHS ${ESMF_LIBSDIR} NO_DEFAULT_PATH) - if(ESMF_LIBRARY_LOCATION MATCHES "ESMF_LIBRARY_LOCATION-NOTFOUND") - message(WARNING "Static ESMF library (libesmf.a) not found in \ - ${ESMF_LIBSDIR}. Try setting USE_ESMF_STATIC_LIBS=OFF") - endif() - if(NOT TARGET ESMF::ESMF) - add_library(ESMF::ESMF STATIC IMPORTED) - endif() - else() - find_library(ESMF_LIBRARY_LOCATION NAMES esmf PATHS ${ESMF_LIBSDIR} NO_DEFAULT_PATH) - if(ESMF_LIBRARY_LOCATION MATCHES "ESMF_LIBRARY_LOCATION-NOTFOUND") - message(WARNING "ESMF library not found in ${ESMF_LIBSDIR}.") - endif() - if(NOT TARGET ESMF::ESMF) - add_library(ESMF::ESMF UNKNOWN IMPORTED) - endif() - endif() - - # Add ESMF as an alias to ESMF::ESMF for backward compatibility - if(NOT TARGET ESMF) - add_library(ESMF ALIAS ESMF::ESMF) - endif() - - # Add ESMF include directories - set(ESMF_INCLUDE_DIRECTORIES "") - separate_arguments(_ESMF_F90COMPILEPATHS UNIX_COMMAND ${ESMF_F90COMPILEPATHS}) - foreach(_ITEM ${_ESMF_F90COMPILEPATHS}) - string(REGEX REPLACE "^-I" "" _ITEM "${_ITEM}") - list(APPEND ESMF_INCLUDE_DIRECTORIES ${_ITEM}) - endforeach() - - # Add ESMF link libraries - string(STRIP "${ESMF_F90LINKRPATHS} ${ESMF_F90ESMFLINKRPATHS} ${ESMF_F90ESMFLINKPATHS} ${ESMF_F90LINKPATHS} ${ESMF_F90LINKLIBS} ${ESMF_F90LINKOPTS}" ESMF_INTERFACE_LINK_LIBRARIES) - - # Finalize find_package - include(FindPackageHandleStandardArgs) - - find_package_handle_standard_args( - ${CMAKE_FIND_PACKAGE_NAME} - REQUIRED_VARS ESMF_LIBRARY_LOCATION - ESMF_INTERFACE_LINK_LIBRARIES - ESMF_F90COMPILEPATHS - VERSION_VAR ESMF_VERSION) - - set_target_properties(ESMF::ESMF PROPERTIES - IMPORTED_LOCATION "${ESMF_LIBRARY_LOCATION}" - INTERFACE_INCLUDE_DIRECTORIES "${ESMF_INCLUDE_DIRECTORIES}" - INTERFACE_LINK_LIBRARIES "${ESMF_INTERFACE_LINK_LIBRARIES}") - -else() - set(ESMF_FOUND FALSE CACHE BOOL "esmf.mk file NOT found" FORCE) - message(WARNING "ESMFMKFILE ${ESMFMKFILE} not found. Try setting ESMFMKFILE \ - to esmf.mk location.") -endif() \ No newline at end of file From 421a90ccc47b7861afa48f5384f642715c5560e1 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 27 Mar 2025 10:43:16 +1100 Subject: [PATCH 27/32] review comments --- configuration/scripts/cmake/CMakeLists.txt | 38 +++++++++++----------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index da69837b6..97769a3d6 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -27,15 +27,15 @@ else() message(STATUS " - CICE_IO ${CICE_IO}") endif() -option(ACCESS3_CICE "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) -option(OPENMP "Enable OpenMP threading" OFF) -message(STATUS " - ACCESS3_CICE ${ACCESS3_CICE}") -message(STATUS " - OPENMP ${OPENMP}") +option(CICE_ACCESS3 "Use ACCESS3 dependencies and install ACCESS3 libraries" OFF) +option(CICE_OPENMP "Enable OpenMP threading" OFF) +message(STATUS " - CICE_ACCESS3 ${CICE_ACCESS3}") +message(STATUS " - CICE_OPENMP ${CICE_OPENMP}") #placeholder CICE_DRIVER option to allow for a nuopc/access driver in the future option(CICE_DRIVER "CICE driver code to use" OFF) if(NOT CICE_DRIVER) - if(ACCESS3_CICE) + if(CICE_ACCESS3) set(CICE_DRIVER "nuopc/cmeps") else() set(CICE_DRIVER "standalone/cice") @@ -43,10 +43,10 @@ if(NOT CICE_DRIVER) endif() message(STATUS " - CICE_DRIVER ${CICE_DRIVER}") -if(ACCESS3_CICE) - option(CESMCOUPLED "CESMCOUPLED Build CPP" OFF) - message(STATUS " - CESMCOUPLED ${CESMCOUPLED}") -elseif(CESMCOUPLED) +if(CICE_ACCESS3) + option(CICE_CESMCOUPLED "CESMCOUPLED Build CPP" OFF) + message(STATUS " - CICE_CESMCOUPLED ${CICE_CESMCOUPLED}") +elseif(CICE_CESMCOUPLED) message(FATAL_ERROR "CESMCOUPLED not supported when ACCESS3_CICE=OFF") endif() @@ -87,7 +87,7 @@ else() message(WARNING "C compiler with ID ${CMAKE_C_COMPILER_ID} will be used with CMake default options") endif() -if (CESMCOUPLED) +if (CICE_CESMCOUPLED) add_compile_definitions( CESMCOUPLED ) @@ -103,7 +103,7 @@ set(CMAKE_INSTALL_MODULEDIR ${CMAKE_INSTALL_INCLUDEDIR} # External packages # #]==============================================================================] -if(ACCESS3_CICE) +if(CICE_ACCESS3) find_package(Access3Share REQUIRED cdeps timing share nuopc_cap_share) if(NOT TARGET ESMF::ESMF) #Access3Share probably already has ESMF with PUBLIC interface message(FATAL_ERROR "ESMF interface missing from Access3Share package") @@ -112,7 +112,7 @@ else() find_package(MPI REQUIRED) endif() -if(OPENMP) +if(CICE_OPENMP) find_package(OpenMP REQUIRED COMPONENTS Fortran) endif() @@ -141,7 +141,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() -if(ACCESS3_CICE) +if(CICE_ACCESS3) target_link_libraries(cicelib PUBLIC ESMF::ESMF PRIVATE Access3::nuopc_cap_share Access3::share Access3::timing Access3::cdeps-common @@ -154,7 +154,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$") endif() endif() -if(OPENMP) +if(CICE_OPENMP) target_link_libraries(cicelib PUBLIC OpenMP::OpenMP_Fortran) endif() @@ -311,7 +311,7 @@ endif() # Install or Export # #]==============================================================================] -if(ACCESS3_CICE) +if(CICE_ACCESS3) ## Library set_target_properties(cicelib PROPERTIES OUTPUT_NAME access-cicelib @@ -319,8 +319,8 @@ if(ACCESS3_CICE) ) install(TARGETS cicelib EXPORT CicelibTargets - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICECmeps_runtime NAMELINK_COMPONENT AccessCICECmeps_Development - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICECmeps_Development + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICE_runtime NAMELINK_COMPONENT AccessCICE_Development + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT AccessCICE_Development ) # Fortran module files are a special case, as currently there is no standard # way of handling them in CMake @@ -342,10 +342,10 @@ if(ACCESS3_CICE) "${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake" INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib ) - + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/CicelibConfig.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Cicelib - COMPONENT AccessCICECmeps_Development + COMPONENT AccessCICE_Development ) if(CICE_IO MATCHES "NetCDF") From 396496507408f4204af2b7ad744c63ca654c9b9f Mon Sep 17 00:00:00 2001 From: Anton Steketee <79179784+anton-seaice@users.noreply.github.com> Date: Thu, 27 Mar 2025 13:37:48 +1100 Subject: [PATCH 28/32] Update configuration/scripts/cmake/CMakeLists.txt Co-authored-by: Micael Oliveira --- configuration/scripts/cmake/CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 97769a3d6..6137fc188 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -117,6 +117,7 @@ if(CICE_OPENMP) endif() if(CICE_IO MATCHES "^(NetCDF|PIO)$" AND NOT TARGET NetCDF::NetCDF_Fortran) + # Code has not been tested with versions older than 4.7.3, but probably still works fine find_package(NetCDF 4.7.3 REQUIRED Fortran) endif() if(CICE_IO MATCHES "PIO" AND NOT TARGET PIO::PIO_Fortran) From 774c9c72c1f50cc05da815b09377b8592cc72a4c Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 27 Mar 2025 13:40:31 +1100 Subject: [PATCH 29/32] note about code versions --- configuration/scripts/cmake/CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 6137fc188..18189cb62 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -122,6 +122,7 @@ if(CICE_IO MATCHES "^(NetCDF|PIO)$" AND NOT TARGET NetCDF::NetCDF_Fortran) endif() if(CICE_IO MATCHES "PIO" AND NOT TARGET PIO::PIO_Fortran) find_package(PIO 2.5.3 REQUIRED COMPONENTS Fortran) + # Code has not been tested with versions older than 2.5.3, but probably still works fine endif() #[==============================================================================[ From b6b4a17e8332bc3e5c988cf27b768046d66a3177 Mon Sep 17 00:00:00 2001 From: Anton Steketee <79179784+anton-seaice@users.noreply.github.com> Date: Thu, 27 Mar 2025 13:42:02 +1100 Subject: [PATCH 30/32] Update configuration/scripts/cmake/CMakeLists.txt Co-authored-by: Micael Oliveira --- configuration/scripts/cmake/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index 18189cb62..cf5380943 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -287,7 +287,7 @@ elseif(CICE_DRIVER MATCHES "standalone/cice") ${CICE_CORE}/drivers/${CICE_DRIVER}/CICE_RunMod.F90 ) else() - message(FATAL_ERROR "CICE_DRIVER: ${CICE_DRIVER} not supported, add to cmake") + message(FATAL_ERROR "CICE_DRIVER: ${CICE_DRIVER} is currently not supported by the CMake build system") endif() # Select IO source files based on CICE_IO From 4c8992955949be5535af8b40582549c0e12188c0 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Thu, 27 Mar 2025 15:21:27 +1100 Subject: [PATCH 31/32] remove CICE_CESMCOUPLED option --- configuration/scripts/cmake/CMakeLists.txt | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index cf5380943..b45cbdcf9 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -43,13 +43,6 @@ if(NOT CICE_DRIVER) endif() message(STATUS " - CICE_DRIVER ${CICE_DRIVER}") -if(CICE_ACCESS3) - option(CICE_CESMCOUPLED "CESMCOUPLED Build CPP" OFF) - message(STATUS " - CICE_CESMCOUPLED ${CICE_CESMCOUPLED}") -elseif(CICE_CESMCOUPLED) - message(FATAL_ERROR "CESMCOUPLED not supported when ACCESS3_CICE=OFF") -endif() - #[==============================================================================[ # Project configuration # #]==============================================================================] @@ -87,7 +80,7 @@ else() message(WARNING "C compiler with ID ${CMAKE_C_COMPILER_ID} will be used with CMake default options") endif() -if (CICE_CESMCOUPLED) +if (CICE_ACCESS3) add_compile_definitions( CESMCOUPLED ) From 5eaa7c2dc32b91deb418ec45827386482c83bb68 Mon Sep 17 00:00:00 2001 From: anton-seaice Date: Fri, 28 Mar 2025 09:21:04 +1100 Subject: [PATCH 32/32] rm comments and set versions consistently --- configuration/scripts/cmake/CMakeLists.txt | 1 - configuration/scripts/cmake/CicelibConfig.cmake.in | 4 ++-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/configuration/scripts/cmake/CMakeLists.txt b/configuration/scripts/cmake/CMakeLists.txt index b45cbdcf9..0f4930678 100644 --- a/configuration/scripts/cmake/CMakeLists.txt +++ b/configuration/scripts/cmake/CMakeLists.txt @@ -132,7 +132,6 @@ set(ICEPACK "${CMAKE_SOURCE_DIR}/../../../icepack") add_fortran_library(cicelib mod STATIC) if(CICE_IO MATCHES "^(NetCDF|PIO)$") - # which is this not just an "add_compile_definitions?" target_compile_definitions(cicelib PRIVATE FORTRANUNDERSCORE ncdf) target_compile_definitions(cicelib PRIVATE USE_NETCDF) endif() diff --git a/configuration/scripts/cmake/CicelibConfig.cmake.in b/configuration/scripts/cmake/CicelibConfig.cmake.in index 3605d5bca..13b9e5fa7 100644 --- a/configuration/scripts/cmake/CicelibConfig.cmake.in +++ b/configuration/scripts/cmake/CicelibConfig.cmake.in @@ -10,10 +10,10 @@ set(_required_components ${Cicelib_FIND_COMPONENTS}) set(CICE_IO @CICE_IO@) if(CICE_IO MATCHES "NetCDF") - find_dependency(NetCDF REQUIRED Fortran) + find_dependency(NetCDF 4.7.3 REQUIRED Fortran) elseif(CICE_IO MATCHES "PIO") if (NOT TARGET PIO::PIO_Fortran) - find_dependency(PIO REQUIRED COMPONENTS C Fortran) + find_dependency(PIO 2.5.3 REQUIRED COMPONENTS C Fortran) endif() find_dependency(NetCDF REQUIRED Fortran) endif()