WRF-CMake / wrf

🌀 The Weather Research and Forecasting (WRF) model with CMake support
Other
44 stars 3 forks source link

Add support to promote Fortran's REAL to DOUBLE #11

Open dmey opened 5 years ago

dmey commented 5 years ago

@letmaik this is currently not a priority or a strong requirement but it would be good to understand the type and amount of work required to add this option to our CMake support. Are you happy to have a look at this so we can judge the feasibility of such enhancement? This option would apply to WRF only -- i.e. it would not apply to WPS.

letmaik commented 5 years ago

It looks doable. There are three changes necessary to use 64-bit reals:

  1. Set the preprocessor definition RWORDSIZE=8 (currently hard-coded to 4).
  2. Add the compiler flag that promotes unqualified real to real(8) (see also the PROMOTION variable in the legacy arch files). This would involve adding something like a PROMOTION variable to the CMake arch files for all supported compilers and handling that in the main CMake file.
    • GCC: -fdefault-real-8
    • Intel: -real-size 64
    • Cray: -r8 (Note: Could only find -s real64 in the manual, whereas -r .. with whitespace is used for something else) (Note that the flags above assume that real is used, not explicit kind annotations like real(4).)
  3. Use 64-bit versions of some data files for em_real in the installation: https://github.com/WRF-CMake/WRF/blob/a338eda922ba4894bf604e814bec081b86005cef/Makefile#L626-L632 The data files to install are defined here: https://github.com/WRF-CMake/WRF/blob/4e02ae03a4225b76338406a5c92e5554c123144a/test/em_real/CMakeLists.txt#L3-L55
zbeekman commented 5 years ago

This may be beyond the scope of your work on a CMake build system, but please note that the Fortran standard says nothing about the values of available real kinds. While, in practice, it may be safe to assume real*8 maps to the same kind as double precision, there is no guarantee for this. I seem to recall---but I may be mistaken and I'm too lazy to pull out an old wg5 draft---that previous standards also made no claims about the underlying storage size of floating point numbers. However, starting with Fortran 2008, the intrinsic iso_fortran_env module provides named integer constants, like real64 for 64-bit reals. Even still, there is no guarantee that this is a IEEE 754 double. From Metcalf, Cohen & Reid:

If the compiler supports more than one kind with a particular size, the standard does not specify which one will be chosen for the constant. If the compiler does not support a kind with a particular size, that constant will have a value of −2 if it supports a kind with a larger size, and −1 if it does not support any larger size.

However, I am unaware of a compiler vendor whose real64 kind reals are not implemented as IEEE 754 double precision.

Ultimately, you may be able to reduce complexity in the build system by relying on iso_fortran_env's named constants for real kinds, or on intrinsice inquiry functions like selected_real_kind() to create compile-time named constants, rather than having to maintain a list of flags (that may change between versions even from the same vendor) to map compilers to default real kinds.

I'm sure this is not news to you or the developers of WRF at NCAR/UCAR and elsewhere, but just wanted to add my $0.02.

letmaik commented 5 years ago

@zbeekman Thanks for the insights. The goal here is to not change the WRF source code at all, but simply bring the CMake setup on parity to the existing configure/Makefile based one which has a -r8 flag. I agree though that for documentation purposes we should probably not directly say that this will give you 64-bit reals, but simply that it will use real(8) instead of real(4). Does that make sense? We'd like to make it as understandable to end-users as possible.

zbeekman commented 5 years ago

In that case, I’d keep it as is or go the other way. I don’t remember which system it is, but I know there’s at least one where the real kind for double precision is NOT 8. So as far as the documentation goes I’d recommend not talking about the real kinds by value, but instead specify that the appropriate option will be passed to promote the default real kinds to double precision reals (or the closest implementation available on that system).

On Wed, May 22, 2019 at 3:58 AM Maik Riechert notifications@github.com wrote:

@zbeekman https://github.com/zbeekman Thanks for the insights. The goal here is to not change the WRF source code at all, but simply bring the CMake setup on parity to the existing configure/Makefile based one which has a -r8 flag. I agree though that for documentation purposes we should probably not directly say that this will give you 64-bit reals, but simply that it will use real(8) instead of real(4). Does that make sense? We'd like to make it as understandable to end-users as possible.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/WRF-CMake/WRF/issues/11?email_source=notifications&email_token=AACEIPDFM4LRSGGWM7SP6FTPWT4JPA5CNFSM4HK55G62YY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGODV6HMUQ#issuecomment-494696018, or mute the thread https://github.com/notifications/unsubscribe-auth/AACEIPFERIIUU7IRNUNEIDLPWT4JPANCNFSM4HK55G6Q .