Fortran

Basics

Fortran is a compiled language and is the language in which the vast majority of earth systems models (such as WRF) are written in. It is very powerful, but like any compiled language, much more tedious to use, as compared to scripted languages.
There are two main versions of Fortran (Fortran77 and Fortran90). Most code nowadays is written in Fortran90 and not 77. These are significant differences between the two, old code tends to be written in Fortran77. The main difference is that Fortran90 allows "free-format". Google search for more details.

Fortran is indexed on 1 and case-insensitive!

Basic compilation

To compile a Fortran program, you need a Fortran compiler. The most commonly used on is gfortran (or GNU Fortran) as it's free! and available by default on all Linux/UNIX systems. However, gfortran is not the most efficient compiler, and on most supercomputers, the Intel compiler will be available, it's called ifort. If you have the choice, it's usually better to pick ifort rather than gfortran.
Here is basic compilation syntax:

ifort program.f90 -o program.exe
gfortran program.f90 -o program.exe

You then run the program:

./program.exe

It is good practice to compile and run programs within a SHELL (e.g., Bash) script, and always delete the executable before compiling, in case it already exists from a previous compile:

#!/bin/bash
rm -f program.exe
ifort program.f90 -o program.exe
./program.exe >& program_log

Compiling Fortran to use netcdf libraries

Very often, you will need your fortran program to handle netcdf data, in which case you need to compile with netcdf libraries, such that you can use them! On the IVec machines:

module load netcdf
ifort test_nc.f90 -o test_nc.o -I/$NETCDF/include -L/$NETCDF/lib -lnetcdff

(note on some machines, depending on how netcdf was built, you may have to replace -lnetcdff with -lnetcdf (one less "f")

Here is the sample program to read a WRF file and extract a variable:

! Simple program to illustrated opening a netcdf file
PROGRAM test_nc
! This is so we can use the netcd libs
USE netcdf
! Always delcare implicit none in ANY fortran program
implicit none
CHARACTER (LEN = *), PARAMETER :: FILE_NAME = "/scratch/y98/jatinkala/WRF-30y-ERA/WRF/WRFV3/run/1981-2010/wrfhrly_d01_2006-10-01_00:00:00"
INTEGER :: ier, ncid, varid
REAL :: T2(223,152,24) ! note dimensions are reversed in Fortran
! Open the file. NF90_NOWRITE tells netCDF we want read-only access to
! the file.
call check(NF90_OPEN(FILE_NAME, NF90_NOWRITE, ncid))
! Get the varid of the data variable, based on its name.
call check(NF90_INQ_VARID(ncid, "T2", varid))
! Get data
call check(NF90_GET_VAR(ncid, varid, T2))
!print *, T2

! Standard subroutine to return the netcdf errors
contains
  subroutine check(status)
    integer, intent ( in) :: status

    if(status /= nf90_noerr) then 
      print *, trim(nf90_strerror(status))
      stop "Stopped"
    end if
  end subroutine check  

END PROGRAM test_nc

Compiler flags

There are thousands of compiler flags, and only a few are described here.

Optimization

You can compile your program with -O0 (lowest), -O2, or -O3 (highest) level optimization. Higher levels will make the code run faster. Unless you really need to, do Not use optimization to keep life simple.

Endian-ness

Machines are either "big_endian" or "little_endian", whenever creating and/or writing data for WRF, always use the "-convert big_endian" flag.

Rules of thumb

Always use the "implicit none" declaration for all programs
Indent your code
Use uppercase for Fortran Intrinsic functions (Fortran is case in-sensitive, but makes the code read better)

Unless otherwise stated, the content of this page is licensed under Creative Commons Attribution-ShareAlike 3.0 License