C $Header: /u/gcmpack/MITgcm/pkg/generic_advdiff/gad_plm_fun.F,v 1.1 2016/03/13 01:44:02 jmc Exp $
C $Name: $
# include "GAD_OPTIONS.h"
C-- File gad_plm_fun.F: Routines for monotone piecewise linear method.
C-- Contents
C-- o GAD_PLM_FUN_U
C-- o GAD_PLM_FUN_V
C---+----1----+----2----+----3----+----4----+----5----+----6----+----7-|--+----|
SUBROUTINE GAD_PLM_FUN_U(
I ffll,ff00,ffrr,
O dfds)
C |================================================================|
C | PLM_FUN_U: monotone piecewise linear method. |
C | - uniform grid-spacing variant. |
C |================================================================|
implicit none
C ====================================================== arguments
_RL ffll,ff00,ffrr
_RL dfds(-1:+1)
C ====================================================== variables
_RL fell,ferr,scal
_RL epsil
PARAMETER( epsil = 1. _d -16 )
dfds(-1) = ff00 - ffll
dfds(+1) = ffrr - ff00
if (dfds(-1) * dfds(+1) .gt. 0.0 _d 0) then
C ======================================= calc. ll//rr edge values
fell = 0.5 _d 0 * (ffll + ff00)
ferr = 0.5 _d 0 * (ff00 + ffrr)
C ======================================= calc. centred derivative
dfds(+0) =
& 0.5 _d 0 * (ferr - fell)
C ======================================= monotonic slope-limiting
scal = min(abs(dfds(-1)),
& abs(dfds(+1)))
& / max(abs(dfds(+0)), epsil)
c & / max(abs(dfds(+0)), epsilon(ff00))
scal = min(scal, 1.0 _d 0)
dfds(+0) = scal * dfds(+0)
else
C ======================================= flatten if local extrema
dfds(+0) = 0.0 _d 0
end
if
dfds(-1) = 0.5 _d 0 * dfds(-1)
dfds(+1) = 0.5 _d 0 * dfds(+1)
return
c end subroutine GAD_PLM_FUN_U
end
C---+----1----+----2----+----3----+----4----+----5----+----6----+----7-|--+----|
SUBROUTINE GAD_PLM_FUN_V(
I ffll,ff00,ffrr,
I ddll,dd00,ddrr,
O dfds)
C |================================================================|
C | PLM_FUN_V: monotone piecewise linear method. |
C | - variable grid-spacing variant. |
C |================================================================|
implicit none
C ====================================================== arguments
_RL ffll,ff00,ffrr
_RL ddll,dd00,ddrr
_RL dfds(-1:+1)
C ====================================================== variables
_RL fell,ferr,scal
_RL epsil
PARAMETER( epsil = 1. _d -16 )
dfds(-1) = ff00 - ffll
dfds(+1) = ffrr - ff00
if (dfds(-1) * dfds(+1) .gt. 0.0 _d 0) then
C ======================================= calc. ll//rr edge values
fell = (dd00 * ffll + ddll * ff00)
& / (ddll + dd00)
ferr = (ddrr * ff00 + dd00 * ffrr)
& / (dd00 + ddrr)
C ======================================= calc. centred derivative
dfds(+0) =
& 0.5 _d 0 * (ferr - fell)
C ======================================= monotonic slope-limiting
scal = min(abs(dfds(-1)),
& abs(dfds(+1)))
& / max(abs(dfds(+0)), epsil)
c & / max(abs(dfds(+0)), epsilon(ff00))
scal = min(scal, 1.0 _d 0)
dfds(+0) = scal * dfds(+0)
else
C ======================================= flatten if local extrema
dfds(+0) = 0.0 _d 0
end
if
C == !! check this
dfds(-1) = dfds(-1) / (ddll + dd00) * dd00
dfds(+1) = dfds(+1) / (dd00 + ddrr) * dd00
return
c end subroutine GAD_PLM_FUN_V
end