Skip to content

Commit

Permalink
Add first version - Shumlib 2018.06.1
Browse files Browse the repository at this point in the history
  • Loading branch information
Steve Wardle committed Jul 27, 2018
0 parents commit 7f9d19b
Show file tree
Hide file tree
Showing 91 changed files with 41,541 additions and 0 deletions.
234 changes: 234 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,234 @@
# Main makefile storing common options for building all libraries, by triggering
# individual makefiles from each library directory
#--------------------------------------------------------------------------------

# The intention is that the user points "make" at one of the platform specific
# files, which include this file at the end; here we try to ensure that this
# has happened (if it hasn't, various important variables will not be set)
ifndef PLATFORM
$(error Platform file not loaded, re-run as "make -f" providing a file from \
the "make" subdirectory as an argument)
endif

# Setup destination directory - this can be overidden by the user if they wish
# to install directly to a different location
LIBDIR_ROOT ?= ${PWD}/build
LIBDIR_OUT ?= ${LIBDIR_ROOT}/${PLATFORM}
export

# Setup test directory
SHUM_TMPDIR ?= $(shell mktemp -d)

# Setup Base directory. This is included as the base in all paths
DIR_ROOT ?= ${PWD}

# Setup the flags which will be passed to all compilations - add the openMP
# flags based on the setting below (defaults to true)
SHUM_OPENMP ?= true
ifeq (${SHUM_OPENMP}, true)
FCFLAGS=${FCFLAGS_PREC} ${FCFLAGS_EXTRA} ${FCFLAGS_OPENMP}
CCFLAGS=${CCFLAGS_PREC} ${CCFLAGS_EXTRA} ${CCFLAGS_OPENMP}
else ifeq (${SHUM_OPENMP}, false)
FCFLAGS=${FCFLAGS_PREC} ${FCFLAGS_EXTRA} ${FCFLAGS_NOOPENMP}
CCFLAGS=${CCFLAGS_PREC} ${CCFLAGS_EXTRA} ${CCFLAGS_NOOPENMP}
else
$(error If specified in the environment SHUM_OPENMP environment variable must \
be set to either "true" or "false")
endif

# Default target - build all available libraries
#--------------------------------------------------------------------------------
.PHONY: default
default: all_libs

# Output directories
#--------------------------------------------------------------------------------
OUTDIRS=${LIBDIR_OUT}/lib ${LIBDIR_OUT}/include

${OUTDIRS}:
mkdir -p ${LIBDIR_OUT}/lib
mkdir -p ${LIBDIR_OUT}/include

OUTDIR_TESTS=${LIBDIR_OUT}/tests

${OUTDIR_TESTS}:
mkdir -p ${LIBDIR_OUT}/tests

# Setup path to directory containing common/shared components; these include
# functions that provide Shumlib version information and the C Precision Bomb
# (which will protect against compilation on platforms where the assumptions
# about precision made in the libraries is invalid)
#--------------------------------------------------------------------------------
COMMON_DIR=${DIR_ROOT}/common

# The FRUIT source itself
#------------------------
FRUIT=fruit
.PHONY: ${FRUIT}
${FRUIT}: ${OUTDIRS}
${MAKE} -C ${DIR_ROOT}/${FRUIT}

# Libraries
#--------------------------------------------------------------------------------

# String conv
#------------
STR_CONV=shum_string_conv
STR_CONV_PREREQ=

# Byte-swapping
#--------------
BSWAP=shum_byteswap
BSWAP_PREREQ=STR_CONV

# Data conv
#----------
DATA_CONV=shum_data_conv
DATA_CONV_PREREQ=STR_CONV

# WGDOS packing
#--------------
PACK=shum_wgdos_packing
PACK_PREREQ=STR_CONV

# Horizontal Interpolation
#--------------
HORIZ_INTERP=shum_horizontal_field_interp
HORIZ_INTERP_PREREQ=

# Thread Utils
#--------------
THREAD_UTILS=shum_thread_utils
THREAD_UTILS_PREREQ=

# LL to/from EQ transformation and wind rotation
#-----------------------------------------------
LLEQ=shum_latlon_eq_grids
LLEQ_PREREQ=CONSTS

# Fieldsfile API
#---------------
FFILE=shum_fieldsfile
FFILE_PREREQ=BSWAP

# Spiral Search Algorithm
#------------------------
SPIRAL=shum_spiral_search
SPIRAL_PREREQ=CONSTS STR_CONV

# Fieldsfile classes
#-------------------
FFCLASS=shum_fieldsfile_class
FFCLASS_PREREQ=FFILE PACK

# Constants
#---------------
CONSTS=shum_constants
CONSTS_PREREQ=

# All libs vars
#--------------
ALL_LIBS_VARS=CONSTS BSWAP STR_CONV DATA_CONV PACK THREAD_UTILS LLEQ \
FFILE HORIZ_INTERP SPIRAL FFCLASS
ALL_LIBS=$(foreach lib,${ALL_LIBS_VARS},${${lib}})

# Forward targets (targets with "VAR" names)
#--------------------------------------------------------------------------------

.PHONY: ${ALL_LIBS_VARS} $(addsuffix _PREREQ, ${ALL_LIBS_VARS}) $(addsuffix _TESTS, ${ALL_LIBS_VARS}) $(addsuffix _PREREQ_TESTS, ${ALL_LIBS_VARS})

# auto-generate main targets
${ALL_LIBS_VARS}: %: %_PREREQ ${OUTDIRS}
${MAKE} -C ${DIR_ROOT}/${$@}/src

# auto-generate prerequisite targets
$(addsuffix _PREREQ, ${ALL_LIBS_VARS}): %:
$(foreach prereq,${$@},${MAKE} -C ${DIR_ROOT} ${prereq};)

# auto-generate test makefile path targets
$(wildcard $(addprefix ${DIR_ROOT}/, $(addsuffix /test, ${ALL_LIBS}))): ${DIR_ROOT}/%/test: ${FRUIT} %

# auto-generate test targets
$(addsuffix _TESTS, ${ALL_LIBS_VARS}): %_TESTS: ${FRUIT} % %_PREREQ_TESTS ${OUTDIR_TESTS}
test ! -d ${DIR_ROOT}/${$(subst _TESTS,,$@)}/test || ${MAKE} -C ${DIR_ROOT}/${$(subst _TESTS,,$@)}/test
@test -d ${DIR_ROOT}/${$(subst _TESTS,,$@)}/test || echo "No tests for ${$(subst _TESTS,,$@)}"

# auto-generate prerequisite test targets
$(addsuffix _PREREQ_TESTS, ${ALL_LIBS_VARS}): %:
$(foreach prereq,${$(subst _PREREQ_TESTS,,$@)_PREREQ},${MAKE} -C ${DIR_ROOT} ${prereq}_TESTS;)

# reverse targets (targets with natural names, resolving to targets with "VAR" names)
#--------------------------------------------------------------------------------

.PHONY: ${ALL_LIBS} $(addsuffix _tests, ${ALL_LIBS}) $(addsuffix _prereq, ${ALL_LIBS}) $(addsuffix _prereq_tests, ${ALL_LIBS})

REVERSE_template = $(strip $(foreach revlib,${ALL_LIBS_VARS},$(if $(filter $(1),${${revlib}}),${revlib},)))

# auto-generate reverse targets
${ALL_LIBS}: %:
${MAKE} -C ${DIR_ROOT} $(call REVERSE_template,$@)

# auto-generate reverse test targets
$(addsuffix _tests, ${ALL_LIBS}): %:
${MAKE} -C ${DIR_ROOT} $(call REVERSE_template,$(subst _tests,,$@))_TESTS

# auto-generate reverse prereq targets
$(addsuffix _prereq, ${ALL_LIBS}): %:
${MAKE} -C ${DIR_ROOT} $(call REVERSE_template,$(subst _prereq,,$@))_PREREQ

# auto-generate reverse prereq test targets
$(addsuffix _prereq_tests, ${ALL_LIBS}): %:
${MAKE} -C ${DIR_ROOT} $(call REVERSE_template,$(subst _prereq_tests,,$@))_PREREQ_TESTS

# All library targets
#--------------------------------------------------------------------------------

.PHONY: all_libs all_tests

# 'make all_libs' builds all libraries
all_libs: ${ALL_LIBS}

# 'make all_tests' builds all tests (but does not run them)
all_tests: $(addsuffix _tests, ${ALL_LIBS})

# FRUIT testing control
#--------------------------------------------------------------------------------

.PHONY: test run_tests check fruit_tests

# 'make check' builds all libraries, then tests, then runs them.
check:
${MAKE} -C ${DIR_ROOT} all_libs
${MAKE} -C ${DIR_ROOT} all_tests
${MAKE} -C ${DIR_ROOT} run_tests

# 'make test' builds the tests for currently build libraries, then runs them
test: ${FRUIT} $(addsuffix _tests, $(patsubst lib%.so, %, $(notdir $(wildcard ${LIBDIR_OUT}/lib/*.so))))
${MAKE} -C ${DIR_ROOT} run_tests

# 'make run_tests' runs the currently built tests
run_tests:
${MAKE} -C ${DIR_ROOT}/${FRUIT} -f Makefile-driver
${LIBDIR_OUT}/tests/fruit_tests_static.exe
${LIBDIR_OUT}/tests/fruit_tests_dynamic.exe

# dummy target for fruit
fruit_tests:
@echo "Fruit Lib Built"

# Cleanup targets
#--------------------------------------------------------------------------------
.PHONY: clean clean-temp clean-build
clean-temp:
@$(foreach libname,$(ALL_LIBS),${MAKE} -C ${DIR_ROOT}/$(libname)/src clean;)
@$(foreach libname_test,$(wildcard $(addsuffix /test, ${ALL_LIBS})),${MAKE} -C ${DIR_ROOT}/$(libname_test) clean;)
${MAKE} -C ${DIR_ROOT}/${FRUIT} clean
${MAKE} -C ${DIR_ROOT}/${FRUIT} -f Makefile-driver clean

clean-build:
rm -rf ${OUTDIRS} ${OUTDIR_TESTS}
rm -rf ${LIBDIR_OUT}
rmdir ${LIBDIR_ROOT} || :

clean: clean-temp clean-build

64 changes: 64 additions & 0 deletions common/Makefile-version
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
# Makefile for the version reporting code; this should be included in each of
# the individual library Makefiles after setting "VERSION_LIBNAME" to the name
# of the library.
#
# This file then performs a few tasks:
# * The C version files and precision-bomb header are compiled to produce
# a bespoke version function (named get_VERSION_LIBNAME_version)
# * A suitable C header file containing the prototype for the above C
# function is created
# * It also produces a fortran module (VERSION_LIBNAME_version_mod) which
# provides an interface to the above C function (with the same name)
# * Lastly it stores the list of objects which are needed at library compile
# time for the including Makefile to pickup (VERSION_OBJECTS[_PIC]) and the
# names of generated files for it to remove on "clean" (VERSION_CLEAN)
#--------------------------------------------------------------------------------

f_${VERSION_LIBNAME}_version_mod.f90:
@echo "MODULE f_${VERSION_LIBNAME}_version_mod" > $@
@echo "USE, INTRINSIC :: ISO_C_BINDING" >> $@
@echo "IMPLICIT NONE" >> $@
@echo "INTERFACE" >> $@
@echo " FUNCTION get_${VERSION_LIBNAME}_version() RESULT(version) &" >> $@
@echo " BIND(C, name='get_${VERSION_LIBNAME}_version')" >> $@
@echo " IMPORT :: C_INT64_T" >> $@
@echo " IMPLICIT NONE" >> $@
@echo " INTEGER(KIND=C_INT64_T) :: version" >> $@
@echo " END FUNCTION get_${VERSION_LIBNAME}_version" >> $@
@echo "END INTERFACE" >> $@
@echo "END MODULE f_${VERSION_LIBNAME}_version_mod" >> $@

c_${VERSION_LIBNAME}_version.h:
@echo "#define SHUMLIB_LIBNAME ${VERSION_LIBNAME}" > $@
@echo "#include \"shumlib_version.h\"" >> $@
@echo "#undef SHUMLIB_LIBNAME" >> $@

f_${VERSION_LIBNAME}_version_mod.o: \
f_${VERSION_LIBNAME}_version_mod.f90 \
c_${VERSION_LIBNAME}_version.o
${FC} ${FCFLAGS} -c $< -o $@

f_${VERSION_LIBNAME}_version_mod_PIC.o: \
f_${VERSION_LIBNAME}_version_mod.f90 \
c_${VERSION_LIBNAME}_version_PIC.o
${FC} ${FCFLAGS} ${FCFLAGS_PIC} -c $< -o $@

c_${VERSION_LIBNAME}_version.o: \
${COMMON_DIR}/shumlib_version.c \
${COMMON_DIR}/shumlib_version.h \
${COMMON_DIR}/precision_bomb.h \
c_${VERSION_LIBNAME}_version.h
${CC} ${CCFLAGS} -c -D SHUMLIB_LIBNAME=${VERSION_LIBNAME} \
-I${COMMON_DIR} $< -o $@

c_${VERSION_LIBNAME}_version_PIC.o: \
${COMMON_DIR}/shumlib_version.c \
${COMMON_DIR}/shumlib_version.h \
${COMMON_DIR}/precision_bomb.h \
c_${VERSION_LIBNAME}_version.h
${CC} ${CCFLAGS} -c -D SHUMLIB_LIBNAME=${VERSION_LIBNAME} \
-I${COMMON_DIR} $< -o $@

VERSION_OBJECTS=c_${VERSION_LIBNAME}_version.o f_${VERSION_LIBNAME}_version_mod.o
VERSION_OBJECTS_PIC=c_${VERSION_LIBNAME}_version_PIC.o f_${VERSION_LIBNAME}_version_mod_PIC.o
VERSION_CLEAN=f_${VERSION_LIBNAME}_version_mod.f90 c_${VERSION_LIBNAME}_version.h
92 changes: 92 additions & 0 deletions common/precision_bomb.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
/* *********************************COPYRIGHT**********************************/
/* (C) Crown copyright Met Office. All rights reserved. */
/* For further details please refer to the file LICENCE.txt */
/* which you should have received as part of this distribution. */
/* *********************************COPYRIGHT**********************************/
/* */
/* This file is part of the UM Shared Library project. */
/* */
/* The UM Shared Library is free software: you can redistribute it */
/* and/or modify it under the terms of the Modified BSD License, as */
/* published by the Open Source Initiative. */
/* */
/* The UM Shared Library is distributed in the hope that it will be */
/* useful, but WITHOUT ANY WARRANTY; without even the implied warranty */
/* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* Modified BSD License for more details. */
/* */
/* You should have received a copy of the Modified BSD License */
/* along with the UM Shared Library. */
/* If not, see <http://opensource.org/licenses/BSD-3-Clause>. */
/******************************************************************************/
/* Description: */
/* Precision bomb pre-processor file. Including this in a compilation will */
/* ensure that the precision of floats and doubles corresponds to IEC 60559 */
/* and fail if this is not the case. */
/******************************************************************************/

#include <float.h>

#if defined(__STDC_IEC_559__)

/* Supports C99 ANNEX F */

#else

/* float */
#if defined(SHUM_FLOAT_BOMB)
#undef SHUM_FLOAT_BOMB
#endif

#if FLT_RADIX != 2
#define SHUM_FLOAT_BOMB
#endif

#if FLT_MANT_DIG != 24
#if !defined(SHUM_FLOAT_BOMB)
#define SHUM_FLOAT_BOMB
#endif
#endif

#if FLT_MAX_EXP != 128
#if !defined(SHUM_FLOAT_BOMB)
#define SHUM_FLOAT_BOMB
#endif
#endif

#if FLT_MIN_EXP != -125
#if !defined(SHUM_FLOAT_BOMB)
#define SHUM_FLOAT_BOMB
#endif
#endif

#if defined(SHUM_FLOAT_BOMB)
#error the type "float" does not conform to IEC 60559 single format. This is a requirement for this code to function correctly.
#endif

/* double */
#if defined(SHUM_DBL_BOMB)
#undef SHUM_DBL_BOMB
#endif

#if DBL_MANT_DIG != 53
#define SHUM_DBL_BOMB
#endif

#if DBL_MAX_EXP != 1024
#if !defined(SHUM_DBL_BOMB)
#define SHUM_DBL_BOMB
#endif
#endif

#if DBL_MIN_EXP != -1021
#if !defined(SHUM_DBL_BOMB)
#define SHUM_DBL_BOMB
#endif
#endif

#if defined(SHUM_DBL_BOMB)
#error the type "double" does not conform to IEC 60559 double format. This is a requirement for this code to function correctly.
#endif

#endif
Loading

0 comments on commit 7f9d19b

Please sign in to comment.