CCPP SciDoc v7.0.x  v7.0.0
Common Community Physics Package Developed at DTC
 
Loading...
Searching...
No Matches
rrtmgp_lw_main.F90
1
3
6 use mpi_f08
7 use machine, only: kind_phys, kind_dbl_prec
8 use mo_optical_props, only: ty_optical_props_1scl, ty_optical_props_2str
9 use mo_rte_lw, only: rte_lw
10 use mo_gas_optics_rrtmgp, only: ty_gas_optics_rrtmgp
11 use mo_gas_concentrations, only: ty_gas_concs
12 use mo_fluxes_byband, only: ty_fluxes_byband
13 use mo_source_functions, only: ty_source_func_lw
14 use radiation_tools, only: check_error_msg
15 use rrtmgp_lw_gas_optics, only: lw_gas_props,rrtmgp_lw_gas_optics_init
16 use rrtmgp_lw_cloud_optics, only: lw_cloud_props, rrtmgp_lw_cloud_optics_init, abssnow0, &
17 abssnow1, absrain
18 use gfs_rrtmgp_pre, only: istr_h2o, istr_co2, istr_o3, istr_n2o, istr_ch4, &
19 istr_o2, istr_ccl4, istr_cfc11, istr_cfc12, istr_cfc22, &
20 eps, oneminus, ftiny
22 use rrtmgp_sampling, only: sampled_mask, draw_samples
23 use mo_rte_kind, only: rte_wp => wp
24 implicit none
25
26 public rrtmgp_lw_main_init, rrtmgp_lw_main_run
27contains
28
32 subroutine rrtmgp_lw_main_init(rrtmgp_root_dir, rrtmgp_lw_file_gas, rrtmgp_lw_file_clouds,&
33 active_gases_array, nrghice, mpicomm, mpirank, mpiroot, nLay, rrtmgp_phys_blksz, &
34 errmsg, errflg)
35
36 ! Inputs
37 character(len=128),intent(in) :: &
38 rrtmgp_root_dir, & !< RTE-RRTMGP root directory
39 rrtmgp_lw_file_clouds, & !< RRTMGP file containing coefficients used to compute
40
41 rrtmgp_lw_file_gas
43 character(len=*), dimension(:), intent(in), optional :: &
44 active_gases_array
45 integer, intent(inout) :: &
46 nrghice
47 type(mpi_comm),intent(in) :: &
48 mpicomm
49 integer,intent(in) :: &
50 mpirank, & !< Current MPI rank
51 mpiroot, & !< Master MPI rank
52 rrtmgp_phys_blksz, & !< Number of horizontal points to process at once.
53 nlay
54
55 ! Outputs
56 character(len=*), intent(out) :: &
57 errmsg
58 integer, intent(out) :: &
59 errflg
60
61 ! Initialize CCPP error handling variables
62 errmsg = ''
63 errflg = 0
64
65 ! RRTMGP longwave gas-optics (k-distribution) initialization
66 call rrtmgp_lw_gas_optics_init(rrtmgp_root_dir, rrtmgp_lw_file_gas, &
67 active_gases_array, mpicomm, mpirank, mpiroot, errmsg, errflg)
68
69 ! RRTMGP longwave cloud-optics initialization
70 call rrtmgp_lw_cloud_optics_init(rrtmgp_root_dir, rrtmgp_lw_file_clouds, &
71 nrghice, mpicomm, mpirank, mpiroot, errmsg, errflg)
72
73 end subroutine rrtmgp_lw_main_init
74
78 subroutine rrtmgp_lw_main_run(doLWrad, doLWclrsky, top_at_1, doGP_lwscat, &
79 nCol, nLay, nGases,rrtmgp_phys_blksz, &
80 nGauss_angles, icseed_lw, iovr, iovr_convcld, iovr_max, iovr_maxrand, iovr_rand, &
81 iovr_dcorr, iovr_exp, iovr_exprand, isubc_lw, semis, tsfg, p_lay, p_lev, t_lay, &
82 t_lev, vmr_o2, vmr_h2o, vmr_o3, vmr_ch4, vmr_n2o, vmr_co2, &
83 cld_frac, cld_lwp, cld_reliq, cld_iwp, cld_reice, cld_swp, cld_resnow, &
84 cld_rwp, cld_rerain, precip_frac, cld_cnv_lwp, cld_cnv_reliq, cld_cnv_iwp, &
85 cld_cnv_reice, cld_pbl_lwp, cld_pbl_reliq, cld_pbl_iwp, cld_pbl_reice, &
86 cloud_overlap_param, active_gases_array, aerlw_tau, aerlw_ssa, aerlw_g, &
87 fluxlwUP_allsky, fluxlwDOWN_allsky, fluxlwUP_clrsky, fluxlwDOWN_clrsky, &
88 fluxlwUP_radtime, fluxlwDOWN_radtime, fluxlwUP_jac, errmsg, errflg)
89
90 ! Inputs
91 logical, intent(in) :: &
92 dolwrad, & ! Flag to perform longwave calculation
93 dolwclrsky, & ! Flag to compute clear-sky fluxes
94 top_at_1, & ! Flag for vertical ordering convention
95 dogp_lwscat ! Flag to include scattering in clouds
96 integer,intent(in) :: &
97 ncol, & ! Number of horizontal points
98 nlay, & ! Number of vertical grid points.
99 ngases, & ! Number of active gases
100 rrtmgp_phys_blksz, & ! Number of horizontal points to process at once.
101 ngauss_angles, & ! Number of gaussian quadrature angles used
102 iovr, & ! Choice of cloud-overlap method
103 iovr_convcld, & ! Choice of convective cloud-overlap
104 iovr_max, & ! Flag for maximum cloud overlap method
105 iovr_maxrand, & ! Flag for maximum-random cloud overlap method
106 iovr_rand, & ! Flag for random cloud overlap method
107 iovr_dcorr, & ! Flag for decorrelation-length cloud overlap method
108 iovr_exp, & ! Flag for exponential cloud overlap method
109 iovr_exprand, & ! Flag for exponential-random cloud overlap method
110 isubc_lw ! Flag for cloud-seeding (rng) for cloud-sampling
111 integer,intent(in),dimension(:) :: &
112 icseed_lw ! Seed for random number generation for longwave radiation
113 real(kind_phys), dimension(:), intent(in) :: &
114 semis, & ! Surface-emissivity (1)
115 tsfg ! Skin temperature (K)
116 real(kind_phys), dimension(:,:), intent(in) :: &
117 p_lay, & ! Pressure @ model layer-centers (Pa)
118 t_lay, & ! Temperature (K)
119 p_lev, & ! Pressure @ model layer-interfaces (Pa)
120 t_lev, & ! Temperature @ model levels (K)
121 vmr_o2, & ! Molar-mixing ratio oxygen
122 vmr_h2o, & ! Molar-mixing ratio water vapor
123 vmr_o3, & ! Molar-mixing ratio ozone
124 vmr_ch4, & ! Molar-mixing ratio methane
125 vmr_n2o, & ! Molar-mixing ratio nitrous oxide
126 vmr_co2 ! Molar-mixing ratio carbon dioxide
127 real(kind_phys), dimension(:,:), intent(in) :: &
128 cld_frac, & ! Cloud-fraction for stratiform clouds
129 cld_lwp, & ! Water path for stratiform liquid cloud-particles
130 cld_reliq, & ! Effective radius for stratiform liquid cloud-particles
131 cld_iwp, & ! Water path for stratiform ice cloud-particles
132 cld_reice, & ! Effective radius for stratiform ice cloud-particles
133 cld_swp, & ! Water path for snow hydrometeors
134 cld_resnow, & ! Effective radius for snow hydrometeors
135 cld_rwp, & ! Water path for rain hydrometeors
136 cld_rerain, & ! Effective radius for rain hydrometeors
137 precip_frac, & ! Precipitation fraction (not active, currently precipitation optics uses cloud-fraction)
138 cloud_overlap_param ! Cloud overlap parameter
139 real(kind_phys), dimension(:,:), intent(in), optional :: &
140 cld_cnv_lwp, & ! Water path for convective liquid cloud-particles
141 cld_cnv_reliq, & ! Effective radius for convective liquid cloud-particles
142 cld_cnv_iwp, & ! Water path for convective ice cloud-particles
143 cld_cnv_reice, & ! Effective radius for convective ice cloud-particles
144 cld_pbl_lwp, & ! Water path for PBL liquid cloud-particles
145 cld_pbl_reliq, & ! Effective radius for PBL liquid cloud-particles
146 cld_pbl_iwp, & ! Water path for PBL ice cloud-particles
147 cld_pbl_reice ! Effective radius for PBL ice cloud-particles
148 real(kind_phys), dimension(:,:,:), intent(in) :: &
149 aerlw_tau, & ! Aerosol optical depth
150 aerlw_ssa, & ! Aerosol single scattering albedo
151 aerlw_g ! Aerosol asymmetry paramter
152 character(len=*), dimension(:), intent(in) :: &
153 active_gases_array ! List of active gases from namelist as array
154
155 ! Outputs
156 real(kind_phys), dimension(:,:), intent(inout), optional :: &
157 fluxlwup_jac ! Jacobian of upwelling LW surface radiation (W/m2/K)
158 real(kind_phys), dimension(:,:), intent(inout) :: &
159 fluxlwup_allsky, & ! All-sky flux (W/m2)
160 fluxlwdown_allsky, & ! All-sky flux (W/m2)
161 fluxlwup_clrsky, & ! Clear-sky flux (W/m2)
162 fluxlwdown_clrsky, & ! All-sky flux (W/m2)
163 fluxlwup_radtime, & ! Copy of fluxes (Used for coupling)
164 fluxlwdown_radtime !
165 character(len=*), intent(out) :: &
166 errmsg ! CCPP error message
167 integer, intent(out) :: &
168 errflg ! CCPP error flag
169
170 ! Local variables
171 type(ty_fluxes_byband) :: flux_allsky, flux_clrsky
172 integer :: icol, ilay, igas, iband, icol2, ix, iblck
173 integer, dimension(rrtmgp_phys_blksz) :: ipseed_lw
174 type(random_stat) :: rng_stat
175 real(kind_phys), dimension(rrtmgp_phys_blksz) :: zcf0, zcf1
176 logical, dimension(rrtmgp_phys_blksz,nLay,lw_gas_props%get_ngpt()) :: maskmcica
177 real(kind_phys), dimension(rrtmgp_phys_blksz) :: tau_rain, tau_snow
178 real(kind_dbl_prec), dimension(lw_gas_props%get_ngpt()) :: rng1d
179 real(rte_wp), dimension(lw_gas_props%get_ngpt(),nLay,rrtmgp_phys_blksz) :: rng3d,rng3d2
180 real(kind_dbl_prec), dimension(lw_gas_props%get_ngpt()*nLay) :: rng2d
181 real(rte_wp), dimension(rrtmgp_phys_blksz,nLay+1,lw_gas_props%get_nband()),target :: &
182 fluxlw_up_allsky, fluxlw_up_clrsky, fluxlw_dn_allsky, fluxlw_dn_clrsky
183 real(rte_wp), dimension(rrtmgp_phys_blksz,lw_gas_props%get_ngpt()) :: lw_ds
184 real(rte_wp), dimension(lw_gas_props%get_nband(),rrtmgp_phys_blksz) :: sfc_emiss_byband
185 real(rte_wp), dimension(rrtmgp_phys_blksz,nLay+1) :: fluxlw_up_jac
186 logical :: dogp_sgs_cnv, dogp_sgs_pbl
187 ! Local RRTMGP DDTs.
188 type(ty_gas_concs) :: gas_concs
189 type(ty_optical_props_1scl) :: lw_optical_props_clrsky, lw_optical_props_aerosol_local
190 type(ty_optical_props_2str) :: lw_optical_props_clouds, lw_optical_props_cloudsbyband, &
191 lw_optical_props_cnvcloudsbyband, lw_optical_props_pblcloudsbyband, &
192 lw_optical_props_precipbyband
193 type(ty_source_func_lw) :: sources
194
195 ! Initialize CCPP error handling variables
196 errmsg = ''
197 errflg = 0
198
199 if (.not. dolwrad) return
200
201 ! Do we have convective cloud properties?
202 dogp_sgs_cnv = .false.
203 if (present(cld_cnv_lwp) .and. present(cld_cnv_reliq) .and. &
204 present(cld_cnv_iwp) .and. present(cld_cnv_reice)) then
205 dogp_sgs_cnv = .true.
206 endif
207
208 ! Do we have pbl cloud prperties?
209 dogp_sgs_pbl = .false.
210 if (present(cld_pbl_lwp) .and. present(cld_pbl_reliq) .and. &
211 present(cld_pbl_iwp) .and. present(cld_pbl_reice)) then
212 dogp_sgs_pbl = .true.
213 endif
214
215 !
216 ! Initialize RRTMGP DDTs (local)
217 !
218
219 ! ty_gas_concs
220 call check_error_msg('rrtmgp_lw_main_gas_concs_run',gas_concs%init(active_gases_array))
221
222 ! ty_optical_props
223 call check_error_msg('rrtmgp_lw_main_gas_optics_run',&
224 lw_optical_props_clrsky%alloc_1scl(rrtmgp_phys_blksz, nlay, lw_gas_props))
225 call check_error_msg('rrtmgp_lw_main_sources_run',&
226 sources%alloc(rrtmgp_phys_blksz, nlay, lw_gas_props))
227 call check_error_msg('rrtmgp_lw_main_cloud_optics_run',&
228 lw_optical_props_cloudsbyband%alloc_2str(rrtmgp_phys_blksz, nlay, lw_gas_props%get_band_lims_wavenumber()))
229 call check_error_msg('rrtmgp_lw_main_precip_optics_run',&
230 lw_optical_props_precipbyband%alloc_2str(rrtmgp_phys_blksz, nlay, lw_gas_props%get_band_lims_wavenumber()))
231 call check_error_msg('rrtmgp_lw_mian_cloud_sampling_run', &
232 lw_optical_props_clouds%alloc_2str(rrtmgp_phys_blksz, nlay, lw_gas_props))
233 call check_error_msg('rrtmgp_lw_main_aerosol_optics_run',&
234 lw_optical_props_aerosol_local%alloc_1scl(rrtmgp_phys_blksz, nlay, lw_gas_props%get_band_lims_wavenumber()))
235 if (dogp_sgs_cnv) then
236 call check_error_msg('rrtmgp_lw_main_cnv_cloud_optics_run',&
237 lw_optical_props_cnvcloudsbyband%alloc_2str(rrtmgp_phys_blksz, nlay, lw_gas_props%get_band_lims_wavenumber()))
238 endif
239 if (dogp_sgs_pbl) then
240 call check_error_msg('rrtmgp_lw_main_pbl_cloud_optics_run',&
241 lw_optical_props_pblcloudsbyband%alloc_2str(rrtmgp_phys_blksz, nlay, lw_gas_props%get_band_lims_wavenumber()))
242 endif
243
244 ! ######################################################################################
245 !
246 ! Loop over all columns...
247 !
248 ! ######################################################################################
249 do icol=1,ncol,rrtmgp_phys_blksz
250 icol2 = icol + rrtmgp_phys_blksz - 1
251
252 ! Initialize/reset
253
254 ! ty_optical_props
255 lw_optical_props_clrsky%tau = 0._kind_phys
256 lw_optical_props_precipbyband%tau = 0._kind_phys
257 lw_optical_props_precipbyband%ssa = 0._kind_phys
258 lw_optical_props_precipbyband%g = 0._kind_phys
259 lw_optical_props_cloudsbyband%tau = 0._kind_phys
260 lw_optical_props_cloudsbyband%ssa = 0._kind_phys
261 lw_optical_props_cloudsbyband%g = 0._kind_phys
262 lw_optical_props_clouds%tau = 0._kind_phys
263 lw_optical_props_clouds%ssa = 0._kind_phys
264 lw_optical_props_clouds%g = 0._kind_phys
265 sources%sfc_source = 0._kind_phys
266 sources%lay_source = 0._kind_phys
267 sources%sfc_source_Jac = 0._kind_phys
268 fluxlw_up_allsky = 0._rte_wp
269 fluxlw_dn_allsky = 0._rte_wp
270 fluxlw_up_clrsky = 0._rte_wp
271 fluxlw_dn_clrsky = 0._rte_wp
272 if (dogp_sgs_cnv) lw_optical_props_cnvcloudsbyband%tau = 0._kind_phys
273 if (dogp_sgs_pbl) lw_optical_props_pblcloudsbyband%tau = 0._kind_phys
274
275 ! ty_fluxes_byband
276 fluxlw_up_allsky = 0._rte_wp
277 fluxlw_dn_allsky = 0._rte_wp
278 fluxlw_up_clrsky = 0._rte_wp
279 fluxlw_dn_clrsky = 0._rte_wp
280 flux_allsky%bnd_flux_up => fluxlw_up_allsky
281 flux_allsky%bnd_flux_dn => fluxlw_dn_allsky
282 flux_clrsky%bnd_flux_up => fluxlw_up_clrsky
283 flux_clrsky%bnd_flux_dn => fluxlw_dn_clrsky
284
285 ! ###################################################################################
286 !
287 ! Set gas-concentrations
288 !
289 ! ###################################################################################
290 call check_error_msg('rrtmgp_lw_main_set_vmr_o2', &
291 gas_concs%set_vmr(trim(active_gases_array(istr_o2)), real(vmr_o2(icol:icol2,:),kind=rte_wp)))
292 call check_error_msg('rrtmgp_lw_main_set_vmr_co2', &
293 gas_concs%set_vmr(trim(active_gases_array(istr_co2)),real(vmr_co2(icol:icol2,:),kind=rte_wp)))
294 call check_error_msg('rrtmgp_lw_main_set_vmr_ch4', &
295 gas_concs%set_vmr(trim(active_gases_array(istr_ch4)),real(vmr_ch4(icol:icol2,:),kind=rte_wp)))
296 call check_error_msg('rrtmgp_lw_main_set_vmr_n2o', &
297 gas_concs%set_vmr(trim(active_gases_array(istr_n2o)),real(vmr_n2o(icol:icol2,:),kind=rte_wp)))
298 call check_error_msg('rrtmgp_lw_main_set_vmr_h2o', &
299 gas_concs%set_vmr(trim(active_gases_array(istr_h2o)),real(vmr_h2o(icol:icol2,:),kind=rte_wp)))
300 call check_error_msg('rrtmgp_lw_main_set_vmr_o3', &
301 gas_concs%set_vmr(trim(active_gases_array(istr_o3)), real(vmr_o3(icol:icol2,:),kind=rte_wp)))
302
303 ! ###################################################################################
304 !
305 ! Surface emissity in each band
306 !
307 ! ###################################################################################
308 ! Assign same emissivity to all band
309 do iblck=1,rrtmgp_phys_blksz
310 if (semis(icol+iblck-1) > eps .and. semis(icol+iblck-1) <= 1._kind_phys) then
311 do iband=1,lw_gas_props%get_nband()
312 sfc_emiss_byband(iband,iblck) = semis(icol+iblck-1)
313 enddo
314 else
315 sfc_emiss_byband(1:lw_gas_props%get_nband(),iblck) = 1.0
316 endif
317 enddo
318
319 ! ###################################################################################
320 !
321 ! Compute gas-optics...
322 !
323 ! ###################################################################################
324 call check_error_msg('rrtmgp_lw_main_gas_optics',lw_gas_props%gas_optics(&
325 real(p_lay(icol:icol2,:),kind=rte_wp), & ! IN - Pressure @ layer-centers (Pa)
326 real(p_lev(icol:icol2,:),kind=rte_wp), & ! IN - Pressure @ layer-interfaces (Pa)
327 real(t_lay(icol:icol2,:),kind=rte_wp), & ! IN - Temperature @ layer-centers (K)
328 real(tsfg(icol:icol2),kind=rte_wp), & ! IN - Skin-temperature (K)
329 gas_concs, & ! IN - RRTMGP DDT: trace gas volumne mixing-ratios
330 lw_optical_props_clrsky, & ! OUT - RRTMGP DDT: longwave optical properties
331 sources, & ! OUT - RRTMGP DDT: source functions
332 tlev=real(t_lev(icol:icol2,:),kind=rte_wp))) ! IN - Temperature @ layer-interfaces (K) (optional)
333
334 ! ###################################################################################
335 !
336 ! Compute cloud-optics...
337 !
338 ! ###################################################################################
339 ! Create clear/cloudy indicator
340 zcf0(:) = 1._kind_phys
341 zcf1(:) = 1._kind_phys
342 do iblck = 1, rrtmgp_phys_blksz
343 do ilay=1,nlay
344 zcf0(iblck) = min(zcf0(iblck), 1._kind_phys - cld_frac(icol+iblck-1,ilay))
345 enddo
346 if (zcf0(iblck) <= ftiny) zcf0(iblck) = 0._kind_phys
347 if (zcf0(iblck) > oneminus) zcf0(iblck) = 1._kind_phys
348 zcf1(iblck) = 1._kind_phys - zcf0(iblck)
349 enddo
350
351 if (any(zcf1 .gt. eps)) then
352 ! Microphysical (gridmean) cloud optics
353 call check_error_msg('rrtmgp_lw_main_cloud_optics',lw_cloud_props%cloud_optics(&
354 real(cld_lwp(icol:icol2,:),kind=rte_wp), & ! IN - Cloud liquid water path (g/m2)
355 real(cld_iwp(icol:icol2,:),kind=rte_wp), & ! IN - Cloud ice water path (g/m2)
356 real(cld_reliq(icol:icol2,:),kind=rte_wp), & ! IN - Cloud liquid effective radius (microns)
357 real(cld_reice(icol:icol2,:),kind=rte_wp), & ! IN - Cloud ice effective radius (microns)
358 lw_optical_props_cloudsbyband)) ! OUT - RRTMGP DDT containing cloud radiative properties
359 ! in each band
360 ! Include convective (subgrid scale) clouds?
361 if (dogp_sgs_cnv) then
362 ! Compute
363 call check_error_msg('rrtmgp_lw_main_cnv_cloud_optics',lw_cloud_props%cloud_optics(&
364 real(cld_cnv_lwp(icol:icol2,:),kind=rte_wp), & ! IN - Convective cloud liquid water path (g/m2)
365 real(cld_cnv_iwp(icol:icol2,:),kind=rte_wp), & ! IN - Convective cloud ice water path (g/m2)
366 real(cld_cnv_reliq(icol:icol2,:),kind=rte_wp), & ! IN - Convective cloud liquid effective radius (microns)
367 real(cld_cnv_reice(icol:icol2,:),kind=rte_wp), & ! IN - Convective cloud ice effective radius (microns)
368 lw_optical_props_cnvcloudsbyband)) ! OUT - RRTMGP DDT containing convective cloud radiative properties
369 ! in each band
370 ! Increment
371 call check_error_msg('rrtmgp_lw_main_increment_cnvclouds_to_clouds',&
372 lw_optical_props_cnvcloudsbyband%increment(lw_optical_props_cloudsbyband))
373 endif
374
375 ! Include PBL (subgrid scale) clouds?
376 if (dogp_sgs_pbl) then
377 ! Compute
378 call check_error_msg('rrtmgp_lw_main_pbl_cloud_optics',lw_cloud_props%cloud_optics(&
379 real(cld_pbl_lwp(icol:icol2,:),kind=rte_wp), & ! IN - PBL cloud liquid water path (g/m2)
380 real(cld_pbl_iwp(icol:icol2,:),kind=rte_wp), & ! IN - PBL cloud ice water path (g/m2)
381 real(cld_pbl_reliq(icol:icol2,:),kind=rte_wp), & ! IN - PBL cloud liquid effective radius (microns)
382 real(cld_pbl_reice(icol:icol2,:),kind=rte_wp), & ! IN - PBL cloud ice effective radius (microns)
383 lw_optical_props_pblcloudsbyband)) ! OUT - RRTMGP DDT containing PBL cloud radiative properties
384 ! in each band
385 ! Increment
386 call check_error_msg('rrtmgp_lw_main_increment_pblclouds_to_clouds',&
387 lw_optical_props_pblcloudsbyband%increment(lw_optical_props_cloudsbyband))
388 endif
389 endif
390
391 ! ###################################################################################
392 !
393 ! Cloud precipitation optics: rain and snow(+groupel)
394 !
395 ! ###################################################################################
396 tau_rain(:) = 0._kind_phys
397 tau_snow(:) = 0._kind_phys
398 do ix=1,rrtmgp_phys_blksz
399 do ilay=1,nlay
400 if (cld_frac(icol+ix-1,ilay) .gt. eps) then
401 ! Rain optical-depth (No band dependence)
402 tau_rain(ix) = absrain*cld_rwp(icol+ix-1,ilay)
403
404 ! Snow (+groupel) optical-depth (No band dependence)
405 if (cld_swp(icol+ix-1,ilay) .gt. 0. .and. cld_resnow(icol+ix-1,ilay) .gt. 10._kind_phys) then
406 tau_snow(ix) = abssnow0*1.05756*cld_swp(icol+ix-1,ilay)/cld_resnow(icol+ix-1,ilay)
407 else
408 tau_snow(ix) = 0.0
409 endif
410 do iband=1,lw_gas_props%get_nband()
411 lw_optical_props_precipbyband%tau(ix,ilay,iband) = tau_rain(ix) + tau_snow(ix)
412 enddo
413 endif
414 enddo
415 enddo
416 ! Increment
417 call check_error_msg('rrtmgp_lw_main_increment_precip_to_clouds',&
418 lw_optical_props_precipbyband%increment(lw_optical_props_cloudsbyband))
419
420 ! ###################################################################################
421 !
422 ! Cloud-sampling
423 ! *Note* All of the included cloud-types are sampled together, not independently.
424 !
425 ! ###################################################################################
426 if (any(zcf1 .gt. eps)) then
427 ! Change random number seed value for each radiation invocation (isubc_lw =1 or 2).
428 if(isubc_lw == 1) then ! advance prescribed permutation seed
429 do ix=1,rrtmgp_phys_blksz
430 ipseed_lw(ix) = lw_gas_props%get_ngpt() + icol + ix - 1
431 enddo
432 elseif (isubc_lw == 2) then ! use input array of permutation seeds
433 do ix=1,rrtmgp_phys_blksz
434 ipseed_lw(ix) = icseed_lw(icol+ix-1)
435 enddo
436 endif
437
438 ! Call RNG
439 do ix=1,rrtmgp_phys_blksz
440 call random_setseed(ipseed_lw(ix),rng_stat)
441 ! Use same rng for each layer
442 if (iovr == iovr_max) then
443 call random_number(rng1d,rng_stat)
444 do ilay=1,nlay
445 rng3d(:,ilay,ix) = rng1d
446 enddo
447 else
448 do ilay=1,nlay
449 call random_number(rng1d,rng_stat)
450 rng3d(:,ilay,ix) = rng1d
451 enddo
452 endif
453 enddo
454
455 ! Cloud-overlap.
456 ! Maximum-random, random or maximum.
457 if (iovr == iovr_maxrand .or. iovr == iovr_rand .or. iovr == iovr_max) then
458 call sampled_mask(rng3d, real(cld_frac(icol:icol2,:),kind=rte_wp), maskmcica)
459 endif
460 ! Exponential decorrelation length overlap
461 if (iovr == iovr_dcorr) then
462 do ix=1,rrtmgp_phys_blksz
463 ! Generate second RNG
464 call random_setseed(ipseed_lw(ix),rng_stat)
465 call random_number(rng2d,rng_stat)
466 rng3d2(:,:,ix) = reshape(source = rng2d,shape=[lw_gas_props%get_ngpt(),nlay])
467 enddo
468 !
469 call sampled_mask(rng3d, real(cld_frac(icol:icol2,:),kind=rte_wp), &
470 maskmcica, overlap_param = real(cloud_overlap_param(icol:icol2,1:nlay-1),kind=rte_wp), &
471 randoms2 = rng3d2)
472 endif
473 ! Exponential or Exponential-random
474 if (iovr == iovr_exp .or. iovr == iovr_exprand) then
475 call sampled_mask(rng3d, real(cld_frac(icol:icol2,:),kind=rte_wp), &
476 maskmcica, overlap_param = real(cloud_overlap_param(icol:icol2,1:nlay-1),kind=rte_wp))
477 endif
478 ! Sampling. Map band optical depth to each g-point using McICA
479 call check_error_msg('rrtmgp_lw_main_cloud_sampling',&
480 draw_samples(maskmcica, .true., &
481 lw_optical_props_cloudsbyband, lw_optical_props_clouds))
482 endif
483
484 ! ###################################################################################
485 !
486 ! Compute clear-sky fluxes (gaseous+aerosol) (optional)
487 !
488 ! ###################################################################################
489 ! Increment
490 lw_optical_props_aerosol_local%tau = aerlw_tau(icol:icol2,:,:)
491 call check_error_msg('rrtmgp_lw_main_increment_aerosol_to_clrsky',&
492 lw_optical_props_aerosol_local%increment(lw_optical_props_clrsky))
493
494 ! Call RTE solver
495 if (dolwclrsky) then
496 call check_error_msg('rrtmgp_lw_main_opt_angle',&
497 lw_gas_props%compute_optimal_angles(lw_optical_props_clrsky,lw_ds))
498 if (ngauss_angles .gt. 1) then
499 call check_error_msg('rrtmgp_lw_main_lw_rte_clrsky',rte_lw( &
500 lw_optical_props_clrsky, & ! IN - optical-properties
501 top_at_1, & ! IN - veritcal ordering flag
502 sources, & ! IN - source function
503 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
504 flux_clrsky, & ! OUT - Fluxes
505 n_gauss_angles = ngauss_angles)) ! IN - Number of angles in Gaussian quadrature
506 else
507 call check_error_msg('rrtmgp_lw_main_lw_rte_clrsky',rte_lw( &
508 lw_optical_props_clrsky, & ! IN - optical-properties
509 top_at_1, & ! IN - veritcal ordering flag
510 sources, & ! IN - source function
511 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
512 flux_clrsky, & ! OUT - Fluxes
513 lw_ds = lw_ds))
514 endif
515
516 ! Store fluxes
517 fluxlwup_clrsky(icol:icol2,:) = sum(flux_clrsky%bnd_flux_up, dim=3)
518 fluxlwdown_clrsky(icol:icol2,:) = sum(flux_clrsky%bnd_flux_dn, dim=3)
519 else
520 fluxlwup_clrsky(icol:icol2,:) = 0.0
521 fluxlwdown_clrsky(icol:icol2,:) = 0.0
522 endif
523
524 ! ###################################################################################
525 !
526 ! All-sky fluxes (clear-sky + clouds + precipitation)
527 ! *Note* CCPP does not allow for polymorphic types, they are ambiguous to the CCPP
528 ! framework. rte-rrtmgp uses polymorphic types extensively, for example, querying the
529 ! type to determine physics configuration/pathway/etc...
530 !
531 ! The logic in the code below is to satisfy the polymorphishm in the rte-rrtmgp code.
532 ! The rte-rrtmgp "increment" procedures are utilized to provide the correct type to the
533 ! rte solver (rte_lw). Rte_lw quieries the type determine if scattering is to be
534 ! included in the calculation. The increment procedures are called so that the correct
535 ! optical properties are inherited. ugh...
536 !
537 ! ###################################################################################
538
539 ! Include LW cloud-scattering?
540 if (dogp_lwscat) then
541 ! Increment
542 call check_error_msg('rrtmgp_lw_main_increment_clrsky_to_clouds',&
543 lw_optical_props_clrsky%increment(lw_optical_props_clouds))
544
545 if (present(fluxlwup_jac)) then
546 ! Compute LW Jacobians
547 call check_error_msg('rrtmgp_lw_main_lw_rte_allsky',rte_lw( &
548 lw_optical_props_clouds, & ! IN - optical-properties
549 top_at_1, & ! IN - veritcal ordering flag
550 sources, & ! IN - source function
551 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
552 flux_allsky, & ! OUT - Flxues
553 n_gauss_angles = ngauss_angles, & ! IN - Number of angles in Gaussian quadrature
554 flux_up_jac = fluxlw_up_jac)) ! OUT - surface temperature flux (upward) Jacobian (W/m2/K)
555 else
556 call check_error_msg('rrtmgp_lw_main_lw_rte_allsky',rte_lw( &
557 lw_optical_props_clouds, & ! IN - optical-properties
558 top_at_1, & ! IN - veritcal ordering flag
559 sources, & ! IN - source function
560 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
561 flux_allsky, & ! OUT - Flxues
562 n_gauss_angles = ngauss_angles)) ! IN - Number of angles in Gaussian quadrature
563 end if
564 ! No scattering in LW clouds.
565 else
566 ! Increment
567 call check_error_msg('rrtmgp_lw_main_increment_clouds_to_clrsky', &
568 lw_optical_props_clouds%increment(lw_optical_props_clrsky))
569
570 if (present(fluxlwup_jac)) then
571 ! Compute LW Jacobians
572 call check_error_msg('rrtmgp_lw_rte_run',rte_lw( &
573 lw_optical_props_clrsky, & ! IN - optical-properties
574 top_at_1, & ! IN - veritcal ordering flag
575 sources, & ! IN - source function
576 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
577 flux_allsky, & ! OUT - Flxues
578 n_gauss_angles = ngauss_angles, & ! IN - Number of angles in Gaussian quadrature
579 flux_up_jac = fluxlw_up_jac)) ! OUT - surface temperature flux (upward) Jacobian (W/m2/K)
580 else
581 call check_error_msg('rrtmgp_lw_rte_run',rte_lw( &
582 lw_optical_props_clrsky, & ! IN - optical-properties
583 top_at_1, & ! IN - veritcal ordering flag
584 sources, & ! IN - source function
585 sfc_emiss_byband, & ! IN - surface emissivity in each LW band
586 flux_allsky, & ! OUT - Flxues
587 n_gauss_angles = ngauss_angles)) ! IN - Number of angles in Gaussian quadrature
588 end if
589 endif
590
591 ! Store fluxes
592 fluxlwup_allsky(icol:icol2,:) = sum(flux_allsky%bnd_flux_up, dim=3)
593 fluxlwdown_allsky(icol:icol2,:) = sum(flux_allsky%bnd_flux_dn, dim=3)
594
595 ! Save fluxes for coupling
596 if (present(fluxlwup_jac)) then
597 fluxlwup_jac(icol:icol2,:) = fluxlw_up_jac
598 endif
599 fluxlwup_radtime(icol:icol2,:) = fluxlwup_allsky(icol:icol2,:)
600 fluxlwdown_radtime(icol:icol2,:) = fluxlwdown_allsky(icol:icol2,:)
601
602 enddo
603
604 end subroutine rrtmgp_lw_main_run
605end module rrtmgp_lw_main
This module calculates random numbers using the Mersenne twister.
This module contains tools for radiation.
This module contains two routines: The first initializes data and functions needed to compute the lon...
This module contains two routines: One to initialize the k-distribution data and functions needed to ...
This module contains the RRTMGP-LW radiation scheme.
This module provides a simple implementation of sampling for the Monte Carlo Independent Pixel Approx...