Skip to content

Complete CCPPization of CAM5 UW PBL scheme (diag_TKE)#370

Open
jimmielin wants to merge 19 commits intoESCOMP:mainfrom
jimmielin:hplin/diag_tke_rebase_main
Open

Complete CCPPization of CAM5 UW PBL scheme (diag_TKE)#370
jimmielin wants to merge 19 commits intoESCOMP:mainfrom
jimmielin:hplin/diag_tke_rebase_main

Conversation

@jimmielin
Copy link
Copy Markdown
Member

@jimmielin jimmielin commented Mar 9, 2026

Tag name (The PR title should also include the tag name):
Originator(s): @jimmielin

Companion PR in CAM - ESCOMP/CAM#1445

Description (include issue title and the keyword ['closes', 'fixes', 'resolves'] and issue number):

List all namelist files that were added or changed:

A       schemes/bretherton_park/bretherton_park_diff_namelist.xml
A       schemes/bretherton_park/eddy_diffusivity_adjustment_above_pbl_namelist.xml
  - for UW PBL

List all files eliminated and why: N/A

List all files added and what they do:

A       schemes/bretherton_park/bretherton_park_diff.F90
A       schemes/bretherton_park/bretherton_park_diff_namelist.xml
  - initial CCPPized subroutines for UW PBL

A       schemes/bretherton_park/eddy_diff.F90
  - moved from CAM (main driver module for UW PBL)

A       schemes/bretherton_park/eddy_diffusivity_adjustment_above_pbl.F90
A       schemes/bretherton_park/eddy_diffusivity_adjustment_above_pbl.meta
A       schemes/bretherton_park/eddy_diffusivity_adjustment_above_pbl_namelist.xml
  - mini-scheme used by the end of UW PBL

A       schemes/vertical_diffusion/vertical_diffusion_interstitials.F90
A       schemes/vertical_diffusion/vertical_diffusion_interstitials.meta
  - new interstitial for common vertical diffusion schemes
  - new interstitial for computing kinematic fluxes and Obukhov length

A       test/test_suites/suite_vdiff_bretherton_park.xml
  - SDF file

A       schemes/sima_diagnostics/bretherton_park_diff_diagnostics.F90
A       schemes/sima_diagnostics/bretherton_park_diff_diagnostics.meta
  - diagnostics for UW PBL

List all existing files that have been modified, and describe the changes:
(Helpful git command: git diff --name-status development...<your_branch_name>)

M       schemes/holtslag_boville/holtslag_boville_diff.F90
M       schemes/holtslag_boville/holtslag_boville_diff.meta
M       schemes/holtslag_boville/holtslag_boville_diff_interstitials.F90
M       schemes/holtslag_boville/holtslag_boville_diff_interstitials.meta
  - rearrange interstitials

M       schemes/sima_diagnostics/diffusion_solver_diagnostics.F90
  - comment update to clarify which surface stress is used here

M       schemes/vertical_diffusion/diffusion_solver.F90
M       schemes/vertical_diffusion/diffusion_solver.meta
  - init phase: changes for dropmixnuc (ndrop vertical mixing)-handled species to skip diffusion solver for tracers

M       schemes/vertical_diffusion/diffusion_stubs.F90
M       schemes/vertical_diffusion/diffusion_stubs.meta
  - new stub to only zero out Beljaars, not TMS
  - new stub for handling surface fluxes for dropmixnuc (ndrop vertical mixing)-handled species

M       suites/suite_cam4.xml
M       test/test_suites/suite_vdiff_holtslag_boville.xml
  - rearrange interstitials

M       test/test_schemes/initialize_constituents.F90
  - fix for #332 qmin incorrect for chemistry and aerosols species when initialized from snapshot

M       schemes/sima_diagnostics/diffusion_solver_diagnostics.F90
M       schemes/sima_diagnostics/diffusion_solver_diagnostics.meta
  - standard name update for clarity

List all automated tests that failed, as well as an explanation for why they weren't fixed:

Is this an answer-changing PR? If so, is it a new physics package, algorithm change, tuning change, etc?

If yes to the above question, describe how this code was validated with the new/modified features:

Copy link
Copy Markdown
Collaborator

@nusbaume nusbaume left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you so much for helping bring in our first (!) CAM5 physics scheme @jimmielin! I realize I have what look like a ton of comments, but hopefully the vast majority of them are easy to resolve. Of course if you have any questions, comments, or concerns with any of my suggestions then just let me know. Thanks again!

Comment on lines +26 to +32
integer, parameter :: nturb = 5

real(kind_phys), parameter :: ml2 = 30.0_kind_phys**2 ! mixing lengths squared for computing free air diffusivity
! used for interfaces in [ntop_eddy+1, nbot_eddy]

logical, parameter :: use_kvf = .false. ! .true. (.false.) : initialize kvh/kvm = kvf (0)
real(kind_phys), parameter :: lambda = 0.5_kind_phys ! Under-relaxation factor (0 < lambda =< 1)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can deal with this in a future PR, but if if these are all tunable parameters then it seems like it would be better if they were namelist variables instead of hardcoded parameters. Maybe worth making a "future work" issue?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good idea, I think we should also test if these can actually be tuned (particularly the logical paths I am worried that they might not actually work beyond the specified defaults) - added an issue here: #385

logical, intent(in) :: amIRoot
integer, intent(in) :: iulog
integer, intent(in) :: pver
integer, intent(in) :: pverp
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think pverp is actually used in this subroutine. Remove?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, removed!

use ccpp_constituent_prop_mod, only: ccpp_constituent_prop_ptr_t

! dependency to get constituent index
use ccpp_const_utils, only: ccpp_const_get_idx
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we use the CCPP-framework equivalent for this?

Suggested change
use ccpp_const_utils, only: ccpp_const_get_idx
use ccpp_scheme_utils, only: ccpp_const_get_idx=>ccpp_constituent_index

This way we can eventually get rid of the helper scheme we currently have in atmospheric_physics.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the suggestion! I think this doesn't have an equivalent stub in CAM yet - https://github.com/ESCOMP/CAM/blob/cam_development/src/utils/cam_ccpp/ccpp_scheme_utils.F90 is a no-op stub right now. I am happy to write the stub but that adds yet another tangential fix to the stub which will be a nightmare to my house of cards.

I added a CAM issue to write the stub: ESCOMP/CAM#1541

The atmos_phys issue is existing: #215 - I can volunteer at the end of CAM5 to sweep through all of these once the stub is in, if that is OK?

Comment on lines +259 to +260
real(kind_phys), intent(inout) :: tauresx(:) ! Residual stress to be added in vdiff to correct for turb [N m-2]
real(kind_phys), intent(inout) :: tauresy(:) ! Stress mismatch between sfc and atm accumulated in prior timesteps [N m-2]
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Definite nit-pick, but should we make these comments the same? I always assumed that they were the same quantity but in the X and Y directions.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No idea, I changed one but not the other. I updated it to a "two-line" comment since I need to annotate the inout, as well:

    real(kind_phys), intent(inout) :: tauresx(:)          ! Residual stress to be added in vdiff to correct for turb [N m-2]
    real(kind_phys), intent(inout) :: tauresy(:)          ! (in from previous timestep; output to current timestep)

integer :: i, k, iturb
integer :: const_wv_idx
integer :: ipbl(ncol) ! If 1, PBL is CL, while if 0, PBL is STL.
integer :: kpblh(ncol) ! Layer index containing PBL top within or at the base interface (NOT USED)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this isn't used then can we get rid of it entirely? It looks like it is purely diagnostic in caleddy (i.e. not used in any other variable calculations).

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, confirmed and removed!

! The following code is overbuilt for when ncvmax < pver
if (ncvmax < pver) then
tmp_lev = 0.0_kind_phys
tmp_lev(:, :ncvmax) = kbase_o(:, :ncvmax)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this order correct, or should it go from the bottom to the top of ncvmax?

Suggested change
tmp_lev(:, :ncvmax) = kbase_o(:, :ncvmax)
tmp_lev(:, (pver-ncvmax+1):pver) = kbase_o(:, ncvmax:)

This same question holds for all of the tmp_lev(:,:ncvmax) lines below as well.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This order is correct although strange. See eddy_diff.F90:

       ! The CL nearest to the surface is CL(1) and the CL index, ncv, increases 
       ! with height. The following outputs are from 'zisocl'. Here, the dimension
       ! of below outputs are (ncol,ncvmax) (except the 'ncvfin(ncol)' and
       ! 'belongcv(ncol,pver+1)) and 'ncv' goes from 1 to 'ncvfin'.

the ordering of the ncv diagnostics confusingly have no relationship with the vertical grid of the output (they just borrow the second dimension). CAM also just outputs these directly without vertical reordering.

Comment thread suites/suite_cam4.xml
<!-- hb pre-interstitial: tautotx/y -->
<scheme>tms_beljaars_zero_stub</scheme> <!-- stub as TMS/Beljaars not implemented -->
<scheme>hb_diff_set_total_surface_stress</scheme>
<!-- stub as TMS/Beljaars not used in CAM4 -->
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Given that we will now have our first CAM5 physics scheme, should we go ahead and create a suite_cam5.xml SDF as well? I believe it will basically be the same as suite_cam4.xml, except with HB replaced with Bretherthon-Park, Hack replaced with the UW shallow scheme, RK replaced with the Park macrophysics and PUMAS microphysics schemes, the cloud fraction schemes replaced with the "two moment" schemes, and the addition of the Beljaars form drag scheme.

Of course if you would like help with setting up the initial version of the SDF, or want to punt it to future work, then just let me know!

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For some reason I wrote it but only for uwshcu. Added now, thanks for the reminder!

errmsg = errmsg)
else
! For chemistry species some special handling is necessary for qmin_value;
! this logic is replicated from chem_register in src/chemistry/mozart.
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would just emphasize that this code is from CAM:

Suggested change
! this logic is replicated from chem_register in src/chemistry/mozart.
! this logic is replicated from chem_register in src/chemistry/mozart in CAM.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated, also will merge this file's more advanced version earlier in #384

Comment on lines +40 to +42
<!-- vdiff pre-interstitial 3: calculate total surface stresses
used for surface momentum flux diagnostic.
here, also used for HB. -->
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need this part of the comment given that HB isn't being used in this SDF?

Suggested change
<!-- vdiff pre-interstitial 3: calculate total surface stresses
used for surface momentum flux diagnostic.
here, also used for HB. -->
<!-- vdiff pre-interstitial 3: calculate total surface stresses
used for surface momentum flux diagnostic. -->

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I removed it since it was confusing, I meant this scheme was shared with HB as a reminder for when I was scoping out all of this. Thanks!


<!-- vdiff pre-interstitial 5: calculate damping rate from drag coef. -->
<scheme>vertical_diffusion_wind_damping_rate</scheme>
<!--<scheme>beljaars_add_wind_damping_rate</scheme>-->
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we need this commented-out scheme in this test SDF?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not here, but it needs to be added to the CAM5 suite when Beljaars is CCPPized. I kept it in suite_cam5 but removed it here.

nusbaume

This comment was marked as duplicate.

jimmielin and others added 2 commits April 21, 2026 17:11
@jimmielin jimmielin requested a review from nusbaume April 21, 2026 21:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

qmin for chemistry/aerosol species read in from snapshot are incorrectly initialized in initialize_constituents

2 participants