MOM6
mom_coriolisadv Module Reference

Detailed Description

Accelerations due to the Coriolis force and momentum advection.

This file contains the subroutine that calculates the time derivatives of the velocities due to Coriolis acceleration and momentum advection. This subroutine uses either a vorticity advection scheme from Arakawa and Hsu, Mon. Wea. Rev. 1990, or Sadourny's (JAS 1975) energy conserving scheme. Both have been modified to use general orthogonal coordinates as described in Arakawa and Lamb, Mon. Wea. Rev. 1981. Both schemes are second order accurate, and allow for vanishingly small layer thicknesses. The Arakawa and Hsu scheme globally conserves both total energy and potential enstrophy in the limit of nondivergent flow. Sadourny's energy conserving scheme conserves energy if the flow is nondivergent or centered difference thickness fluxes are used.

Two sets of boundary conditions have been coded in the definition of relative vorticity. These are written as: NOSLIP defined (in spherical coordinates): relvort = dv/dx (east & west), with v = 0. relvort = -sec(Q) * d(u cos(Q))/dy (north & south), with u = 0.

NOSLIP not defined (free slip): relvort = 0 (all boundaries)

with Q temporarily defined as latitude. The free slip boundary condition is much more natural on a C-grid.

A small fragment of the grid is shown below:

    j+1  x ^ x ^ x   At x:  q, CoriolisBu
    j+1  > o > o >   At ^:  v, CAv, vh
    j    x ^ x ^ x   At >:  u, CAu, uh, a, b, c, d
    j    > o > o >   At o:  h, KE
    j-1  x ^ x ^ x
        i-1  i  i+1  At x & ^:
           i  i+1    At > & o:

The boundaries always run through q grid points (x).

Data Types

type  coriolisadv_cs
 Control structure for mom_coriolisadv. More...
 

Functions/Subroutines

subroutine, public coradcalc (u, v, h, uh, vh, CAu, CAv, OBC, AD, G, GV, CS)
 Calculates the Coriolis and momentum advection contributions to the acceleration. More...
 
subroutine gradke (u, v, h, KE, KEx, KEy, k, OBC, G, CS)
 Calculates the acceleration due to the gradient of kinetic energy. More...
 
subroutine, public coriolisadv_init (Time, G, param_file, diag, AD, CS)
 Initializes the control structure for coriolisadv_cs. More...
 
subroutine, public coriolisadv_end (CS)
 Destructor for coriolisadv_cs. More...
 

Variables

integer, parameter sadourny75_energy = 1
 
integer, parameter arakawa_hsu90 = 2
 
integer, parameter robust_enstro = 3
 
integer, parameter sadourny75_enstro = 4
 
integer, parameter arakawa_lamb81 = 5
 
integer, parameter al_blend = 6
 
character *(20), parameter sadourny75_energy_string = "SADOURNY75_ENERGY"
 
character *(20), parameter arakawa_hsu_string = "ARAKAWA_HSU90"
 
character *(20), parameter robust_enstro_string = "ROBUST_ENSTRO"
 
character *(20), parameter sadourny75_enstro_string = "SADOURNY75_ENSTRO"
 
character *(20), parameter arakawa_lamb_string = "ARAKAWA_LAMB81"
 
character *(20), parameter al_blend_string = "ARAKAWA_LAMB_BLEND"
 
integer, parameter ke_arakawa = 10
 
integer, parameter ke_simple_gudonov = 11
 
integer, parameter ke_gudonov = 12
 
character *(20), parameter ke_arakawa_string = "KE_ARAKAWA"
 
character *(20), parameter ke_simple_gudonov_string = "KE_SIMPLE_GUDONOV"
 
character *(20), parameter ke_gudonov_string = "KE_GUDONOV"
 
integer, parameter pv_adv_centered = 21
 
integer, parameter pv_adv_upwind1 = 22
 
character *(20), parameter pv_adv_centered_string = "PV_ADV_CENTERED"
 
character *(20), parameter pv_adv_upwind1_string = "PV_ADV_UPWIND1"
 

Function/Subroutine Documentation

◆ coradcalc()

subroutine, public mom_coriolisadv::coradcalc ( real, dimension(szib_(g),szj_(g),szk_(g)), intent(in)  u,
real, dimension(szi_(g),szjb_(g),szk_(g)), intent(in)  v,
real, dimension(szi_(g),szj_(g),szk_(g)), intent(in)  h,
real, dimension(szib_(g),szj_(g),szk_(g)), intent(in)  uh,
real, dimension(szi_(g),szjb_(g),szk_(g)), intent(in)  vh,
real, dimension(szib_(g),szj_(g),szk_(g)), intent(out)  CAu,
real, dimension(szi_(g),szjb_(g),szk_(g)), intent(out)  CAv,
type(ocean_obc_type), pointer  OBC,
type(accel_diag_ptrs), intent(inout)  AD,
type(ocean_grid_type), intent(in)  G,
type(verticalgrid_type), intent(in)  GV,
type(coriolisadv_cs), pointer  CS 
)

Calculates the Coriolis and momentum advection contributions to the acceleration.

Parameters
[in]gOcen grid structure
[in]gvVertical grid structure
[in]uZonal velocity (m/s)
[in]vMeridional velocity (m/s)
[in]hLayer thickness (m or kg/m2)
[in]uhZonal transport u*h*dy (m3/s or kg/s)
[in]vhMeridional transport v*h*dx (m3/s or kg/s)
[out]cauZonal acceleration due to Coriolis and momentum advection, in m/s2.
[out]cavMeridional acceleration due to Coriolis and momentum advection, in m/s2.
obcOpen boundary control structure
[in,out]adStorage for acceleration diagnostics
csControl structure for MOM_CoriolisAdv

Definition at line 107 of file MOM_CoriolisAdv.F90.

References al_blend, arakawa_hsu90, arakawa_lamb81, gradke(), mom_error_handler::mom_error(), mom_open_boundary::obc_direction_n, pv_adv_centered, pv_adv_upwind1, robust_enstro, sadourny75_energy, and sadourny75_enstro.

Referenced by mom_dynamics_legacy_split::step_mom_dyn_legacy_split(), mom_dynamics_split_rk2::step_mom_dyn_split_rk2(), mom_dynamics_unsplit::step_mom_dyn_unsplit(), and mom_dynamics_unsplit_rk2::step_mom_dyn_unsplit_rk2().

107  type(ocean_grid_type), intent(in) :: g !< Ocen grid structure
108  type(verticalgrid_type), intent(in) :: gv !< Vertical grid structure
109  real, dimension(SZIB_(G),SZJ_(G),SZK_(G)), intent(in) :: u !< Zonal velocity (m/s)
110  real, dimension(SZI_(G),SZJB_(G),SZK_(G)), intent(in) :: v !< Meridional velocity (m/s)
111  real, dimension(SZI_(G),SZJ_(G),SZK_(G)), intent(in) :: h !< Layer thickness (m or kg/m2)
112  real, dimension(SZIB_(G),SZJ_(G),SZK_(G)), intent(in) :: uh !< Zonal transport u*h*dy (m3/s or kg/s)
113  real, dimension(SZI_(G),SZJB_(G),SZK_(G)), intent(in) :: vh !< Meridional transport v*h*dx (m3/s or kg/s)
114  real, dimension(SZIB_(G),SZJ_(G),SZK_(G)), intent(out) :: cau !< Zonal acceleration due to Coriolis
115  !! and momentum advection, in m/s2.
116  real, dimension(SZI_(G),SZJB_(G),SZK_(G)), intent(out) :: cav !< Meridional acceleration due to Coriolis
117  !! and momentum advection, in m/s2.
118  type(ocean_obc_type), pointer :: obc !< Open boundary control structure
119  type(accel_diag_ptrs), intent(inout) :: ad !< Storage for acceleration diagnostics
120  type(coriolisadv_cs), pointer :: cs !< Control structure for MOM_CoriolisAdv
121  ! Local variables
122 
123  real, dimension(SZIB_(G),SZJB_(G)) :: &
124  q, & ! Layer potential vorticity, in m-1 s-1.
125  ih_q, & ! The inverse of thickness interpolated to q pointes, in
126  ! units of m-1 or m2 kg-1.
127  area_q ! The sum of the ocean areas at the 4 adjacent thickness
128  ! points, in m2.
129 
130  real, dimension(SZIB_(G),SZJ_(G)) :: &
131  a, b, c, d ! a, b, c, & d are combinations of the potential vorticities
132  ! surrounding an h grid point. At small scales, a = q/4,
133  ! b = q/4, etc. All are in units of m-1 s-1 or m2 kg-1 s-1,
134  ! and use the indexing of the corresponding u point.
135 
136  real, dimension(SZI_(G),SZJ_(G)) :: &
137  area_h, & ! The ocean area at h points, in m2. Area_h is used to find the
138  ! average thickness in the denominator of q. 0 for land points.
139  ke ! Kinetic energy per unit mass, KE = (u^2 + v^2)/2, in m2 s-2.
140  real, dimension(SZIB_(G),SZJ_(G)) :: &
141  harea_u, & ! The cell area weighted thickness interpolated to u points
142  ! times the effective areas, in H m2.
143  kex, & ! The zonal gradient of Kinetic energy per unit mass,
144  ! KEx = d/dx KE, in m s-2.
145  uh_center ! centered u times h at u-points
146  real, dimension(SZI_(G),SZJB_(G)) :: &
147  harea_v, & ! The cell area weighted thickness interpolated to v points
148  ! times the effective areas, in H m2.
149  key, & ! The meridonal gradient of Kinetic energy per unit mass,
150  ! KEy = d/dy KE, in m s-2.
151  vh_center ! centered v times h at v-points
152  real, dimension(SZI_(G),SZJ_(G)) :: &
153  uh_min, uh_max, & ! The smallest and largest estimates of the volume
154  vh_min, vh_max, & ! fluxes through the faces (i.e. u*h*dy & v*h*dx),
155  ! in m3 s-1 or kg s-1.
156  ep_u, ep_v ! Additional pseudo-Coriolis terms in the Arakawa and Lamb
157  ! discretization, in m-1 s-1 or m2 kg-1 s-1.
158  real, dimension(SZIB_(G),SZJB_(G)) :: &
159  dvdx,dudy, &! Contributions to the circulation around q-points (m2 s-1)
160  abs_vort, & ! Absolute vorticity at q-points, in s-1.
161  q2, & ! Relative vorticity over thickness.
162  max_fvq, & ! The maximum or minimum of the
163  min_fvq, & ! adjacent values of (-u) or v times
164  max_fuq, & ! the absolute vorticity, in m s-2.
165  min_fuq ! All are defined at q points.
166  real, dimension(SZIB_(G),SZJB_(G),SZK_(G)) :: &
167  pv, & ! A diagnostic array of the potential vorticities, in m-1 s-1.
168  rv ! A diagnostic array of the relative vorticities, in s-1.
169  real :: fv1, fv2, fu1, fu2 ! (f+rv)*v or (f+rv)*u in m s-2.
170  real :: max_fv, max_fu ! The maximum or minimum of the neighbor-
171  real :: min_fv, min_fu ! max(min)_fu(v)q, in m s-2.
172 
173  real, parameter :: c1_12=1.0/12.0 ! C1_12 = 1/12
174  real, parameter :: c1_24=1.0/24.0 ! C1_24 = 1/24
175  real :: absolute_vorticity ! Absolute vorticity, in s-1.
176  real :: relative_vorticity ! Relative vorticity, in s-1.
177  real :: ih ! Inverse of thickness, m-1 or m2 kg-1.
178  real :: max_ihq, min_ihq ! The maximum and minimum of the nearby Ihq.
179  real :: harea_q ! The sum of area times thickness of the cells
180  ! surrounding a q point, in m3 or kg.
181  real :: h_neglect ! A thickness that is so small it is usually
182  ! lost in roundoff and can be neglected, in m.
183  real :: temp1, temp2 ! Temporary variables, in m2 s-2.
184  real, parameter :: eps_vel=1.0e-10 ! A tiny, positive velocity, in m s-1.
185 
186  real :: uhc, vhc ! Centered estimates of uh and vh in m3 s-1 or kg s-1.
187  real :: uhm, vhm ! The input estimates of uh and vh in m3 s-1 or kg s-1.
188  real :: c1, c2, c3, slope ! Nondimensional parameters for the Coriolis
189  ! limiter scheme.
190 
191  real :: fe_m2 ! Nondimensional temporary variables asssociated with
192  real :: rat_lin ! the ARAKAWA_LAMB_BLEND scheme.
193  real :: rat_m1 ! The ratio of the maximum neighboring inverse thickness
194  ! to the minimum inverse thickness minus 1. rat_m1 >= 0.
195  real :: al_wt ! The relative weight of the Arakawa & Lamb scheme to the
196  ! Arakawa & Hsu scheme, nondimensional between 0 and 1.
197  real :: sad_wt ! The relative weight of the Sadourny energy scheme to
198  ! the other two with the ARAKAWA_LAMB_BLEND scheme,
199  ! nondimensional between 0 and 1.
200 
201  real :: heff1, heff2 ! Temporary effective H at U or V points in m or kg m-2.
202  real :: heff3, heff4 ! Temporary effective H at U or V points in m or kg m-2.
203  real :: h_tiny ! A very small thickness, in m or kg m-2.
204  real :: uheff, vheff ! More temporary variables, in m3 s-1 or kg s-1.
205  real :: quheff,qvheff ! More temporary variables, in m3 s-2 or kg s-2.
206  integer :: i, j, k, n, is, ie, js, je, isq, ieq, jsq, jeq, nz
207 
208 ! To work, the following fields must be set outside of the usual
209 ! is to ie range before this subroutine is called:
210 ! v[is-1,ie+1,ie+2], u[is-1,ie+1], vh[ie+1], uh[is-1], and
211 ! h[is-1,ie+1,ie+2].
212 ! In the y-direction, the following fields must be set:
213 ! v[js-1,je+1], u[js-1,je+1,je+2], vh[js-1], uh[je+1], and
214 ! h[js-1,je+1,je+2].
215 
216  if (.not.associated(cs)) call mom_error(fatal, &
217  "MOM_CoriolisAdv: Module must be initialized before it is used.")
218  is = g%isc ; ie = g%iec ; js = g%jsc ; je = g%jec
219  isq = g%IscB ; ieq = g%IecB ; jsq = g%JscB ; jeq = g%JecB ; nz = g%ke
220  h_neglect = gv%H_subroundoff
221  h_tiny = gv%Angstrom ! Perhaps this should be set to h_neglect instead.
222 
223  !$OMP parallel do default(private) shared(Isq,Ieq,Jsq,Jeq,G,Area_h)
224  do j=jsq-1,jeq+2 ; do i=isq-1,ieq+2
225  area_h(i,j) = g%mask2dT(i,j) * g%areaT(i,j)
226  enddo ; enddo
227  !$OMP parallel do default(private) shared(Isq,Ieq,Jsq,Jeq,G,Area_h,Area_q)
228  do j=jsq-1,jeq+1 ; do i=isq-1,ieq+1
229  area_q(i,j) = (area_h(i,j) + area_h(i+1,j+1)) + &
230  (area_h(i+1,j) + area_h(i,j+1))
231  enddo ; enddo
232 
233  !$OMP parallel do default(private) shared(u,v,h,uh,vh,CAu,CAv,G,CS,AD,Area_h,Area_q,&
234  !$OMP RV,PV,is,ie,js,je,Isq,Ieq,Jsq,Jeq,nz,h_neglect,h_tiny,OBC)
235  do k=1,nz
236  ! Here the second order accurate layer potential vorticities, q,
237  ! are calculated. hq is second order accurate in space. Relative
238  ! vorticity is second order accurate everywhere with free slip b.c.s,
239  ! but only first order accurate at boundaries with no slip b.c.s.
240  ! First calculate the contributions to the circulation around the q-point.
241  do j=jsq-1,jeq+1 ; do i=isq-1,ieq+1
242  dvdx(i,j) = v(i+1,j,k)*g%dyCv(i+1,j) - v(i,j,k)*g%dyCv(i,j)
243  dudy(i,j) = u(i,j+1,k)*g%dxCu(i,j+1) - u(i,j,k)*g%dxCu(i,j)
244  enddo ; enddo
245  do j=jsq-1,jeq+1 ; do i=isq-1,ieq+2
246  harea_v(i,j) = 0.5*(area_h(i,j) * h(i,j,k) + area_h(i,j+1) * h(i,j+1,k))
247  enddo ; enddo
248  do j=jsq-1,jeq+2 ; do i=isq-1,ieq+1
249  harea_u(i,j) = 0.5*(area_h(i,j) * h(i,j,k) + area_h(i+1,j) * h(i+1,j,k))
250  enddo ; enddo
251  if (cs%Coriolis_En_Dis) then
252  do j=jsq,jeq+1 ; do i=is-1,ie
253  uh_center(i,j) = 0.5 * (g%dy_Cu(i,j) * u(i,j,k)) * (h(i,j,k) + h(i+1,j,k))
254  enddo ; enddo
255  do j=js-1,je ; do i=isq,ieq+1
256  vh_center(i,j) = 0.5 * (g%dx_Cv(i,j) * v(i,j,k)) * (h(i,j,k) + h(i,j+1,k))
257  enddo ; enddo
258  endif
259 
260  ! Adjust circulation components to relative vorticity and thickness projected onto
261  ! velocity points on open boundaries.
262  if (associated(obc)) then ; do n=1,obc%number_of_segments
263  if (.not. obc%segment(n)%on_pe) cycle
264  i = obc%segment(n)%HI%IsdB ; j = obc%segment(n)%HI%JsdB
265  if (obc%segment(n)%is_N_or_S .and. (j >= jsq-1) .and. (j <= jeq+1)) then
266  if (obc%zero_vorticity) then ; do i=obc%segment(n)%HI%IsdB,obc%segment(n)%HI%IedB
267  dvdx(i,j) = 0. ; dudy(i,j) = 0.
268  enddo ; endif
269  if (obc%freeslip_vorticity) then ; do i=obc%segment(n)%HI%IsdB,obc%segment(n)%HI%IedB
270  dudy(i,j) = 0.
271  enddo ; endif
272 
273  ! Project thicknesses across OBC points with a no-gradient condition.
274  do i = max(isq-1,obc%segment(n)%HI%isd), min(ieq+2,obc%segment(n)%HI%ied)
275  if (obc%segment(n)%direction == obc_direction_n) then
276  harea_v(i,j) = 0.5 * (area_h(i,j) + area_h(i,j+1)) * h(i,j,k)
277  else ! (OBC%segment(n)%direction == OBC_DIRECTION_S)
278  harea_v(i,j) = 0.5 * (area_h(i,j) + area_h(i,j+1)) * h(i,j+1,k)
279  endif
280  enddo
281 
282  if (cs%Coriolis_En_Dis) then
283  do i = max(isq-1,obc%segment(n)%HI%isd), min(ieq+2,obc%segment(n)%HI%ied)
284  if (obc%segment(n)%direction == obc_direction_n) then
285  vh_center(i,j) = g%dx_Cv(i,j) * v(i,j,k) * h(i,j,k)
286  else ! (OBC%segment(n)%direction == OBC_DIRECTION_S)
287  vh_center(i,j) = g%dx_Cv(i,j) * v(i,j,k) * h(i,j+1,k)
288  endif
289  enddo
290  endif
291  elseif (obc%segment(n)%is_E_or_W .and. (i >= isq-1) .and. (i <= ieq+1)) then
292  if (obc%zero_vorticity) then ; do j=obc%segment(n)%HI%JsdB,obc%segment(n)%HI%JedB
293  dvdx(i,j) = 0. ; dudy(i,j) = 0.
294  enddo ; endif
295  if (obc%freeslip_vorticity) then ; do j=obc%segment(n)%HI%JsdB,obc%segment(n)%HI%JedB
296  dvdx(i,j) = 0.
297  enddo ; endif
298 
299  ! Project thicknesses across OBC points with a no-gradient condition.
300  do j = max(jsq-1,obc%segment(n)%HI%jsd), min(jeq+2,obc%segment(n)%HI%jed)
301  if (obc%segment(n)%direction == obc_direction_e) then
302  harea_u(i,j) = 0.5*(area_h(i,j) + area_h(i+1,j)) * h(i,j,k)
303  else ! (OBC%segment(n)%direction == OBC_DIRECTION_W)
304  harea_u(i,j) = 0.5*(area_h(i,j) + area_h(i+1,j)) * h(i+1,j,k)
305  endif
306  enddo
307  if (cs%Coriolis_En_Dis) then
308  do j = max(jsq-1,obc%segment(n)%HI%jsd), min(jeq+2,obc%segment(n)%HI%jed)
309  if (obc%segment(n)%direction == obc_direction_e) then
310  uh_center(i,j) = g%dy_Cu(i,j) * u(i,j,k) * h(i,j,k)
311  else ! (OBC%segment(n)%direction == OBC_DIRECTION_W)
312  uh_center(i,j) = g%dy_Cu(i,j) * u(i,j,k) * h(i+1,j,k)
313  endif
314  enddo
315  endif
316  endif
317  enddo ; endif
318 
319  if (associated(obc)) then ; do n=1,obc%number_of_segments
320  if (.not. obc%segment(n)%on_pe) cycle
321  ! Now project thicknesses across cell-corner points in the OBCs. The two
322  ! projections have to occur in sequence and can not be combined easily.
323  i = obc%segment(n)%HI%IsdB ; j = obc%segment(n)%HI%JsdB
324  if (obc%segment(n)%is_N_or_S .and. (j >= jsq-1) .and. (j <= jeq+1)) then
325  do i = max(isq-1,obc%segment(n)%HI%IsdB), min(ieq+1,obc%segment(n)%HI%IedB)
326  if (obc%segment(n)%direction == obc_direction_n) then
327  if (area_h(i,j) + area_h(i+1,j) > 0.0) then
328  harea_u(i,j+1) = harea_u(i,j) * ((area_h(i,j+1) + area_h(i+1,j+1)) / &
329  (area_h(i,j) + area_h(i+1,j)))
330  else ; harea_u(i,j+1) = 0.0 ; endif
331  else ! (OBC%segment(n)%direction == OBC_DIRECTION_S)
332  if (area_h(i,j+1) + area_h(i+1,j+1) > 0.0) then
333  harea_u(i,j) = harea_u(i,j+1) * ((area_h(i,j) + area_h(i+1,j)) / &
334  (area_h(i,j+1) + area_h(i+1,j+1)))
335  else ; harea_u(i,j) = 0.0 ; endif
336  endif
337  enddo
338  elseif (obc%segment(n)%is_E_or_W .and. (i >= isq-1) .and. (i <= ieq+1)) then
339  do j = max(jsq-1,obc%segment(n)%HI%JsdB), min(jeq+1,obc%segment(n)%HI%JedB)
340  if (obc%segment(n)%direction == obc_direction_e) then
341  if (area_h(i,j) + area_h(i,j+1) > 0.0) then
342  harea_v(i+1,j) = harea_v(i,j) * ((area_h(i+1,j) + area_h(i+1,j+1)) / &
343  (area_h(i,j) + area_h(i,j+1)))
344  else ; harea_v(i+1,j) = 0.0 ; endif
345  else ! (OBC%segment(n)%direction == OBC_DIRECTION_W)
346  harea_v(i,j) = 0.5 * (area_h(i,j) + area_h(i,j+1)) * h(i,j+1,k)
347  if (area_h(i+1,j) + area_h(i+1,j+1) > 0.0) then
348  harea_v(i,j) = harea_v(i+1,j) * ((area_h(i,j) + area_h(i,j+1)) / &
349  (area_h(i+1,j) + area_h(i+1,j+1)))
350  else ; harea_v(i,j) = 0.0 ; endif
351  endif
352  enddo
353  endif
354  enddo ; endif
355 
356  do j=jsq-1,jeq+1 ; do i=isq-1,ieq+1
357  if (cs%no_slip ) then
358  relative_vorticity = (2.0-g%mask2dBu(i,j)) * (dvdx(i,j) - dudy(i,j)) * &
359  g%IareaBu(i,j)
360  else
361  relative_vorticity = g%mask2dBu(i,j) * (dvdx(i,j) - dudy(i,j)) * &
362  g%IareaBu(i,j)
363  endif
364  absolute_vorticity = g%CoriolisBu(i,j) + relative_vorticity
365  ih = 0.0
366  if (area_q(i,j) > 0.0) then
367  harea_q = (harea_u(i,j) + harea_u(i,j+1)) + (harea_v(i,j) + harea_v(i+1,j))
368  ih = area_q(i,j) / (harea_q + h_neglect*area_q(i,j))
369  endif
370  q(i,j) = absolute_vorticity * ih
371  abs_vort(i,j) = absolute_vorticity
372  ih_q(i,j) = ih
373 
374  if (cs%bound_Coriolis) then
375  fv1 = absolute_vorticity*v(i+1,j,k)
376  fv2 = absolute_vorticity*v(i,j,k)
377  fu1 = -absolute_vorticity*u(i,j+1,k)
378  fu2 = -absolute_vorticity*u(i,j,k)
379  if (fv1 > fv2) then
380  max_fvq(i,j) = fv1 ; min_fvq(i,j) = fv2
381  else
382  max_fvq(i,j) = fv2 ; min_fvq(i,j) = fv1
383  endif
384  if (fu1 > fu2) then
385  max_fuq(i,j) = fu1 ; min_fuq(i,j) = fu2
386  else
387  max_fuq(i,j) = fu2 ; min_fuq(i,j) = fu1
388  endif
389  endif
390 
391  if (cs%id_rv > 0) rv(i,j,k) = relative_vorticity
392  if (cs%id_PV > 0) pv(i,j,k) = q(i,j)
393  if (ASSOCIATED(ad%rv_x_v) .or. ASSOCIATED(ad%rv_x_u)) &
394  q2(i,j) = relative_vorticity * ih
395  enddo ; enddo
396 
397  ! a, b, c, and d are combinations of neighboring potential
398  ! vorticities which form the Arakawa and Hsu vorticity advection
399  ! scheme. All are defined at u grid points.
400 
401  if (cs%Coriolis_Scheme == arakawa_hsu90) then
402  do j=jsq,jeq+1
403  do i=is-1,ieq
404  a(i,j) = (q(i,j) + (q(i+1,j) + q(i,j-1))) * c1_12
405  d(i,j) = ((q(i,j) + q(i+1,j-1)) + q(i,j-1)) * c1_12
406  enddo
407  do i=isq,ieq
408  b(i,j) = (q(i,j) + (q(i-1,j) + q(i,j-1))) * c1_12
409  c(i,j) = ((q(i,j) + q(i-1,j-1)) + q(i,j-1)) * c1_12
410  enddo
411  enddo
412  elseif (cs%Coriolis_Scheme == arakawa_lamb81) then
413  do j=jsq,jeq+1 ; do i=isq,ieq+1
414  a(i-1,j) = (2.0*(q(i,j) + q(i-1,j-1)) + (q(i-1,j) + q(i,j-1))) * c1_24
415  d(i-1,j) = ((q(i,j) + q(i-1,j-1)) + 2.0*(q(i-1,j) + q(i,j-1))) * c1_24
416  b(i,j) = ((q(i,j) + q(i-1,j-1)) + 2.0*(q(i-1,j) + q(i,j-1))) * c1_24
417  c(i,j) = (2.0*(q(i,j) + q(i-1,j-1)) + (q(i-1,j) + q(i,j-1))) * c1_24
418  ep_u(i,j) = ((q(i,j) - q(i-1,j-1)) + (q(i-1,j) - q(i,j-1))) * c1_24
419  ep_v(i,j) = (-(q(i,j) - q(i-1,j-1)) + (q(i-1,j) - q(i,j-1))) * c1_24
420  enddo ; enddo
421  elseif (cs%Coriolis_Scheme == al_blend) then
422  fe_m2 = cs%F_eff_max_blend - 2.0
423  rat_lin = 1.5 * fe_m2 / max(cs%wt_lin_blend, 1.0e-16)
424 
425  ! This allows the code to always give Sadourny Energy
426  if (cs%F_eff_max_blend <= 2.0) then ; fe_m2 = -1. ; rat_lin = -1.0 ; endif
427 
428  do j=jsq,jeq+1 ; do i=isq,ieq+1
429  min_ihq = min(ih_q(i-1,j-1), ih_q(i,j-1), ih_q(i-1,j), ih_q(i,j))
430  max_ihq = max(ih_q(i-1,j-1), ih_q(i,j-1), ih_q(i-1,j), ih_q(i,j))
431  rat_m1 = 1.0e15
432  if (max_ihq < 1.0e15*min_ihq) rat_m1 = max_ihq / min_ihq - 1.0
433  ! The weights used here are designed to keep the effective Coriolis
434  ! acceleration from any one point on its neighbors within a factor
435  ! of F_eff_max. The minimum permitted value is 2 (the factor for
436  ! Sadourny's energy conserving scheme).
437 
438  ! Determine the relative weights of Arakawa & Lamb vs. Arakawa and Hsu.
439  if (rat_m1 <= fe_m2) then ; al_wt = 1.0
440  elseif (rat_m1 < 1.5*fe_m2) then ; al_wt = 3.0*fe_m2 / rat_m1 - 2.0
441  else ; al_wt = 0.0 ; endif
442 
443  ! Determine the relative weights of Sadourny Energy vs. the other two.
444  if (rat_m1 <= 1.5*fe_m2) then ; sad_wt = 0.0
445  elseif (rat_m1 <= rat_lin) then
446  sad_wt = 1.0 - (1.5*fe_m2) / rat_m1
447  elseif (rat_m1 < 2.0*rat_lin) then
448  sad_wt = 1.0 - (cs%wt_lin_blend / rat_lin) * (rat_m1 - 2.0*rat_lin)
449  else ; sad_wt = 1.0 ; endif
450 
451  a(i-1,j) = sad_wt * 0.25 * q(i-1,j) + (1.0 - sad_wt) * &
452  ( ((2.0-al_wt)* q(i-1,j) + al_wt*q(i,j-1)) + &
453  2.0 * (q(i,j) + q(i-1,j-1)) ) * c1_24
454  d(i-1,j) = sad_wt * 0.25 * q(i-1,j-1) + (1.0 - sad_wt) * &
455  ( ((2.0-al_wt)* q(i-1,j-1) + al_wt*q(i,j)) + &
456  2.0 * (q(i-1,j) + q(i,j-1)) ) * c1_24
457  b(i,j) = sad_wt * 0.25 * q(i,j) + (1.0 - sad_wt) * &
458  ( ((2.0-al_wt)* q(i,j) + al_wt*q(i-1,j-1)) + &
459  2.0 * (q(i-1,j) + q(i,j-1)) ) * c1_24
460  c(i,j) = sad_wt * 0.25 * q(i,j-1) + (1.0 - sad_wt) * &
461  ( ((2.0-al_wt)* q(i,j-1) + al_wt*q(i-1,j)) + &
462  2.0 * (q(i,j) + q(i-1,j-1)) ) * c1_24
463  ep_u(i,j) = al_wt * ((q(i,j) - q(i-1,j-1)) + (q(i-1,j) - q(i,j-1))) * c1_24
464  ep_v(i,j) = al_wt * (-(q(i,j) - q(i-1,j-1)) + (q(i-1,j) - q(i,j-1))) * c1_24
465  enddo ; enddo
466  endif
467 
468  if (cs%Coriolis_En_Dis) then
469  ! c1 = 1.0-1.5*RANGE ; c2 = 1.0-RANGE ; c3 = 2.0 ; slope = 0.5
470  c1 = 1.0-1.5*0.5 ; c2 = 1.0-0.5 ; c3 = 2.0 ; slope = 0.5
471 
472  do j=jsq,jeq+1 ; do i=is-1,ie
473  uhc = uh_center(i,j)
474  uhm = uh(i,j,k)
475  ! This sometimes matters with some types of open boundary conditions.
476  if (g%dy_Cu(i,j) == 0.0) uhc = uhm
477 
478  if (abs(uhc) < 0.1*abs(uhm)) then
479  uhm = 10.0*uhc
480  elseif (abs(uhc) > c1*abs(uhm)) then
481  if (abs(uhc) < c2*abs(uhm)) then ; uhc = (3.0*uhc+(1.0-c2*3.0)*uhm)
482  elseif (abs(uhc) <= c3*abs(uhm)) then ; uhc = uhm
483  else ; uhc = slope*uhc+(1.0-c3*slope)*uhm
484  endif
485  endif
486 
487  if (uhc > uhm) then
488  uh_min(i,j) = uhm ; uh_max(i,j) = uhc
489  else
490  uh_max(i,j) = uhm ; uh_min(i,j) = uhc
491  endif
492  enddo ; enddo
493  do j=js-1,je ; do i=isq,ieq+1
494  vhc = vh_center(i,j)
495  vhm = vh(i,j,k)
496  ! This sometimes matters with some types of open boundary conditions.
497  if (g%dx_Cv(i,j) == 0.0) vhc = vhm
498 
499  if (abs(vhc) < 0.1*abs(vhm)) then
500  vhm = 10.0*vhc
501  elseif (abs(vhc) > c1*abs(vhm)) then
502  if (abs(vhc) < c2*abs(vhm)) then ; vhc = (3.0*vhc+(1.0-c2*3.0)*vhm)
503  else if (abs(vhc) <= c3*abs(vhm)) then ; vhc = vhm
504  else ; vhc = slope*vhc+(1.0-c3*slope)*vhm
505  endif
506  endif
507 
508  if (vhc > vhm) then
509  vh_min(i,j) = vhm ; vh_max(i,j) = vhc
510  else
511  vh_max(i,j) = vhm ; vh_min(i,j) = vhc
512  endif
513  enddo ; enddo
514  endif
515 
516  ! Calculate KE and the gradient of KE
517  call gradke(u, v, h, ke, kex, key, k, obc, g, cs)
518 
519  ! Calculate the tendencies of zonal velocity due to the Coriolis
520  ! force and momentum advection. On a Cartesian grid, this is
521  ! CAu = q * vh - d(KE)/dx.
522  if (cs%Coriolis_Scheme == sadourny75_energy) then
523  if (cs%Coriolis_En_Dis) then
524  ! Energy dissipating biased scheme, Hallberg 200x
525  do j=js,je ; do i=isq,ieq
526  if (q(i,j)*u(i,j,k) == 0.0) then
527  temp1 = q(i,j) * ( (vh_max(i,j)+vh_max(i+1,j)) &
528  + (vh_min(i,j)+vh_min(i+1,j)) )*0.5
529  elseif (q(i,j)*u(i,j,k) < 0.0) then
530  temp1 = q(i,j) * (vh_max(i,j)+vh_max(i+1,j))
531  else
532  temp1 = q(i,j) * (vh_min(i,j)+vh_min(i+1,j))
533  endif
534  if (q(i,j-1)*u(i,j,k) == 0.0) then
535  temp2 = q(i,j-1) * ( (vh_max(i,j-1)+vh_max(i+1,j-1)) &
536  + (vh_min(i,j-1)+vh_min(i+1,j-1)) )*0.5
537  elseif (q(i,j-1)*u(i,j,k) < 0.0) then
538  temp2 = q(i,j-1) * (vh_max(i,j-1)+vh_max(i+1,j-1))
539  else
540  temp2 = q(i,j-1) * (vh_min(i,j-1)+vh_min(i+1,j-1))
541  endif
542  cau(i,j,k) = 0.25 * g%IdxCu(i,j) * (temp1 + temp2)
543  enddo ; enddo
544  else
545  ! Energy conserving scheme, Sadourny 1975
546  do j=js,je ; do i=isq,ieq
547  cau(i,j,k) = 0.25 * &
548  (q(i,j) * (vh(i+1,j,k) + vh(i,j,k)) + &
549  q(i,j-1) * (vh(i,j-1,k) + vh(i+1,j-1,k))) * g%IdxCu(i,j)
550  enddo ; enddo
551  endif
552  elseif (cs%Coriolis_Scheme == sadourny75_enstro) then
553  do j=js,je ; do i=isq,ieq
554  cau(i,j,k) = 0.125 * (g%IdxCu(i,j) * (q(i,j) + q(i,j-1))) * &
555  ((vh(i+1,j,k) + vh(i,j,k)) + (vh(i,j-1,k) + vh(i+1,j-1,k)))
556  enddo ; enddo
557  elseif ((cs%Coriolis_Scheme == arakawa_hsu90) .or. &
558  (cs%Coriolis_Scheme == arakawa_lamb81) .or. &
559  (cs%Coriolis_Scheme == al_blend)) then
560  ! (Global) Energy and (Local) Enstrophy conserving, Arakawa & Hsu 1990
561  do j=js,je ; do i=isq,ieq
562  cau(i,j,k) = ((a(i,j) * vh(i+1,j,k) + &
563  c(i,j) * vh(i,j-1,k)) &
564  + (b(i,j) * vh(i,j,k) + &
565  d(i,j) * vh(i+1,j-1,k))) * g%IdxCu(i,j)
566  enddo ; enddo
567  elseif (cs%Coriolis_Scheme == robust_enstro) then
568  ! An enstrophy conserving scheme robust to vanishing layers
569  ! Note: Heffs are in lieu of h_at_v that should be returned by the
570  ! continuity solver. AJA
571  do j=js,je ; do i=isq,ieq
572  heff1 = abs(vh(i,j,k)*g%IdxCv(i,j))/(eps_vel+abs(v(i,j,k)))
573  heff1 = max(heff1,min(h(i,j,k),h(i,j+1,k)))
574  heff1 = min(heff1,max(h(i,j,k),h(i,j+1,k)))
575  heff2 = abs(vh(i,j-1,k)*g%IdxCv(i,j-1))/(eps_vel+abs(v(i,j-1,k)))
576  heff2 = max(heff2,min(h(i,j-1,k),h(i,j,k)))
577  heff2 = min(heff2,max(h(i,j-1,k),h(i,j,k)))
578  heff3 = abs(vh(i+1,j,k)*g%IdxCv(i+1,j))/(eps_vel+abs(v(i+1,j,k)))
579  heff3 = max(heff3,min(h(i+1,j,k),h(i+1,j+1,k)))
580  heff3 = min(heff3,max(h(i+1,j,k),h(i+1,j+1,k)))
581  heff4 = abs(vh(i+1,j-1,k)*g%IdxCv(i+1,j-1))/(eps_vel+abs(v(i+1,j-1,k)))
582  heff4 = max(heff4,min(h(i+1,j-1,k),h(i+1,j,k)))
583  heff4 = min(heff4,max(h(i+1,j-1,k),h(i+1,j,k)))
584  if (cs%PV_Adv_Scheme == pv_adv_centered) then
585  cau(i,j,k) = 0.5*(abs_vort(i,j)+abs_vort(i,j-1)) * &
586  ((vh(i ,j ,k)+vh(i+1,j-1,k)) + &
587  (vh(i ,j-1,k)+vh(i+1,j ,k)) ) / &
588  (h_tiny +((heff1+heff4) +(heff2+heff3)) ) * g%IdxCu(i,j)
589  elseif (cs%PV_Adv_Scheme == pv_adv_upwind1) then
590  vheff = ((vh(i ,j ,k)+vh(i+1,j-1,k)) + &
591  (vh(i ,j-1,k)+vh(i+1,j ,k)) )
592  qvheff = 0.5*( (abs_vort(i,j)+abs_vort(i,j-1))*vheff &
593  -(abs_vort(i,j)-abs_vort(i,j-1))*abs(vheff) )
594  cau(i,j,k) = qvheff / &
595  (h_tiny +((heff1+heff4) +(heff2+heff3)) ) * g%IdxCu(i,j)
596  endif
597  enddo ; enddo
598  endif
599  ! Add in the additonal terms with Arakawa & Lamb.
600  if ((cs%Coriolis_Scheme == arakawa_lamb81) .or. &
601  (cs%Coriolis_Scheme == al_blend)) then ; do j=js,je ; do i=isq,ieq
602  cau(i,j,k) = cau(i,j,k) + &
603  (ep_u(i,j)*uh(i-1,j,k) - ep_u(i+1,j)*uh(i+1,j,k)) * g%IdxCu(i,j)
604  enddo ; enddo ; endif
605 
606 
607  if (cs%bound_Coriolis) then
608  do j=js,je ; do i=isq,ieq
609  max_fv = max(max_fvq(i,j),max_fvq(i,j-1))
610  min_fv = min(min_fvq(i,j),min_fvq(i,j-1))
611  ! CAu(I,j,k) = min( CAu(I,j,k), max_fv )
612  ! CAu(I,j,k) = max( CAu(I,j,k), min_fv )
613  if (cau(i,j,k) > max_fv) then
614  cau(i,j,k) = max_fv
615  else
616  if (cau(i,j,k) < min_fv) cau(i,j,k) = min_fv
617  endif
618  enddo ; enddo
619  endif
620 
621  ! Term - d(KE)/dx.
622  do j=js,je ; do i=isq,ieq
623  cau(i,j,k) = cau(i,j,k) - kex(i,j)
624  if (ASSOCIATED(ad%gradKEu)) ad%gradKEu(i,j,k) = -kex(i,j)
625  enddo ; enddo
626 
627 
628  ! Calculate the tendencies of meridional velocity due to the Coriolis
629  ! force and momentum advection. On a Cartesian grid, this is
630  ! CAv = - q * uh - d(KE)/dy.
631  if (cs%Coriolis_Scheme == sadourny75_energy) then
632  if (cs%Coriolis_En_Dis) then
633  ! Energy dissipating biased scheme, Hallberg 200x
634  do j=jsq,jeq ; do i=is,ie
635  if (q(i-1,j)*v(i,j,k) == 0.0) then
636  temp1 = q(i-1,j) * ( (uh_max(i-1,j)+uh_max(i-1,j+1)) &
637  + (uh_min(i-1,j)+uh_min(i-1,j+1)) )*0.5
638  elseif (q(i-1,j)*v(i,j,k) > 0.0) then
639  temp1 = q(i-1,j) * (uh_max(i-1,j)+uh_max(i-1,j+1))
640  else
641  temp1 = q(i-1,j) * (uh_min(i-1,j)+uh_min(i-1,j+1))
642  endif
643  if (q(i,j)*v(i,j,k) == 0.0) then
644  temp2 = q(i,j) * ( (uh_max(i,j)+uh_max(i,j+1)) &
645  + (uh_min(i,j)+uh_min(i,j+1)) )*0.5
646  elseif (q(i,j)*v(i,j,k) > 0.0) then
647  temp2 = q(i,j) * (uh_max(i,j)+uh_max(i,j+1))
648  else
649  temp2 = q(i,j) * (uh_min(i,j)+uh_min(i,j+1))
650  endif
651  cav(i,j,k) = - 0.25 * g%IdyCv(i,j) * (temp1 + temp2)
652  enddo ; enddo
653  else
654  ! Energy conserving scheme, Sadourny 1975
655  do j=jsq,jeq ; do i=is,ie
656  cav(i,j,k) = - 0.25* &
657  (q(i-1,j)*(uh(i-1,j,k) + uh(i-1,j+1,k)) + &
658  q(i,j)*(uh(i,j,k) + uh(i,j+1,k))) * g%IdyCv(i,j)
659  enddo ; enddo
660  endif
661  elseif (cs%Coriolis_Scheme == sadourny75_enstro) then
662  do j=jsq,jeq ; do i=is,ie
663  cav(i,j,k) = -0.125 * (g%IdyCv(i,j) * (q(i-1,j) + q(i,j))) * &
664  ((uh(i-1,j,k) + uh(i-1,j+1,k)) + (uh(i,j,k) + uh(i,j+1,k)))
665  enddo ; enddo
666  elseif ((cs%Coriolis_Scheme == arakawa_hsu90) .or. &
667  (cs%Coriolis_Scheme == arakawa_lamb81) .or. &
668  (cs%Coriolis_Scheme == al_blend)) then
669  ! (Global) Energy and (Local) Enstrophy conserving, Arakawa & Hsu 1990
670  do j=jsq,jeq ; do i=is,ie
671  cav(i,j,k) = - ((a(i-1,j) * uh(i-1,j,k) + &
672  c(i,j+1) * uh(i,j+1,k)) &
673  + (b(i,j) * uh(i,j,k) + &
674  d(i-1,j+1) * uh(i-1,j+1,k))) * g%IdyCv(i,j)
675  enddo ; enddo
676  elseif (cs%Coriolis_Scheme == robust_enstro) then
677  ! An enstrophy conserving scheme robust to vanishing layers
678  ! Note: Heffs are in lieu of h_at_u that should be returned by the
679  ! continuity solver. AJA
680  do j=jsq,jeq ; do i=is,ie
681  heff1 = abs(uh(i,j,k)*g%IdyCu(i,j))/(eps_vel+abs(u(i,j,k)))
682  heff1 = max(heff1,min(h(i,j,k),h(i+1,j,k)))
683  heff1 = min(heff1,max(h(i,j,k),h(i+1,j,k)))
684  heff2 = abs(uh(i-1,j,k)*g%IdyCu(i-1,j))/(eps_vel+abs(u(i-1,j,k)))
685  heff2 = max(heff2,min(h(i-1,j,k),h(i,j,k)))
686  heff2 = min(heff2,max(h(i-1,j,k),h(i,j,k)))
687  heff3 = abs(uh(i,j+1,k)*g%IdyCu(i,j+1))/(eps_vel+abs(u(i,j+1,k)))
688  heff3 = max(heff3,min(h(i,j+1,k),h(i+1,j+1,k)))
689  heff3 = min(heff3,max(h(i,j+1,k),h(i+1,j+1,k)))
690  heff4 = abs(uh(i-1,j+1,k)*g%IdyCu(i-1,j+1))/(eps_vel+abs(u(i-1,j+1,k)))
691  heff4 = max(heff4,min(h(i-1,j+1,k),h(i,j+1,k)))
692  heff4 = min(heff4,max(h(i-1,j+1,k),h(i,j+1,k)))
693  if (cs%PV_Adv_Scheme == pv_adv_centered) then
694  cav(i,j,k) = - 0.5*(abs_vort(i,j)+abs_vort(i-1,j)) * &
695  ((uh(i ,j ,k)+uh(i-1,j+1,k)) + &
696  (uh(i-1,j ,k)+uh(i ,j+1,k)) ) / &
697  (h_tiny + ((heff1+heff4) +(heff2+heff3)) ) * g%IdyCv(i,j)
698  elseif (cs%PV_Adv_Scheme == pv_adv_upwind1) then
699  uheff = ((uh(i ,j ,k)+uh(i-1,j+1,k)) + &
700  (uh(i-1,j ,k)+uh(i ,j+1,k)) )
701  quheff = 0.5*( (abs_vort(i,j)+abs_vort(i-1,j))*uheff &
702  -(abs_vort(i,j)-abs_vort(i-1,j))*abs(uheff) )
703  cav(i,j,k) = - quheff / &
704  (h_tiny + ((heff1+heff4) +(heff2+heff3)) ) * g%IdyCv(i,j)
705  endif
706  enddo ; enddo
707  endif
708  ! Add in the additonal terms with Arakawa & Lamb.
709  if ((cs%Coriolis_Scheme == arakawa_lamb81) .or. &
710  (cs%Coriolis_Scheme == al_blend)) then ; do j=jsq,jeq ; do i=is,ie
711  cav(i,j,k) = cav(i,j,k) + &
712  (ep_v(i,j)*vh(i,j-1,k) - ep_v(i,j+1)*vh(i,j+1,k)) * g%IdyCv(i,j)
713  enddo ; enddo ; endif
714 
715  if (cs%bound_Coriolis) then
716  do j=jsq,jeq ; do i=is,ie
717  max_fu = max(max_fuq(i,j),max_fuq(i-1,j))
718  min_fu = min(min_fuq(i,j),min_fuq(i-1,j))
719  if (cav(i,j,k) > max_fu) then
720  cav(i,j,k) = max_fu
721  else
722  if (cav(i,j,k) < min_fu) cav(i,j,k) = min_fu
723  endif
724  enddo ; enddo
725  endif
726 
727  ! Term - d(KE)/dy.
728  do j=jsq,jeq ; do i=is,ie
729  cav(i,j,k) = cav(i,j,k) - key(i,j)
730  if (ASSOCIATED(ad%gradKEv)) ad%gradKEv(i,j,k) = -key(i,j)
731  enddo ; enddo
732 
733  if (ASSOCIATED(ad%rv_x_u) .or. ASSOCIATED(ad%rv_x_v)) then
734  ! Calculate the Coriolis-like acceleration due to relative vorticity.
735  if (cs%Coriolis_Scheme == sadourny75_energy) then
736  if (ASSOCIATED(ad%rv_x_u)) then
737  do j=jsq,jeq ; do i=is,ie
738  ad%rv_x_u(i,j,k) = - 0.25* &
739  (q2(i-1,j)*(uh(i-1,j,k) + uh(i-1,j+1,k)) + &
740  q2(i,j)*(uh(i,j,k) + uh(i,j+1,k))) * g%IdyCv(i,j)
741  enddo ; enddo
742  endif
743 
744  if (ASSOCIATED(ad%rv_x_v)) then
745  do j=js,je ; do i=isq,ieq
746  ad%rv_x_v(i,j,k) = 0.25 * &
747  (q2(i,j) * (vh(i+1,j,k) + vh(i,j,k)) + &
748  q2(i,j-1) * (vh(i,j-1,k) + vh(i+1,j-1,k))) * g%IdxCu(i,j)
749  enddo ; enddo
750  endif
751  else
752  if (ASSOCIATED(ad%rv_x_u)) then
753  do j=jsq,jeq ; do i=is,ie
754  ad%rv_x_u(i,j,k) = -g%IdyCv(i,j) * c1_12 * &
755  ((q2(i,j) + q2(i-1,j) + q2(i-1,j-1)) * uh(i-1,j,k) + &
756  (q2(i-1,j) + q2(i,j) + q2(i,j-1)) * uh(i,j,k) + &
757  (q2(i-1,j) + q2(i,j+1) + q2(i,j)) * uh(i,j+1,k) + &
758  (q2(i,j) + q2(i-1,j+1) + q2(i-1,j)) * uh(i-1,j+1,k))
759  enddo ; enddo
760  endif
761 
762  if (ASSOCIATED(ad%rv_x_v)) then
763  do j=js,je ; do i=isq,ieq
764  ad%rv_x_v(i,j,k) = g%IdxCu(i,j) * c1_12 * &
765  ((q2(i+1,j) + q2(i,j) + q2(i,j-1)) * vh(i+1,j,k) + &
766  (q2(i-1,j) + q2(i,j) + q2(i,j-1)) * vh(i,j,k) + &
767  (q2(i-1,j-1) + q2(i,j) + q2(i,j-1)) * vh(i,j-1,k) + &
768  (q2(i+1,j-1) + q2(i,j) + q2(i,j-1)) * vh(i+1,j-1,k))
769  enddo ; enddo
770  endif
771  endif
772  endif
773 
774  enddo ! k-loop.
775 
776  ! Here the various Coriolis-related derived quantities are offered for averaging.
777  if (query_averaging_enabled(cs%diag)) then
778  if (cs%id_rv > 0) call post_data(cs%id_rv, rv, cs%diag)
779  if (cs%id_PV > 0) call post_data(cs%id_PV, pv, cs%diag)
780  if (cs%id_gKEu>0) call post_data(cs%id_gKEu, ad%gradKEu, cs%diag)
781  if (cs%id_gKEv>0) call post_data(cs%id_gKEv, ad%gradKEv, cs%diag)
782  if (cs%id_rvxu > 0) call post_data(cs%id_rvxu, ad%rv_x_u, cs%diag)
783  if (cs%id_rvxv > 0) call post_data(cs%id_rvxv, ad%rv_x_v, cs%diag)
784  endif
785 
Here is the call graph for this function:
Here is the caller graph for this function:

◆ coriolisadv_end()

subroutine, public mom_coriolisadv::coriolisadv_end ( type(coriolisadv_cs), pointer  CS)

Destructor for coriolisadv_cs.

Parameters
csControl structure fro MOM_CoriolisAdv

Definition at line 1045 of file MOM_CoriolisAdv.F90.

1045  type(coriolisadv_cs), pointer :: cs !< Control structure fro MOM_CoriolisAdv
1046  deallocate(cs)

◆ coriolisadv_init()

subroutine, public mom_coriolisadv::coriolisadv_init ( type(time_type), intent(in), target  Time,
type(ocean_grid_type), intent(in)  G,
type(param_file_type), intent(in)  param_file,
type(diag_ctrl), intent(inout), target  diag,
type(accel_diag_ptrs), intent(inout), target  AD,
type(coriolisadv_cs), pointer  CS 
)

Initializes the control structure for coriolisadv_cs.

Parameters
[in]timeCurrent model time
[in]gOcean grid structure
[in]param_fileRuntime parameter handles
[in,out]diagDiagnostics control structure
[in,out]adStrorage for acceleration diagnostics
csControl structure fro MOM_CoriolisAdv

Definition at line 875 of file MOM_CoriolisAdv.F90.

References al_blend, al_blend_string, arakawa_hsu90, arakawa_hsu_string, arakawa_lamb81, arakawa_lamb_string, ke_arakawa, ke_arakawa_string, ke_gudonov, ke_gudonov_string, ke_simple_gudonov, ke_simple_gudonov_string, mom_error_handler::mom_error(), mom_error_handler::mom_mesg(), pv_adv_centered, pv_adv_centered_string, pv_adv_upwind1, pv_adv_upwind1_string, mom_diag_mediator::register_diag_field(), robust_enstro, robust_enstro_string, sadourny75_energy, sadourny75_energy_string, sadourny75_enstro, sadourny75_enstro_string, and mom_string_functions::uppercase().

875  type(time_type), target, intent(in) :: time !< Current model time
876  type(ocean_grid_type), intent(in) :: g !< Ocean grid structure
877  type(param_file_type), intent(in) :: param_file !< Runtime parameter handles
878  type(diag_ctrl), target, intent(inout) :: diag !< Diagnostics control structure
879  type(accel_diag_ptrs), target, intent(inout) :: ad !< Strorage for acceleration diagnostics
880  type(coriolisadv_cs), pointer :: cs !< Control structure fro MOM_CoriolisAdv
881  ! Local variables
882 ! This include declares and sets the variable "version".
883 #include "version_variable.h"
884  character(len=40) :: mdl = "MOM_CoriolisAdv" ! This module's name.
885  character(len=20) :: tmpstr
886  character(len=400) :: mesg
887  integer :: isd, ied, jsd, jed, isdb, iedb, jsdb, jedb, nz
888 
889  isd = g%isd ; ied = g%ied ; jsd = g%jsd ; jed = g%jed ; nz = g%ke
890  isdb = g%IsdB ; iedb = g%IedB ; jsdb = g%JsdB ; jedb = g%JedB
891 
892  if (associated(cs)) then
893  call mom_error(warning, "CoriolisAdv_init called with associated control structure.")
894  return
895  endif
896  allocate(cs)
897 
898  cs%diag => diag ; cs%Time => time
899 
900  ! Read all relevant parameters and write them to the model log.
901  call log_version(param_file, mdl, version, "")
902  call get_param(param_file, mdl, "NOSLIP", cs%no_slip, &
903  "If true, no slip boundary conditions are used; otherwise \n"//&
904  "free slip boundary conditions are assumed. The \n"//&
905  "implementation of the free slip BCs on a C-grid is much \n"//&
906  "cleaner than the no slip BCs. The use of free slip BCs \n"//&
907  "is strongly encouraged, and no slip BCs are not used with \n"//&
908  "the biharmonic viscosity.", default=.false.)
909 
910  call get_param(param_file, mdl, "CORIOLIS_EN_DIS", cs%Coriolis_En_Dis, &
911  "If true, two estimates of the thickness fluxes are used \n"//&
912  "to estimate the Coriolis term, and the one that \n"//&
913  "dissipates energy relative to the other one is used.", &
914  default=.false.)
915 
916  ! Set %Coriolis_Scheme
917  ! (Select the baseline discretization for the Coriolis term)
918  call get_param(param_file, mdl, "CORIOLIS_SCHEME", tmpstr, &
919  "CORIOLIS_SCHEME selects the discretization for the \n"//&
920  "Coriolis terms. Valid values are: \n"//&
921  "\t SADOURNY75_ENERGY - Sadourny, 1975; energy cons. \n"//&
922  "\t ARAKAWA_HSU90 - Arakawa & Hsu, 1990 \n"//&
923  "\t SADOURNY75_ENSTRO - Sadourny, 1975; enstrophy cons. \n"//&
924  "\t ARAKAWA_LAMB81 - Arakawa & Lamb, 1981; En. + Enst.\n"//&
925  "\t ARAKAWA_LAMB_BLEND - A blend of Arakawa & Lamb with \n"//&
926  "\t Arakawa & Hsu and Sadourny energy", &
927  default=sadourny75_energy_string)
928  tmpstr = uppercase(tmpstr)
929  select case (tmpstr)
930  case (sadourny75_energy_string)
931  cs%Coriolis_Scheme = sadourny75_energy
932  case (arakawa_hsu_string)
933  cs%Coriolis_Scheme = arakawa_hsu90
934  case (sadourny75_enstro_string)
935  cs%Coriolis_Scheme = sadourny75_enstro
936  case (arakawa_lamb_string)
937  cs%Coriolis_Scheme = arakawa_lamb81
938  case (al_blend_string)
939  cs%Coriolis_Scheme = al_blend
940  case (robust_enstro_string)
941  cs%Coriolis_Scheme = robust_enstro
942  cs%Coriolis_En_Dis = .false.
943  case default
944  call mom_mesg('CoriolisAdv_init: Coriolis_Scheme ="'//trim(tmpstr)//'"', 0)
945  call mom_error(fatal, "CoriolisAdv_init: Unrecognized setting "// &
946  "#define CORIOLIS_SCHEME "//trim(tmpstr)//" found in input file.")
947  end select
948  if (cs%Coriolis_Scheme == al_blend) then
949  call get_param(param_file, mdl, "CORIOLIS_BLEND_WT_LIN", cs%wt_lin_blend, &
950  "A weighting value for the ratio of inverse thicknesses, \n"//&
951  "beyond which the blending between Sadourny Energy and \n"//&
952  "Arakawa & Hsu goes linearly to 0 when CORIOLIS_SCHEME \n"//&
953  "is ARAWAKA_LAMB_BLEND. This must be between 1 and 1e-16.", &
954  units="nondim", default=0.125)
955  call get_param(param_file, mdl, "CORIOLIS_BLEND_F_EFF_MAX", cs%F_eff_max_blend, &
956  "The factor by which the maximum effective Coriolis \n"//&
957  "acceleration from any point can be increased when \n"//&
958  "blending different discretizations with the \n"//&
959  "ARAKAWA_LAMB_BLEND Coriolis scheme. This must be \n"//&
960  "greater than 2.0 (the max value for Sadourny energy).", &
961  units="nondim", default=4.0)
962  cs%wt_lin_blend = min(1.0, max(cs%wt_lin_blend,1e-16))
963  if (cs%F_eff_max_blend < 2.0) call mom_error(warning, "CoriolisAdv_init: "//&
964  "CORIOLIS_BLEND_F_EFF_MAX should be at least 2.")
965  endif
966 
967  mesg = "If true, the Coriolis terms at u-points are bounded by \n"//&
968  "the four estimates of (f+rv)v from the four neighboring \n"//&
969  "v-points, and similarly at v-points."
970  if (cs%Coriolis_En_Dis .and. (cs%Coriolis_Scheme == sadourny75_energy)) then
971  mesg = trim(mesg)//" This option is \n"//&
972  "always effectively false with CORIOLIS_EN_DIS defined and \n"//&
973  "CORIOLIS_SCHEME set to "//trim(sadourny75_energy_string)//"."
974  else
975  mesg = trim(mesg)//" This option would \n"//&
976  "have no effect on the SADOURNY Coriolis scheme if it \n"//&
977  "were possible to use centered difference thickness fluxes."
978  endif
979  call get_param(param_file, mdl, "BOUND_CORIOLIS", cs%bound_Coriolis, mesg, &
980  default=.false.)
981  if ((cs%Coriolis_En_Dis .and. (cs%Coriolis_Scheme == sadourny75_energy)) .or. &
982  (cs%Coriolis_Scheme == robust_enstro)) cs%bound_Coriolis = .false.
983 
984  ! Set KE_Scheme (selects discretization of KE)
985  call get_param(param_file, mdl, "KE_SCHEME", tmpstr, &
986  "KE_SCHEME selects the discretization for acceleration \n"//&
987  "due to the kinetic energy gradient. Valid values are: \n"//&
988  "\t KE_ARAKAWA, KE_SIMPLE_GUDONOV, KE_GUDONOV", &
989  default=ke_arakawa_string)
990  tmpstr = uppercase(tmpstr)
991  select case (tmpstr)
992  case (ke_arakawa_string); cs%KE_Scheme = ke_arakawa
993  case (ke_simple_gudonov_string); cs%KE_Scheme = ke_simple_gudonov
994  case (ke_gudonov_string); cs%KE_Scheme = ke_gudonov
995  case default
996  call mom_mesg('CoriolisAdv_init: KE_Scheme ="'//trim(tmpstr)//'"', 0)
997  call mom_error(fatal, "CoriolisAdv_init: "// &
998  "#define KE_SCHEME "//trim(tmpstr)//" in input file is invalid.")
999  end select
1000 
1001  ! Set PV_Adv_Scheme (selects discretization of PV advection)
1002  call get_param(param_file, mdl, "PV_ADV_SCHEME", tmpstr, &
1003  "PV_ADV_SCHEME selects the discretization for PV \n"//&
1004  "advection. Valid values are: \n"//&
1005  "\t PV_ADV_CENTERED - centered (aka Sadourny, 75) \n"//&
1006  "\t PV_ADV_UPWIND1 - upwind, first order", &
1007  default=pv_adv_centered_string)
1008  select case (uppercase(tmpstr))
1009  case (pv_adv_centered_string)
1010  cs%PV_Adv_Scheme = pv_adv_centered
1011  case (pv_adv_upwind1_string)
1012  cs%PV_Adv_Scheme = pv_adv_upwind1
1013  case default
1014  call mom_mesg('CoriolisAdv_init: PV_Adv_Scheme ="'//trim(tmpstr)//'"', 0)
1015  call mom_error(fatal, "CoriolisAdv_init: "// &
1016  "#DEFINE PV_ADV_SCHEME in input file is invalid.")
1017  end select
1018 
1019  cs%id_rv = register_diag_field('ocean_model', 'RV', diag%axesBL, time, &
1020  'Relative Vorticity', 'second-1')
1021 
1022  cs%id_PV = register_diag_field('ocean_model', 'PV', diag%axesBL, time, &
1023  'Potential Vorticity', 'meter-1 second-1')
1024 
1025  cs%id_gKEu = register_diag_field('ocean_model', 'gKEu', diag%axesCuL, time, &
1026  'Zonal Acceleration from Grad. Kinetic Energy', 'meter-1 second-2')
1027  if (cs%id_gKEu > 0) call safe_alloc_ptr(ad%gradKEu,isdb,iedb,jsd,jed,nz)
1028 
1029  cs%id_gKEv = register_diag_field('ocean_model', 'gKEv', diag%axesCvL, time, &
1030  'Meridional Acceleration from Grad. Kinetic Energy', 'meter-1 second-2')
1031  if (cs%id_gKEv > 0) call safe_alloc_ptr(ad%gradKEv,isd,ied,jsdb,jedb,nz)
1032 
1033  cs%id_rvxu = register_diag_field('ocean_model', 'rvxu', diag%axesCvL, time, &
1034  'Meridional Acceleration from Relative Vorticity', 'meter-1 second-2')
1035  if (cs%id_rvxu > 0) call safe_alloc_ptr(ad%rv_x_u,isd,ied,jsdb,jedb,nz)
1036 
1037  cs%id_rvxv = register_diag_field('ocean_model', 'rvxv', diag%axesCuL, time, &
1038  'Zonal Acceleration from Relative Vorticity', 'meter-1 second-2')
1039  if (cs%id_rvxv > 0) call safe_alloc_ptr(ad%rv_x_v,isdb,iedb,jsd,jed,nz)
1040 
Here is the call graph for this function:

◆ gradke()

subroutine mom_coriolisadv::gradke ( real, dimension( g %isdb: g %iedb, g %jsd: g %jed, g %ke), intent(in)  u,
real, dimension( g %isd: g %ied, g %jsdb: g %jedb, g %ke), intent(in)  v,
real, dimension( g %isd: g %ied, g %jsd: g %jed, g %ke), intent(in)  h,
real, dimension( g %isd: g %ied , g %jsd: g %jed ), intent(out)  KE,
real, dimension( g %isdb: g %iedb, g %jsd: g %jed ), intent(out)  KEx,
real, dimension( g %isd: g %ied , g %jsdb: g %jedb), intent(out)  KEy,
integer, intent(in)  k,
type(ocean_obc_type), pointer  OBC,
type(ocean_grid_type), intent(in)  G,
type(coriolisadv_cs), pointer  CS 
)
private

Calculates the acceleration due to the gradient of kinetic energy.

Parameters
[in]gOcen grid structure
[in]uZonal velocity (m/s)
[in]vMeridional velocity (m/s)
[in]hLayer thickness (m or kg/m2)
[out]keKinetic energy (m2/s2)
[out]kexZonal acceleration due to kinetic energy gradient (m/s2)
[out]keyMeridional acceleration due to kinetic energy gradient (m/s2)
[in]kLayer number to calculate for
obcOpen boundary control structure
csControl structure for MOM_CoriolisAdv

Definition at line 791 of file MOM_CoriolisAdv.F90.

References ke_arakawa, ke_gudonov, and ke_simple_gudonov.

Referenced by coradcalc().

791  type(ocean_grid_type), intent(in) :: g !< Ocen grid structure
792  real, dimension(SZIB_(G),SZJ_(G),SZK_(G)), intent(in) :: u !< Zonal velocity (m/s)
793  real, dimension(SZI_(G),SZJB_(G),SZK_(G)), intent(in) :: v !< Meridional velocity (m/s)
794  real, dimension(SZI_(G),SZJ_(G),SZK_(G)), intent(in) :: h !< Layer thickness (m or kg/m2)
795  real, dimension(SZI_(G) ,SZJ_(G) ), intent(out) :: ke !< Kinetic energy (m2/s2)
796  real, dimension(SZIB_(G),SZJ_(G) ), intent(out) :: kex !< Zonal acceleration due to kinetic
797  !! energy gradient (m/s2)
798  real, dimension(SZI_(G) ,SZJB_(G)), intent(out) :: key !< Meridional acceleration due to kinetic
799  !! energy gradient (m/s2)
800  integer, intent(in) :: k !< Layer number to calculate for
801  type(ocean_obc_type), pointer :: obc !< Open boundary control structure
802  type(coriolisadv_cs), pointer :: cs !< Control structure for MOM_CoriolisAdv
803  ! Local variables
804  real :: um, up, vm, vp ! Temporary variables with units of m s-1.
805  real :: um2, up2, vm2, vp2 ! Temporary variables with units of m2 s-2.
806  real :: um2a, up2a, vm2a, vp2a ! Temporary variables with units of m4 s-2.
807  integer :: i, j, is, ie, js, je, isq, ieq, jsq, jeq, nz, n
808 
809  is = g%isc ; ie = g%iec ; js = g%jsc ; je = g%jec ; nz = g%ke
810  isq = g%IscB ; ieq = g%IecB ; jsq = g%JscB ; jeq = g%JecB
811 
812 
813  ! Calculate KE (Kinetic energy for use in the -grad(KE) acceleration term).
814  if (cs%KE_Scheme.eq.ke_arakawa) then
815  ! The following calculation of Kinetic energy includes the metric terms
816  ! identified in Arakawa & Lamb 1982 as important for KE conservation. It
817  ! also includes the possibility of partially-blocked tracer cell faces.
818  do j=jsq,jeq+1 ; do i=isq,ieq+1
819  ke(i,j) = ( ( g%areaCu( i ,j)*(u( i ,j,k)*u( i ,j,k)) &
820  +g%areaCu(i-1,j)*(u(i-1,j,k)*u(i-1,j,k)) ) &
821  +( g%areaCv(i, j )*(v(i, j ,k)*v(i, j ,k)) &
822  +g%areaCv(i,j-1)*(v(i,j-1,k)*v(i,j-1,k)) ) &
823  )*0.25*g%IareaT(i,j)
824  enddo ; enddo
825  elseif (cs%KE_Scheme.eq.ke_simple_gudonov) then
826  ! The following discretization of KE is based on the one-dimensinal Gudonov
827  ! scheme which does not take into account any geometric factors
828  do j=jsq,jeq+1 ; do i=isq,ieq+1
829  up = 0.5*( u(i-1,j,k) + abs( u(i-1,j,k) ) ) ; up2 = up*up
830  um = 0.5*( u( i ,j,k) - abs( u( i ,j,k) ) ) ; um2 = um*um
831  vp = 0.5*( v(i,j-1,k) + abs( v(i,j-1,k) ) ) ; vp2 = vp*vp
832  vm = 0.5*( v(i, j ,k) - abs( v(i, j ,k) ) ) ; vm2 = vm*vm
833  ke(i,j) = ( max(up2,um2) + max(vp2,vm2) ) *0.5
834  enddo ; enddo
835  elseif (cs%KE_Scheme.eq.ke_gudonov) then
836  ! The following discretization of KE is based on the one-dimensinal Gudonov
837  ! scheme but has been adapted to take horizontal grid factors into account
838  do j=jsq,jeq+1 ; do i=isq,ieq+1
839  up = 0.5*( u(i-1,j,k) + abs( u(i-1,j,k) ) ) ; up2a = up*up*g%areaCu(i-1,j)
840  um = 0.5*( u( i ,j,k) - abs( u( i ,j,k) ) ) ; um2a = um*um*g%areaCu( i ,j)
841  vp = 0.5*( v(i,j-1,k) + abs( v(i,j-1,k) ) ) ; vp2a = vp*vp*g%areaCv(i,j-1)
842  vm = 0.5*( v(i, j ,k) - abs( v(i, j ,k) ) ) ; vm2a = vm*vm*g%areaCv(i, j )
843  ke(i,j) = ( max(um2a,up2a) + max(vm2a,vp2a) )*0.5*g%IareaT(i,j)
844  enddo ; enddo
845  endif
846 
847  ! Term - d(KE)/dx.
848  do j=js,je ; do i=isq,ieq
849  kex(i,j) = (ke(i+1,j) - ke(i,j)) * g%IdxCu(i,j)
850  enddo ; enddo
851 
852  ! Term - d(KE)/dy.
853  do j=jsq,jeq ; do i=is,ie
854  key(i,j) = (ke(i,j+1) - ke(i,j)) * g%IdyCv(i,j)
855  enddo ; enddo
856 
857  if (associated(obc)) then
858  do n=1,obc%number_of_segments
859  if (obc%segment(n)%is_N_or_S) then
860  do i=obc%segment(n)%HI%isd,obc%segment(n)%HI%ied
861  key(i,obc%segment(n)%HI%JsdB) = 0.
862  enddo
863  elseif (obc%segment(n)%is_E_or_W) then
864  do j=obc%segment(n)%HI%jsd,obc%segment(n)%HI%jed
865  kex(obc%segment(n)%HI%IsdB,j) = 0.
866  enddo
867  endif
868  enddo
869  endif
870 
Here is the caller graph for this function:

Variable Documentation

◆ al_blend

integer, parameter mom_coriolisadv::al_blend = 6
private

Definition at line 83 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

83 integer, parameter :: al_blend = 6

◆ al_blend_string

character*(20), parameter mom_coriolisadv::al_blend_string = "ARAKAWA_LAMB_BLEND"
private

Definition at line 89 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

89 character*(20), parameter :: AL_BLEND_STRING = "ARAKAWA_LAMB_BLEND"

◆ arakawa_hsu90

integer, parameter mom_coriolisadv::arakawa_hsu90 = 2
private

Definition at line 79 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

79 integer, parameter :: arakawa_hsu90 = 2

◆ arakawa_hsu_string

character*(20), parameter mom_coriolisadv::arakawa_hsu_string = "ARAKAWA_HSU90"
private

Definition at line 85 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

85 character*(20), parameter :: ARAKAWA_HSU_STRING = "ARAKAWA_HSU90"

◆ arakawa_lamb81

integer, parameter mom_coriolisadv::arakawa_lamb81 = 5
private

Definition at line 82 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

82 integer, parameter :: arakawa_lamb81 = 5

◆ arakawa_lamb_string

character*(20), parameter mom_coriolisadv::arakawa_lamb_string = "ARAKAWA_LAMB81"
private

Definition at line 88 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

88 character*(20), parameter :: ARAKAWA_LAMB_STRING = "ARAKAWA_LAMB81"

◆ ke_arakawa

integer, parameter mom_coriolisadv::ke_arakawa = 10
private

Definition at line 91 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init(), and gradke().

91 integer, parameter :: ke_arakawa = 10

◆ ke_arakawa_string

character*(20), parameter mom_coriolisadv::ke_arakawa_string = "KE_ARAKAWA"
private

Definition at line 94 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

94 character*(20), parameter :: KE_ARAKAWA_STRING = "KE_ARAKAWA"

◆ ke_gudonov

integer, parameter mom_coriolisadv::ke_gudonov = 12
private

Definition at line 93 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init(), and gradke().

93 integer, parameter :: ke_gudonov = 12

◆ ke_gudonov_string

character*(20), parameter mom_coriolisadv::ke_gudonov_string = "KE_GUDONOV"
private

Definition at line 96 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

96 character*(20), parameter :: KE_GUDONOV_STRING = "KE_GUDONOV"

◆ ke_simple_gudonov

integer, parameter mom_coriolisadv::ke_simple_gudonov = 11
private

Definition at line 92 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init(), and gradke().

92 integer, parameter :: ke_simple_gudonov = 11

◆ ke_simple_gudonov_string

character*(20), parameter mom_coriolisadv::ke_simple_gudonov_string = "KE_SIMPLE_GUDONOV"
private

Definition at line 95 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

95 character*(20), parameter :: KE_SIMPLE_GUDONOV_STRING = "KE_SIMPLE_GUDONOV"

◆ pv_adv_centered

integer, parameter mom_coriolisadv::pv_adv_centered = 21
private

Definition at line 98 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

98 integer, parameter :: pv_adv_centered = 21

◆ pv_adv_centered_string

character*(20), parameter mom_coriolisadv::pv_adv_centered_string = "PV_ADV_CENTERED"
private

Definition at line 100 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

100 character*(20), parameter :: PV_ADV_CENTERED_STRING = "PV_ADV_CENTERED"

◆ pv_adv_upwind1

integer, parameter mom_coriolisadv::pv_adv_upwind1 = 22
private

Definition at line 99 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

99 integer, parameter :: pv_adv_upwind1 = 22

◆ pv_adv_upwind1_string

character*(20), parameter mom_coriolisadv::pv_adv_upwind1_string = "PV_ADV_UPWIND1"
private

Definition at line 101 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

101 character*(20), parameter :: PV_ADV_UPWIND1_STRING = "PV_ADV_UPWIND1"

◆ robust_enstro

integer, parameter mom_coriolisadv::robust_enstro = 3
private

Definition at line 80 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

80 integer, parameter :: robust_enstro = 3

◆ robust_enstro_string

character*(20), parameter mom_coriolisadv::robust_enstro_string = "ROBUST_ENSTRO"
private

Definition at line 86 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

86 character*(20), parameter :: ROBUST_ENSTRO_STRING = "ROBUST_ENSTRO"

◆ sadourny75_energy

integer, parameter mom_coriolisadv::sadourny75_energy = 1

Definition at line 78 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

78 integer, parameter :: sadourny75_energy = 1

◆ sadourny75_energy_string

character*(20), parameter mom_coriolisadv::sadourny75_energy_string = "SADOURNY75_ENERGY"
private

Definition at line 84 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

84 character*(20), parameter :: SADOURNY75_ENERGY_STRING = "SADOURNY75_ENERGY"

◆ sadourny75_enstro

integer, parameter mom_coriolisadv::sadourny75_enstro = 4
private

Definition at line 81 of file MOM_CoriolisAdv.F90.

Referenced by coradcalc(), and coriolisadv_init().

81 integer, parameter :: sadourny75_enstro = 4

◆ sadourny75_enstro_string

character*(20), parameter mom_coriolisadv::sadourny75_enstro_string = "SADOURNY75_ENSTRO"
private

Definition at line 87 of file MOM_CoriolisAdv.F90.

Referenced by coriolisadv_init().

87 character*(20), parameter :: SADOURNY75_ENSTRO_STRING = "SADOURNY75_ENSTRO"