Skip to content

Commit af91b60

Browse files
Merge branch 'whannah/eam/test-frontogenesis-correction' into next (PR #7797)
Frontogenesis function pressure gradient correction This implements a missing correction for the frontogenesis function (FGF) used for the frontal gravity wave drag scheme. The FGF gradient calculations are done on model levels for convenience, but the original papers indicate a simple correction should be used to effectively put these gradients on height or pressure levels. However, going back to the original implementation in CESM with FV dynamics this correction was never implemented, and this mistake was carried through to E3SM with the SE dynamics. The correction addresses problematic biases of excessive gravity wave drag over areas of steep topography. It is controlled by a new namelist variable "use_fgf_pgrad_correction" that is off by default to preserve the behavior of official v3 release version. [BFB] * whannah/eam/test-frontogenesis-correction: comment fix fix namelist variable description misc fixes misc fixes fix white space update compute_frontogenesis for zgrad correction add get_hydro_pressure_interface subroutine add use_fgf_zgrad_correction namelist variable remove pmid_hydro update pressure calculation update comments switch convention for clarity add namelist control for frontogenesis pgrad correction fix typos add comments describing tensor vector contraction code bug fix add experimental pressure gradient correction for frontogensis function calculation
2 parents f356f2a + 3f4a52a commit af91b60

File tree

6 files changed

+242
-36
lines changed

6 files changed

+242
-36
lines changed

components/eam/bld/build-namelist

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4137,6 +4137,9 @@ if ($nl->get_value('use_gw_convect') =~ /$TRUE/io) {
41374137
add_default($nl, 'gw_drag_file');
41384138
}
41394139

4140+
# this correction is disabled in the released version E3SMv3 and prior versions
4141+
add_default($nl, 'use_fgf_pgrad_correction', 'val'=>'.false.');
4142+
add_default($nl, 'use_fgf_zgrad_correction', 'val'=>'.false.');
41404143
add_default($nl, 'use_gw_energy_fix' , 'val'=>'.true.');
41414144

41424145

components/eam/bld/namelist_files/namelist_definition.xml

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1072,6 +1072,18 @@ Whether or not to enable gravity waves produced by convection.
10721072
Default: set by build-namelist.
10731073
</entry>
10741074

1075+
<entry id="use_fgf_pgrad_correction" type="logical" category="gw_drag"
1076+
group="phys_ctl_nl" valid_values="" >
1077+
Flag to enable frontogenesis pressure gradient correction for frontal GWD
1078+
Default: set by build-namelist.
1079+
</entry>
1080+
1081+
<entry id="use_fgf_zgrad_correction" type="logical" category="gw_drag"
1082+
group="phys_ctl_nl" valid_values="" >
1083+
Flag to enable frontogenesis geopotential gradient correction for frontal GWD
1084+
Default: set by build-namelist.
1085+
</entry>
1086+
10751087
<entry id="use_gw_energy_fix" type="logical" category="gw_drag"
10761088
group="phys_ctl_nl" valid_values="" >
10771089
Whether or not to enable GWD brute-force energy fix.

components/eam/src/dynamics/se/dp_coupling.F90

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ subroutine d_p_coupling(phys_state, phys_tend, pbuf2d, dyn_out)
3838
use cam_abortutils, only: endrun
3939
use gravity_waves_sources, only: gws_src_fnct
4040
use dyn_comp, only: frontgf_idx, frontga_idx, hvcoord
41-
use phys_control, only: use_gw_front
41+
use phys_control, only: use_gw_front, use_fgf_pgrad_correction, use_fgf_zgrad_correction
4242
use dyn_comp, only: dom_mt
4343
use gllfvremap_mod, only: gfr_dyn_to_fv_phys
4444

@@ -107,7 +107,10 @@ subroutine d_p_coupling(phys_state, phys_tend, pbuf2d, dyn_out)
107107
elem => dyn_out%elem
108108
tl_f = TimeLevel%n0 ! time split physics (with forward-in-time RK)
109109

110-
if (use_gw_front) call gws_src_fnct(elem, tl_f, nphys, frontgf, frontga)
110+
if (use_gw_front) call gws_src_fnct(elem, tl_f, nphys, &
111+
use_fgf_pgrad_correction, &
112+
use_fgf_zgrad_correction, &
113+
frontgf, frontga)
111114

112115
if (fv_nphys > 0) then
113116
!-----------------------------------------------------------------------

components/eam/src/dynamics/se/gravity_waves_sources.F90

Lines changed: 190 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
module gravity_waves_sources
22
use derivative_mod, only : derivative_t
3-
use dimensions_mod, only : np,nlev
3+
use dimensions_mod, only : np,nlev,nlevp
44
use edgetype_mod, only : EdgeBuffer_t
55
use element_mod, only : element_t
66
use hybrid_mod, only : hybrid_t
@@ -38,7 +38,7 @@ subroutine gws_init(elem)
3838

3939
end subroutine gws_init
4040
!-------------------------------------------------------------------------------------------------
41-
subroutine gws_src_fnct(elem, tl, nphys, frontgf, frontga)
41+
subroutine gws_src_fnct(elem, tl, nphys, use_fgf_pgrad_correction, use_fgf_zgrad_correction, frontgf, frontga)
4242
use dimensions_mod, only : npsq, nelemd
4343
use dof_mod, only : UniquePoints
4444
use dyn_comp, only : dom_mt
@@ -51,6 +51,8 @@ subroutine gws_src_fnct(elem, tl, nphys, frontgf, frontga)
5151
type (element_t), intent(inout), dimension(:) :: elem
5252
integer, intent(in ) :: tl
5353
integer, intent(in ) :: nphys
54+
logical, intent(in ) :: use_fgf_pgrad_correction
55+
logical, intent(in ) :: use_fgf_zgrad_correction
5456
real (kind=real_kind), intent(out ) :: frontgf(nphys*nphys,pver,nelemd)
5557
real (kind=real_kind), intent(out ) :: frontga(nphys*nphys,pver,nelemd)
5658

@@ -67,7 +69,10 @@ subroutine gws_src_fnct(elem, tl, nphys, frontgf, frontga)
6769
hybrid = hybrid_create(par,ithr,hthreads)
6870
allocate(frontgf_thr(nphys,nphys,nlev,nets:nete))
6971
allocate(frontga_thr(nphys,nphys,nlev,nets:nete))
70-
call compute_frontogenesis(frontgf_thr,frontga_thr,tl,elem,hybrid,nets,nete,nphys)
72+
call compute_frontogenesis( frontgf_thr, frontga_thr, tl, &
73+
use_fgf_pgrad_correction, &
74+
use_fgf_zgrad_correction, &
75+
elem, hybrid, nets, nete, nphys )
7176
if (fv_nphys>0) then
7277
do ie = nets,nete
7378
do k = 1,nlev
@@ -88,7 +93,10 @@ subroutine gws_src_fnct(elem, tl, nphys, frontgf, frontga)
8893

8994
end subroutine gws_src_fnct
9095
!-------------------------------------------------------------------------------------------------
91-
subroutine compute_frontogenesis(frontgf,frontga,tl,elem,hybrid,nets,nete,nphys)
96+
subroutine compute_frontogenesis( frontgf, frontga, tl, &
97+
use_fgf_pgrad_correction, &
98+
use_fgf_zgrad_correction, &
99+
elem, hybrid, nets, nete, nphys )
92100
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
93101
! compute frontogenesis function F
94102
! F = -gradth dot C
@@ -99,63 +107,180 @@ subroutine compute_frontogenesis(frontgf,frontga,tl,elem,hybrid,nets,nete,nphys)
99107
!
100108
! Original by Mark Taylor, July 2011
101109
! Change by Santos, 10 Aug 2011:
102-
! Integrated into gravity_waves_sources module, several arguments made global
103-
! to prevent repeated allocation/initialization
110+
! Integrated into gravity_waves_sources module, several arguments made global
111+
! to prevent repeated allocation/initialization
104112
! Change by Aaron Donahue, April 2017:
105113
! Fixed bug where boundary information was called for processors not associated
106114
! with dynamics when dyn_npes<npes
115+
! Change by Walter Hannah, Oct 2025:
116+
! added pressure gradient correction
107117
!
108118
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
109-
use physical_constants, only: kappa
119+
use physical_constants, only: kappa, g
110120
use derivative_mod, only: gradient_sphere, ugradv_sphere
111-
use edge_mod, only : edge_g, edgevpack_nlyr, edgevunpack_nlyr
121+
use edge_mod, only: edge_g, edgevpack_nlyr, edgevunpack_nlyr
112122
use bndry_mod, only: bndry_exchangev
113123
use dyn_comp, only: hvcoord
114124
use spmd_utils, only: iam
115125
use parallel_mod, only: par
116-
use element_ops, only : get_temperature
126+
use element_ops, only: get_temperature, get_hydro_pressure_i, get_phi
117127
use dyn_grid, only: fv_nphys
118-
use prim_driver_mod, only : deriv1
119-
use element_ops, only : get_temperature
120-
use gllfvremap_mod, only : gfr_g2f_scalar, gfr_g2f_vector
128+
use prim_driver_mod, only: deriv1
129+
use gllfvremap_mod, only: gfr_g2f_scalar, gfr_g2f_vector
121130
implicit none
122131
type(hybrid_t), intent(in ) :: hybrid
123132
type(element_t),target,intent(inout) :: elem(:)
124133
integer, intent(in ) :: nets,nete,nphys
125134
integer, intent(in ) :: tl ! timelevel to use
135+
logical, intent(in ) :: use_fgf_pgrad_correction
136+
logical, intent(in ) :: use_fgf_zgrad_correction
126137
real(kind=real_kind), intent(out ) :: frontgf(nphys,nphys,nlev,nets:nete)
127138
real(kind=real_kind), intent(out ) :: frontga(nphys,nphys,nlev,nets:nete)
128139

129140
! local
130141
integer :: k,kptr,i,j,ie,component
131142
real(kind=real_kind) :: frontgf_gll(np,np,nlev,nets:nete)
132143
real(kind=real_kind) :: gradth_gll(np,np,2,nlev,nets:nete) ! grad(theta)
133-
real(kind=real_kind) :: p(np,np) ! pressure at mid points
134-
real(kind=real_kind) :: theta(np,np) ! potential temperature at mid points
135-
real(kind=real_kind) :: temperature(np,np,nlev) ! Temperature
144+
real(kind=real_kind) :: zint(np,np,nlevp) ! interface altitude
145+
real(kind=real_kind) :: zmid(np,np,nlev) ! mid-point altitude
146+
real(kind=real_kind) :: pint(np,np,nlevp) ! interface hydrostatic pressure
147+
real(kind=real_kind) :: pmid(np,np,nlev) ! mid-point hydrostatic pressure
148+
real(kind=real_kind) :: temperature(np,np,nlev) ! Temperature
136149
real(kind=real_kind) :: C(np,np,2), wf1(nphys*nphys,nlev), wf2(nphys*nphys,nlev)
150+
151+
real(kind=real_kind) :: theta(np,np,nlev) ! potential temperature at mid points
152+
real(kind=real_kind) :: dum_grad(np,np,2) ! temporary variable for spherical gradient calcualtions
153+
real(kind=real_kind) :: dum_cart(np,np,3,nlev) ! temporary variable for cartesian gradient calcualtions
154+
155+
! variables needed for eta to pressure surface correction
156+
real(kind=real_kind) :: grad_vert_gll(np,np,2,nlev) ! grad(vertical coordinate) - either pressure or geopotential
157+
real(kind=real_kind) :: theta_dvert(np,np,nlev) ! d(theta)/dp for eta to pressure surface correction
158+
real(kind=real_kind) :: dum_cart_dvert(np,np,3,nlev)! vertical pressure derivative of dum_cart
159+
160+
!---------------------------------------------------------------------------
161+
!
162+
! For a vector velocity "v", a tensor "grad(v)", and a vector "grad(theta)",
163+
! this loop computes the vector "grad(theta)*grad(v)"
164+
!
165+
! Representing the tensor "grad(v)" in spherical coordinates is difficult.
166+
! This routine avoids this by computing a mathematically equivalent form
167+
! using a mixture of Cartesian and spherical coordinates
168+
!
169+
! This routine is a modified version of derivative_mod.F90:ugradv_sphere()
170+
! in that the grad(v) term is modified to compute grad_z(v) (or grad_p(v))
171+
! - the gradient on z-surfaces expressed in terms of the gradient on model
172+
! surfaces and a vertical geopotential gradient.
173+
!
174+
! The old version only computed gradients on model surfaces, which creates
175+
! issues around topograpy. This is address with use_fgf_pgrad_correction=.true.
176+
!
177+
! First, v is represented in cartesian coordinates v(c) for c=1,2,3
178+
! For each v(c), we compute its gradient on z (or p) surfaces via:
179+
! grad(v(c)) - d(v(c))/dz grad(z)
180+
! Each of these gradients is represented in *spherical* coordinates (i=1,2)
181+
!
182+
! We then dot each of these vectors with grad(theta). This dot product is
183+
! computed in spherical coordinates. The end result is dum_cart(c),
184+
! for c=1,2,3 These three scalars are the three Cartesian coefficients of
185+
! the vector "grad(theta)*grad(v)"
186+
!
187+
! This Cartesian vector is then transformed back to spherical coordinates
188+
!
137189
!---------------------------------------------------------------------------
138190

139191
do ie = nets,nete
140-
do k = 1,nlev
141-
! pressure at mid points
142-
p(:,:) = hvcoord%hyam(k)*hvcoord%ps0 + hvcoord%hybm(k)*elem(ie)%state%ps_v(:,:,tl)
143-
! potential temperature: theta = T (p/p0)^kappa
192+
193+
if (use_fgf_pgrad_correction .or. use_fgf_zgrad_correction) then
194+
195+
! compute pressure at interfaces and mid-points
196+
call get_hydro_pressure_i(pint,elem(ie)%state%dp3d(:,:,:,tl),hvcoord)
197+
144198
call get_temperature(elem(ie),temperature,hvcoord,tl)
145-
theta(:,:) = temperature(:,:,k)*(psurf_ref / p(:,:))**kappa
146-
gradth_gll(:,:,:,k,ie) = gradient_sphere(theta,deriv1,elem(ie)%Dinv)
147-
! compute C = (grad(theta) dot grad ) u
148-
C(:,:,:) = ugradv_sphere(gradth_gll(:,:,:,k,ie), elem(ie)%state%v(:,:,:,k,tl),deriv1,elem(ie))
149-
! gradth_gll dot C
150-
frontgf_gll(:,:,k,ie) = -( C(:,:,1)*gradth_gll(:,:,1,k,ie) + C(:,:,2)*gradth_gll(:,:,2,k,ie) )
151-
! apply mass matrix
152-
gradth_gll(:,:,1,k,ie) = gradth_gll(:,:,1,k,ie)*elem(ie)%spheremp(:,:)
153-
gradth_gll(:,:,2,k,ie) = gradth_gll(:,:,2,k,ie)*elem(ie)%spheremp(:,:)
154-
frontgf_gll(:,:,k,ie) = frontgf_gll(:,:,k,ie)*elem(ie)%spheremp(:,:)
155-
end do ! k
199+
200+
! calculate pmid and potential temperature: theta = T (p/p0)^kappa
201+
do k = 1,nlev
202+
pmid(:,:,k) = pint(:,:,k) + elem(ie)%state%dp3d(:,:,k,tl)/2
203+
theta(:,:,k) = temperature(:,:,k)*(psurf_ref / pmid(:,:,k))**kappa
204+
end do
205+
206+
if (use_fgf_pgrad_correction) then
207+
! compute d(theta)/dp
208+
call compute_vertical_derivative(pint,theta,theta_dvert)
209+
end if
210+
211+
if (use_fgf_zgrad_correction) then
212+
! compute geopotential
213+
call get_phi(elem(ie), zmid, zint, hvcoord, tl)
214+
! compute d(theta)/dz
215+
call compute_vertical_derivative(zint,theta,theta_dvert)
216+
end if
217+
218+
do k = 1,nlev
219+
gradth_gll(:,:,:,k,ie) = gradient_sphere(theta(:,:,k),deriv1,elem(ie)%Dinv)
220+
if (use_fgf_pgrad_correction) grad_vert_gll(:,:,:,k) = gradient_sphere(pmid(:,:,k),deriv1,elem(ie)%Dinv)
221+
if (use_fgf_zgrad_correction) grad_vert_gll(:,:,:,k) = gradient_sphere(zmid(:,:,k),deriv1,elem(ie)%Dinv)
222+
do component=1,2
223+
gradth_gll(:,:,component,k,ie) = gradth_gll(:,:,component,k,ie) - theta_dvert(:,:,k) * grad_vert_gll(:,:,component,k)
224+
end do
225+
end do
226+
227+
do k = 1,nlev
228+
! latlon -> cartesian - Summing along the third dimension is a sum over components for each point
229+
do component=1,3
230+
dum_cart(:,:,component,k)=sum( elem(ie)%vec_sphere2cart(:,:,component,:) * elem(ie)%state%v(:,:,:,k,tl) ,3)
231+
end do
232+
end do
233+
234+
do component=1,3
235+
if (use_fgf_pgrad_correction) call compute_vertical_derivative(pint,dum_cart(:,:,component,:),dum_cart_dvert(:,:,component,:))
236+
if (use_fgf_zgrad_correction) call compute_vertical_derivative(zint,dum_cart(:,:,component,:),dum_cart_dvert(:,:,component,:))
237+
end do
238+
239+
do k = 1,nlev
240+
! Do ugradv on the cartesian components - Dot u with the gradient of each component
241+
do component=1,3
242+
dum_grad(:,:,:) = gradient_sphere(dum_cart(:,:,component,k),deriv1,elem(ie)%Dinv)
243+
do i=1,2
244+
dum_grad(:,:,i) = dum_grad(:,:,i) - dum_cart_dvert(:,:,component,k) * grad_vert_gll(:,:,i,k)
245+
end do
246+
dum_cart(:,:,component,k) = sum( gradth_gll(:,:,:,k,ie) * dum_grad ,3)
247+
enddo
248+
! cartesian -> latlon - vec_sphere2cart is its own pseudoinverse.
249+
do i=1,2
250+
C(:,:,i) = sum(dum_cart(:,:,:,k)*elem(ie)%vec_sphere2cart(:,:,:,i), 3)
251+
end do
252+
! gradth_gll dot C
253+
frontgf_gll(:,:,k,ie) = -( C(:,:,1)*gradth_gll(:,:,1,k,ie) + C(:,:,2)*gradth_gll(:,:,2,k,ie) )
254+
! apply mass matrix
255+
gradth_gll(:,:,1,k,ie) = gradth_gll(:,:,1,k,ie)*elem(ie)%spheremp(:,:)
256+
gradth_gll(:,:,2,k,ie) = gradth_gll(:,:,2,k,ie)*elem(ie)%spheremp(:,:)
257+
frontgf_gll(:,:,k,ie) = frontgf_gll(:,:,k,ie)*elem(ie)%spheremp(:,:)
258+
end do ! k
259+
260+
else ! .not. use_fgf_pgrad_correction
261+
262+
do k = 1,nlev
263+
! pressure at mid points - this pressure preserves the old behavior of E3SMv3 and prior
264+
pmid(:,:,k) = hvcoord%hyam(k)*hvcoord%ps0 + hvcoord%hybm(k)*elem(ie)%state%ps_v(:,:,tl)
265+
! potential temperature: theta = T (p/p0)^kappa
266+
call get_temperature(elem(ie),temperature,hvcoord,tl)
267+
theta(:,:,k) = temperature(:,:,k)*(psurf_ref / pmid(:,:,k))**kappa
268+
gradth_gll(:,:,:,k,ie) = gradient_sphere(theta(:,:,k),deriv1,elem(ie)%Dinv)
269+
! compute C = (grad(theta) dot grad ) u
270+
C(:,:,:) = ugradv_sphere(gradth_gll(:,:,:,k,ie), elem(ie)%state%v(:,:,:,k,tl),deriv1,elem(ie))
271+
! gradth_gll dot C
272+
frontgf_gll(:,:,k,ie) = -( C(:,:,1)*gradth_gll(:,:,1,k,ie) + C(:,:,2)*gradth_gll(:,:,2,k,ie) )
273+
! apply mass matrix
274+
gradth_gll(:,:,1,k,ie) = gradth_gll(:,:,1,k,ie)*elem(ie)%spheremp(:,:)
275+
gradth_gll(:,:,2,k,ie) = gradth_gll(:,:,2,k,ie)*elem(ie)%spheremp(:,:)
276+
frontgf_gll(:,:,k,ie) = frontgf_gll(:,:,k,ie)*elem(ie)%spheremp(:,:)
277+
end do ! k
278+
279+
end if ! use_fgf_pgrad_correction
280+
156281
! pack
157-
call edgeVpack_nlyr(edge_g, elem(ie)%desc, frontgf_gll(:,:,:,ie),nlev,0,3*nlev)
158-
call edgeVpack_nlyr(edge_g, elem(ie)%desc, gradth_gll(:,:,:,:,ie),2*nlev,nlev,3*nlev)
282+
call edgeVpack_nlyr(edge_g, elem(ie)%desc, frontgf_gll(:,:,:,ie),nlev,0,3*nlev)
283+
call edgeVpack_nlyr(edge_g, elem(ie)%desc, gradth_gll(:,:,:,:,ie),2*nlev,nlev,3*nlev)
159284

160285
end do ! ie
161286

@@ -192,4 +317,37 @@ subroutine compute_frontogenesis(frontgf,frontga,tl,elem,hybrid,nets,nete,nphys)
192317

193318
end subroutine compute_frontogenesis
194319
!-------------------------------------------------------------------------------------------------
320+
subroutine compute_vertical_derivative(vert_int, data_mid, ddata_dvert)
321+
!---------------------------------------------------------------------------
322+
real(kind=real_kind), intent(in ) :: vert_int(np,np,nlev) ! vertical coord on interfaces (i.e. pint or zint)
323+
real(kind=real_kind), intent(in ) :: data_mid(np,np,nlev) ! input data in mid-points
324+
real(kind=real_kind), intent(out) :: ddata_dvert(np,np,nlev) ! vertical derivative of data
325+
!---------------------------------------------------------------------------
326+
integer :: k
327+
real(kind=real_kind) :: vert_above(np,np) ! pressure interpolated to interface above the current k mid-point
328+
real(kind=real_kind) :: vert_below(np,np) ! pressure interpolated to interface below the current k mid-point
329+
real(kind=real_kind) :: data_above(np,np) ! data interpolated to interface above the current k mid-point
330+
real(kind=real_kind) :: data_below(np,np) ! data interpolated to interface below the current k mid-point
331+
!---------------------------------------------------------------------------
332+
do k = 1,nlev
333+
if (k==1) then
334+
data_above = data_mid(:,:,k)
335+
data_below = ( data_mid(:,:,k+1) + data_mid(:,:,k) ) / 2.0 ! interpolate to interface k+1
336+
vert_above = ( vert_int(:,:,k+1) + vert_int(:,:,k) ) / 2.0 ! interpolate to mid-point k
337+
vert_below = vert_int(:,:,k+1)
338+
elseif (k==nlev) then
339+
data_above = ( data_mid(:,:,k-1) + data_mid(:,:,k) ) / 2.0 ! interpolate to interface
340+
data_below = data_mid(:,:,k)
341+
vert_above = vert_int(:,:,k)
342+
vert_below = ( vert_int(:,:,k+1) + vert_int(:,:,k) ) / 2.0 ! interpolate to mid-point k
343+
else
344+
data_above = ( data_mid(:,:,k-1) + data_mid(:,:,k) ) / 2.0 ! interpolate to interface k
345+
data_below = ( data_mid(:,:,k+1) + data_mid(:,:,k) ) / 2.0 ! interpolate to interface k+1
346+
vert_above = vert_int(:,:,k)
347+
vert_below = vert_int(:,:,k+1)
348+
end if
349+
ddata_dvert(:,:,k) = ( data_above - data_below ) / ( vert_above - vert_below )
350+
end do
351+
end subroutine compute_vertical_derivative
352+
!-------------------------------------------------------------------------------------------------
195353
end module gravity_waves_sources

0 commit comments

Comments
 (0)