William.Hatheway
Active member
When building WRF 4.6.1 with the configure_new.sh script, an issue arises when using libraries installed in non-standard locations. Although CMake tutorials and WRF documentation suggest exporting library paths with the LIBRARYNAME_ROOT format, I've encountered a situation where certain libraries require a different format to work properly. This was determined through trial and error.
These export statements set the required environment variables to point to the correct locations for each library.
The issue here is that CMake is treating uppercase variables like PNETCDF_ROOT as reserved and does not use them, leading to compatibility warnings. This happens because of the way the find_package logic in CMakeLists.txt handles uppercase variables.
This setup ensures that the build system can correctly find and use the libraries from their custom locations.
By making sure that pnetCDF_ROOT is in lowercase, the CMake configuration will work without the compatibility warning.
Here’s why the problem occurs:
Correct Environment Variables for Non-Standard Library Paths
For example, the correct export statements for non-standard library locations should look like this:
Bash:
export ZLIB_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export JASPER_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export HDF5_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export PNETCDF_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
These export statements set the required environment variables to point to the correct locations for each library.
Issue with PNETCDF_ROOT in All Uppercase
However, a problem arises when using PNETCDF_ROOT in all uppercase, as this results in the following error:
Code:
CMake Warning (dev) at CMakeLists.txt:499 (find_package):
Policy CMP0144 is not set: find_package uses upper-case <PACKAGENAME>_ROOT
variables. Run "cmake --help-policy CMP0144" for policy details. Use the
cmake_policy command to set the policy and suppress this warning.
Environment variable PNETCDF_ROOT is set to:
/home/workhorse/WRFHYDRO_COUPLED/Libs/grib2
For compatibility, find_package is ignoring the variable, but code in a
.cmake module might still use it.
This warning is for project developers. Use -Wno-dev to suppress it.
The issue here is that CMake is treating uppercase variables like PNETCDF_ROOT as reserved and does not use them, leading to compatibility warnings. This happens because of the way the find_package logic in CMakeLists.txt handles uppercase variables.
Solution: Use pnetCDF_ROOT in Lowercase
To resolve this issue, the environment variable PNETCDF_ROOT should be written in lowercase (pnetCDF_ROOT). This change allows the CMake script to properly find and link the pnetCDF library. So, the corrected export statement is:
Bash:
export pnetCDF_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
Summary of Correct Configuration
To configure your environment with non-standard library locations, you should set the following environment variables:
Bash:
export ZLIB_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export JASPER_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export HDF5_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
export pnetCDF_ROOT=$HOME/WRFHYDRO_COUPLED/Libs/grib2
This setup ensures that the build system can correctly find and use the libraries from their custom locations.
By making sure that pnetCDF_ROOT is in lowercase, the CMake configuration will work without the compatibility warning.
Why the CMakeLists.txt is the Problem
The issue with the PNETCDF_ROOT variable arises due to how the CMakeLists.txt script in the WRF build system processes environment variables (line 499) , particularly those related to finding external libraries. Specifically, the CMake find_package command used in CMakeLists.txt has a particular way of handling uppercase and lowercase variables.Here’s why the problem occurs:
- CMake's Handling of Uppercase Package Variables:
- The find_package function in CMake uses a case-sensitive approach to locate packages. By default, CMake expects variables like PNETCDF_ROOT to be lowercase. However, in the WRF build system, the find_package function checks for PNETCDF_ROOT as an uppercase variable.
- Compatibility Policy (CMP0144):
- CMake introduced the CMP0144 policy, which governs how find_package handles package root variables. The policy affects whether uppercase or lowercase versions of these variables are used.
- When PNETCDF_ROOT is written in all uppercase, as the default in many tutorials and guides, the build system may ignore this variable. CMake’s behavior, in combination with the find_package directive, causes it to overlook the environment variable, leading to a warning that it is being ignored. This results in the issue where pnetCDF cannot be found, even though the library is installed and available.
- The CMake find_package Logic:
- In the specific version of CMakeLists.txt used by WRF, the find_package(pnetCDF) function is searching for the pnetCDFConfig.cmake file using the lowercase naming convention (i.e., pnetCDF instead of PNETCDF). Therefore, if the environment variable is set in uppercase, CMake will not use it as expected, resulting in the error and the failure to find pnetCDF.
- Workaround Through Trial and Error:
- After noticing this issue, we determined through trial and error that the correct approach is to set the environment variable in lowercase (pnetCDF_ROOT). This aligns with how CMake expects to handle package paths and resolves the conflict caused by the uppercase setting.