--- MITgcm/verification/testscript 2001/05/29 14:01:41 1.3 +++ MITgcm/verification/testscript 2001/09/04 17:17:48 1.19 @@ -1,177 +1,438 @@ -#!/bin/csh +#!/bin/sh -# Run this script from the verification directory -# It will automatically configure, compile, run and verify all experiments -# in the verification directory for whcih there is an results/output.txt -# file. - -# This is the number of least-significant digits allows to be -# in error before the test is classified as a "fail". - -set on_error_die -set passaccuracy=7 -set SKIP=( ) -printf '%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\n' " " Make " " " " Exact "# of" " " " " > summary.txt -printf '%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\n' Config Depend Compile Execute Match Digits Status Experiment >> summary.txt - -# Pass any arguments -foreach arg ($argv) - switch ($arg) - case -clean: - echo Cleaning ... - foreach dr ([a-zA-Z01-9]*) - if (-d $dr/input) then - echo Entering $dr - cd $dr/input - echo "" - make CLEAN - \rm -f {*output,*high,*low}.txt *.log - \rm -f ?ake* - cd ../.. - endif - end - rm -f summary.txt - exit 0 - breaksw - case -nodie: - unset on_error_die - breaksw - case -skip=*: - set SKIP = ( $SKIP `echo $arg | sed 's/-skip=//' | sed 's/,/ /g' `) - breaksw - default: - echo Unknown argument given to $0 - exit 1 - endsw -end - -foreach dr ([a-zA-Z01-9]*) - if (! -d $dr/input ) continue - foreach skip ($SKIP) - if ($skip == $dr) continue;continue - end - set config=- - set makedepend=- - set compile=- - set execute=- - set exactmatch=- - set accuracy=- - set pass=FAIL - echo ============================================================================== - echo Entering $dr - cd $dr - echo "" - if (! -r results/output.txt) then - echo " ***** No results to compare with *****" - if (! $?untested) set untested - set untested=($untested $dr) +compare_lines() +{ +# use codelet to compare lines + if [ $verbose -gt 1 ]; then + cat tmp3.txt 1>&2 + fi + return `./a.out < tmp3.txt` +} + +testoutput_for_prop() +{ +# testoutput_for_prop dir s1 label +# +# compares files in $dir/input/output.txt and $dir/results.output.txt +# using search strings s1 and text label + + if [ $debug -gt 0 ]; then + echo testoutput_for_prop: grep "$2" $1/input/output.txt 1>&2 + fi + if [ -r $1/input/output.txt ]; then + grep "$2" $1/input/output.txt | sed 's/.*=//' | nl > tmp1.txt else - set config=NO - cd input - echo -n " generating Makefile ..." - ../../../tools/genmake -mods=../code >&! make.log - if ($status == 0) set config=Yes - set makedepend=NO - echo " done." - echo -n " make depend ..." - make cleanlinks depend >>& make.log - if ($status == 0) set makedepend=Yes - echo " done." - echo -n " make ..." - make >>& make.log - if ($status) then - echo " ***** An error occurred during make *****" - cat make.log - echo The error during compilation occured in \"$dr\" - set compile=NO - if ($?on_error_die) exit 1 - else - set compile=Yes - set execute=NO - endif - echo " done." - echo -n " running model ..." - if ($compile == 'Yes') then -# ./mitgcmuv | & grep "D iters" > output.txt - ./mitgcmuv > & output.txt - if ($status == 0) then - set execute=Yes - set exactmatch=NO - set accuracy=- - echo " done." - grep "D iters" output.txt | sed 's/.*D iters, err =//' \ - | grep " 0 " \ - > high.txt - grep "D iters" ../results/output.txt \ - | sed 's/.*D iters, err =//' \ - | grep " 0 " \ - > oldhigh.txt - diff oldhigh.txt high.txt > /dev/null - if ($status) then - echo " output differs:" - diff oldhigh.txt high.txt - echo "" - @ lvl=0 - set accuracy='.' - set fail - echo -n Trying reduced accuracy - while ($lvl <= $passaccuracy) - @ lvl+=1 - echo -n " " $lvl - sed s/{$accuracy}E/E/ high.txt > low.txt - sed s/{$accuracy}E/E/ oldhigh.txt > oldlow.txt - diff oldlow.txt low.txt > /dev/null - if ($status == 0) then - unset fail - break + echo testoutput_for_prop: output.txt from model run was not readable 1>&2 + return 99 + fi + if [ $debug -gt 0 ]; then + echo testoutput_for_prop: grep "$2" $1/results/output.txt 1>&2 + fi + grep "$2" $1/results/output.txt | sed 's/.*=//' | nl > tmp2.txt + if [ $debug -gt 0 ]; then + echo testoutput_for_prop: join tmp1.txt tmp2.txt 1>&2 + fi + join tmp1.txt tmp2.txt | awk '{print $1 " " $2 " " $3}' > tmp3.txt + if [ $debug -gt 0 ]; then + echo testoutput_for_prop: compare_lines 1>&2 + fi + compare_lines + digits_of_similarity=$? + if [ $digits_of_similarity -eq 99 ]; then + if [ $verbose -gt 0 ]; then + echo testoutput_for_prop: No comparison was available for \"$2\" 1>&2 + fi + digits_of_similarity=99 + else + if [ $verbose -gt 0 ]; then + echo There were $digits_of_similarity decimal places of similarity for \"$2\" 1>&2 + fi + fi + rm tmp1.txt tmp2.txt tmp3.txt + + return $digits_of_similarity +} + +dashnum() +{ +# dashnum n1 n2 n3 ... +# +# print numbers using %3i format or "--" if number = 99 +for num in $@ +do + if [ $num = 99 ]; then + printf ' --' + else + printf '%3i' $num + fi +done +} + +testoutput() +{ +# testoutput diretory +# +# test output in "directory" + +if [ $debug -gt 0 ]; then + echo testoutput: testoutput_for_prop $1 cg2d_init_res 1>&2 +fi +testoutput_for_prop $1 "cg2d_init_res" "cg2d init. residual"; cg2dres=$? +if [ $debug -gt 0 ]; then + echo testoutput: cg2dres=$cg2dres 1>&2 +fi + +if [ $longtest -gt 0 ]; then +testoutput_for_prop $1 "dynstat_theta_min" "theta minimum"; tmin=$? +testoutput_for_prop $1 "dynstat_theta_max" "theta maximum"; tmax=$? +testoutput_for_prop $1 "dynstat_theta_mean" "theta mean"; tmean=$? +testoutput_for_prop $1 "dynstat_theta_sd" "theta s.d."; tsd=$? +testoutput_for_prop $1 "dynstat_salt_min" "salt minimum"; smin=$? +testoutput_for_prop $1 "dynstat_salt_max" "salt maximum"; smax=$? +testoutput_for_prop $1 "dynstat_salt_mean" "salt mean"; smean=$? +testoutput_for_prop $1 "dynstat_salt_sd" "salt s.d."; ssd=$? +testoutput_for_prop $1 "dynstat_uvel_min" "U minimum"; umin=$? +testoutput_for_prop $1 "dynstat_uvel_max" "U maximum"; umax=$? +testoutput_for_prop $1 "dynstat_uvel_mean" "U mean"; umean=$? +testoutput_for_prop $1 "dynstat_uvel_sd" "U s.d."; usd=$? +testoutput_for_prop $1 "dynstat_vvel_min" "V minimum"; vmin=$? +testoutput_for_prop $1 "dynstat_vvel_max" "V maximum"; vmax=$? +testoutput_for_prop $1 "dynstat_vvel_mean" "V mean"; vmean=$? +testoutput_for_prop $1 "dynstat_vvel_sd" "V s.d."; vsd=$? +else +testoutput_for_prop $1 "dynstat_theta_min" "theta minimum"; tmin=$? +testoutput_for_prop $1 "dynstat_theta_max" "theta maximum"; tmax=$? +testoutput_for_prop $1 "dynstat_salt_min" "salt minimum"; smin=$? +testoutput_for_prop $1 "dynstat_salt_max" "salt maximum"; smax=$? +testoutput_for_prop $1 "dynstat_uvel_min" "U minimum"; umin=$? +testoutput_for_prop $1 "dynstat_uvel_max" "U maximum"; umax=$? +testoutput_for_prop $1 "dynstat_vvel_min" "V minimum"; vmin=$? +testoutput_for_prop $1 "dynstat_vvel_max" "V maximum"; vmax=$? +fi + +dashnum $cg2dres $tmin $tmax $tmean $tsd $smin $smax $smean $ssd \ + $umin $umax $umean $usd $vmin $vmax $vmean $vsd +#printf '%3i' $cg2dres $tmin $tmax $tmean $tsd $smin $smax $smean $ssd \ +# $umin $umax $umean $usd $vmin $vmax $vmean $vsd +} + +genmakemodel() +{ +# genmakemodel directory + ( cd $1; + if [ $quick -eq 0 -o ! -r Makefile ]; then + printf 'genmake ... ' 1>&2 + if [ $ieee -eq 0 ]; then + ../../../tools/genmake -mods=../code > make.log 2>&1 + else + ../../../tools/genmake -ieee -mods=../code > make.log 2>&1 + fi + if [ $? -ne 0 ]; then + tail make.log + echo genmakemodel: genmake failed 1>&2 + return 1 + else + echo succesful 1>&2 + fi + fi + ) +} + +makecleancompile() +{ +# makecleancompile directory + ( cd $1; + if [ $force -gt 0 ]; then + rm -f output.txt + printf 'make clean ... ' 2>&1 + make CLEAN >> make.log 2>&1 + if [ $? -ne 0 ]; then + tail make.log + echo makecleancompile: make clean failed 1>&2 + return 1 + else + echo succesful 1>&2 + fi + fi + ) +} + +makecleanupafter() +{ +# makeupafter directory + ( cd $1; + if [ $clean -gt 0 ]; then + rm -f output.txt + printf 'make clean ... ' 2>&1 + make CLEAN >> make.log 2>&1 + if [ $? -ne 0 ]; then + tail make.log + echo makeupafter: make clean failed 1>&2 + return 1 + else + echo succesful 1>&2 + fi + fi + ) +} + +makedependmodel() +{ +# makedependmodel directory + ( cd $1; + if [ $quick -eq 0 -o ! -r Makefile ]; then + printf 'make depend ... ' 1>&2 + make cleanlinks >> make.log 2>&1 + make depend >> make.log 2>&1 + if [ $? -ne 0 ]; then + tail make.log + echo makemodel: make depend failed 1>&2 + return 1 + else + echo succesful 1>&2 + fi + fi + ) +} + +makemodel() +{ +# makemodel directory + ( cd $1; + if [ -r Makefile ]; then + printf 'make ... ' 1>&2 + make >> make.log 2>&1 + if [ $? -ne 0 ]; then + tail make.log + echo failed 1>&2 + return 1 + else + echo succesful 1>&2 + fi + fi + ) +} + +runmodel() +{ +# runmodel directory exe +# +# runs the model "exe" in "directory" (exe is relative to directory) + + ( cd $1 + if [ -x $2 ]; then + if [ $quick -eq 0 ]; then + rm -f output.txt + fi + printf 'runmodel: ' 1>&2 + make output.txt && return 0 +# if [ ! -r output.txt -o $quick -eq 0 ]; then +# echo runmodel: running... 1>&2 +# ( ./$2 > output.txt 2>&1 ) && return 0 +# rm -f output.txt +# ( make output.txt ) && return 0 +# return 1 +# else +# echo runmodel: output.txt is newer than executable 1>&2 +# ( make output.txt ) && return 0 +# return 0 +# fi +# else +# echo runmodel: executable \"$1/$2\" is missing 1>&2 +# return 1 + fi + ) +} + +createcodelet() +{ +# create codelet for comparing model output +cat > tmp_cmpnum.f <&2 + exit 1 +fi +} + +formatresults() +{ +# formatresults expt genmake depend make run results* + + nm=$1 + printf '%s %s %s %s' $2 $3 $4 $5 + shift; shift; shift; shift; shift; + printf '%3s' $@ + + if [ $1 = '--' ]; then + printf ' N/O ' + else + if [ $1 -gt 12 ]; then + printf ' pass' else - echo " error" - echo " ***** An error occured running the model *****" - tail output.txt - echo The runtime error occured in \"$dr\" - if ($?on_error_die) exit 1 - set pass=- - endif - rm -f high.txt oldhigh.txt low.txt oldlow.txt output.txt make.log - endif - cd .. - endif - echo "" - cd .. -# Pretty summary - printresults: - printf ' %s\t %s\t %s\t %s\t %s\t %s\t %s\t%s\n' $config $makedepend $compile $execute $exactmatch $accuracy $pass $dr >> summary.txt -end -echo ============================================================================== -echo "" + printf ' FAIL' + fi + fi + printf ' %s' $nm + printf '\n' + +} + +show_help() +{ +cat - << EOF +$0 [-help] [-quick] [-verbose] dir1 [dir2] [...] + -help Show this help message + -quick Skip "genmake" and "make depend" if the Makefile exists + -quiet Reduce the amount of output + -verbose Produce copious amounts of output + -debug Produce even more output which will mean nothing to most + -force Do "make CLEAN" before compiling. This forces a complete rebuild. + -clean Do "make CLEAN" after compiling and testing. + -longtest Compare numeric output for mean and s.d. of variables. + -noieee By default, $0 uses the -ieee option for genmake. This turns it off. + +Normal usage: + $0 * Configure, compile, run and analyze in all experiment directories +EOF +} + +scandirs() +{ +if [ $# -eq 0 ]; then + for arg in * + do + test -d $arg/input && echo $arg + done +else + echo $* +fi +} + +############################################################################### + +# Main function + +# Default properties +debug=0 +verbose=1 +quick=0 +force=0 +clean=0 +ieee=1 +longtest=0 +expts='' + +# Process arguments +for arg in $@ +do + case $arg in + -quick) quick=1;; + -verbose) verbose=2;; + -debug) debug=1;; + -force) force=1;; + -clean) clean=1;; + -noieee) ieee=0;; + -longtest) longtest=1;; + -quiet) verbose=0;; + -help) show_help; exit 0;; + -*) echo Unrecognized option:$arg; exit 9;; + *) test -d $arg && expts=`echo $expts $arg`;; + esac +done + +if [ $force -gt 0 -a $quick -gt 0 ]; then + echo You specified -quick and -force together which conflict. + echo Please specify either -quick or -force or neither but not both. + exit 1 +fi + +#if [ ${#expts} -eq 0 ]; then +# echo Scanning all directories +# for arg in * +# do +# test -d $arg && expts=`echo $expts $arg` +# done +#fi +expts=`scandirs $expts` + +createcodelet + +if [ $longtest -gt 0 ]; then +cat << EOF > summary.txt + T S U V +C D M c m s m s m s m s +n p a R g m m e . m m e . m m e . m m e . +f n k u 2 i a a d i a a d i a a d i a a d +g d e n d n x n . n x n . n x n . n x n . + +EOF +else +cat << EOF > summary.txt + T S U V +C D M c +n p a R g m m m m m m m m +f n k u 2 i a i a i a i a +g d e n d n x n x n x n x + +EOF +fi + +# Now configue, make, run and test in each directory +for dir in $expts +do + if [ -r $dir/results/output.txt ]; then + echo ------------------------------------------------------------------------------- + echo + echo Experiment: $dir + echo + unset genmake makedepend make run + if [ $longtest -gt 0 ]; then + results='-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --' + else + results='-- -- -- -- -- -- -- -- --' + fi + genmakemodel $dir/input && genmake=Y \ + && makecleancompile $dir/input \ + && makedependmodel $dir/input && makedepend=Y \ + && makemodel $dir/input && make=Y \ + && runmodel $dir/input mitgcmuv && run=Y \ + && results=`testoutput $dir` \ + && makecleanupafter $dir/input + echo + formatresults $dir ${genmake:-N} ${makedepend:-N} ${make:-N} ${run:-N} $results + echo + formatresults $dir ${genmake:-N} ${makedepend:-N} ${make:-N} ${run:-N} $results >> summary.txt + fi +done + +rm tmp_cmpnum.f a.out -echo "Summary:" -echo "" +echo ------------------------------------------------------------------------------- +echo cat summary.txt