diff --git a/bld/CLMBuildNamelist.pm b/bld/CLMBuildNamelist.pm index 359909f94b..f25ceb2fae 100755 --- a/bld/CLMBuildNamelist.pm +++ b/bld/CLMBuildNamelist.pm @@ -1645,11 +1645,6 @@ sub process_namelist_inline_logic { ############################################# setup_logic_friction_vel($opts, $nl_flags, $definition, $defaults, $nl); - ################################################ - # namelist group: century_soilbgcdecompcascade # - ################################################ - setup_logic_century_soilbgcdecompcascade($opts, $nl_flags, $definition, $defaults, $nl); - ############################# # namelist group: cngeneral # ############################# @@ -3621,23 +3616,6 @@ sub setup_logic_soilwater_movement { } #------------------------------------------------------------------------------- -sub setup_logic_century_soilbgcdecompcascade { - # - my ($opts, $nl_flags, $definition, $defaults, $nl) = @_; - - if ( (&value_is_true($nl->get_value('use_cn')) || &value_is_true($nl->get_value('use_fates'))) && - &value_is_true($nl->get_value('use_century_decomp')) ) { - add_default($opts, $nl_flags->{'inputdata_rootdir'}, $definition, $defaults, $nl, 'initial_Cstocks', - 'use_cn' => $nl->get_value('use_cn'), 'use_fates' => $nl->get_value('use_fates'), - 'use_century_decomp' => $nl->get_value('use_century_decomp') ); - add_default($opts, $nl_flags->{'inputdata_rootdir'}, $definition, $defaults, $nl, 'initial_Cstocks_depth', - 'use_cn' => $nl->get_value('use_cn'), 'use_fates' => $nl->get_value('use_fates'), - 'use_century_decomp' => $nl->get_value('use_century_decomp') ); - } -} - -#------------------------------------------------------------------------------- - sub setup_logic_cnvegcarbonstate { # MUST be AFTER: setup_logic_dynamic_plant_nitrogen_alloc as depends on mm_nuptake_opt which is set there my ($opts, $nl_flags, $definition, $defaults, $nl) = @_; diff --git a/bld/namelist_files/namelist_defaults_ctsm.xml b/bld/namelist_files/namelist_defaults_ctsm.xml index 0dcc29680e..fbdc9f81fd 100644 --- a/bld/namelist_files/namelist_defaults_ctsm.xml +++ b/bld/namelist_files/namelist_defaults_ctsm.xml @@ -483,9 +483,9 @@ attributes from the config_cache.xml file (with keys converted to upper-case). -lnd/clm2/paramdata/ctsm51_params.c210305.nc -lnd/clm2/paramdata/clm50_params.c210217.nc -lnd/clm2/paramdata/clm45_params.c210217.nc +lnd/clm2/paramdata/ctsm51_params.c210528.nc +lnd/clm2/paramdata/clm50_params.c210528.nc +lnd/clm2/paramdata/clm45_params.c210528.nc @@ -1422,20 +1422,6 @@ lnd/clm2/surfdata_map/release-clm5.0.30/surfdata_ne0np4.CONUS.ne30x8_hist_78pfts 0.015d00 0.015d00 - -20.0d00, 20.0d00, 20.0d00 -200.0d00, 200.0d00, 200.0d00 -200.0d00, 200.0d00, 200.0d00 -20.0d00, 20.0d00, 20.0d00 -200.0d00, 200.0d00, 200.0d00 -200.0d00, 200.0d00, 200.0d00 - -1.50d00 -1.50d00 -0.3 -1.50d00 -1.50d00 -0.3 100.d00 100.d00 diff --git a/bld/namelist_files/namelist_definition_ctsm.xml b/bld/namelist_files/namelist_definition_ctsm.xml index d74989889c..f5bea80050 100644 --- a/bld/namelist_files/namelist_definition_ctsm.xml +++ b/bld/namelist_files/namelist_definition_ctsm.xml @@ -306,16 +306,6 @@ Critical threshold of negative Nitrogen to die (abort when Nitrogen states are b Critical threshold of negative Carbon to die (abort when Carbon states are below this value) - -Initial stocks of Carbon to use in soil organic matter pools for CENTURY decomposition - - - -Soil depth to place initial stocks of Carbon in soil organic matter pools for CENTURY decomposition - - Slope of free living Nitrogen fixation with annual ET diff --git a/cime_config/testdefs/ExpectedTestFails.xml b/cime_config/testdefs/ExpectedTestFails.xml index 1ec6606467..2584fdbf6b 100644 --- a/cime_config/testdefs/ExpectedTestFails.xml +++ b/cime_config/testdefs/ExpectedTestFails.xml @@ -79,6 +79,48 @@ + + FAIL + #1356 + + + + + + FAIL + #1356 + + + + + + FAIL + #1356 + + + + + FAIL + #1356 + + + + + + FAIL + #1356 + + + + + + FAIL + #1356 + + + diff --git a/doc/ChangeLog b/doc/ChangeLog index ecd9de8758..e575e27feb 100644 --- a/doc/ChangeLog +++ b/doc/ChangeLog @@ -1,4 +1,111 @@ =============================================================== +Tag name: ctsm5.1.dev043 +Originator(s): slevis/ekluzek (Samuel Levis,SLevis Consulting,303-665-1310) +Date: Thu Jun 3 17:14:30 MDT 2021 +One-line Summary: Refactor in preparation for MIMICS + +Purpose and description of changes +---------------------------------- + + Refactor aspects of the CTSM in preparation for our introduction of + MIMICS, which has started in #1318 . + + +Significant changes to scientifically-supported configurations +-------------------------------------------------------------- + +Does this tag change answers significantly for any of the following physics configurations? NO +(Details of any changes will be given in the "Answer changes" section below.) + + [Put an [X] in the box for any configuration with significant answer changes.] + +[ ] clm5_1 + +[ ] clm5_0 + +[ ] ctsm5_0-nwp + +[ ] clm4_5 + + +Bugs fixed or introduced +------------------------ +Known bugs introduced in this tag (include issue #): #1356, #1392 + #1356 -- CN is no longer just deprecated it breaks when you try to use it + #1392 -- Some soil decomposition history fields have the pool number rather than a descr. + +Notes of particular relevance for users +--------------------------------------- +Changes to CTSM's user interface (e.g., new/renamed XML or namelist variables): + Moved initial_Cstocks_depth_bgc and initial_Cstocks_bgc from the + namelist to the params file. Also renamed tau_cwd to tau_cwd_bgc and + k_frag to k_frag_cn in the params file according to the models that use + these parameters. + +Changes made to namelist defaults (e.g., changed parameter values): + initial_Cstocks_depth_bgc and initial_Cstocks_bgc are not namelist + variables anymore. + +Changes to the datasets (e.g., parameter, surface or initial files): + There are new params files for clm45, clm50, and ctsm51. + +Substantial timing or memory changes: + FAIL PFS_Ld20.f09_g17.I2000Clm50BgcCrop.cheyenne_intel MEMCOMP Error: Memory usage increase > 10% from baseline + Throughput doesn't seem to change. There might be an increase in memory as it's indicated for 20 tests. + And some arrays were changed to add an extra dimension. + +Testing summary: +---------------- + + [PASS means all tests PASS; OK means tests PASS other than expected fails.] + + build-namelist tests (if CLMBuildNamelist.pm has changed): + + cheyenne - PASS (785 tests are different because of new params files and removed namelist items) + + python testing (if python code has changed; see instructions in python/README.md; document testing done): + + cheyenne - PASS + + regular tests (aux_clm: https://github.com/ESCOMP/CTSM/wiki/System-Testing-Guide#pre-merge-system-testing): + + cheyenne ---- OK (read above in "bugs introduced" about CN failures) + izumi ------- OK (read below in "other testing" about pgi failures) + + any other testing (give details below): + Two unexpected tests fail on izumi, so I performed additional testing. + The tests that fail: + 1) SMS_D.f10_f10_mg37.I2000Clm51BgcCrop.izumi_pgi.clm-crop + BASELINE ctsm5.1.dev042: DIFF roundoff + 2) SMS.f10_f10_mg37.I2000Clm50BgcCrop.izumi_pgi.clm-crop + BASELINE ctsm5.1.dev042: DIFF greater than roundoff for CH4-related vars + I confirmed same result with my earlier commit against BASELINE dev033. + + Same tests but with gnu/intel instead of pgi pass on izumi for both + comparisons to dev042 and to dev033. These tests are part of the izumi + test-suite already. + + Additional testing: + Repeated these gnu/intel tests (had to run for baseline first) on cheyenne + and they passed. + +If the tag used for baseline comparisons was NOT the previous tag, note that here: + + +Answer changes +-------------- + +Changes answers relative to baseline: NO + + +Other details +------------- + +Pull Requests that document the changes (include PR ids): + https://github.com/ESCOMP/CTSM/pull/1340 + +=============================================================== +=============================================================== Tag name: ctsm5.1.dev042 Originator(s): erik (Erik Kluzek,UCAR/TSS,303-497-1326) Date: Fri May 28 14:07:45 MDT 2021 diff --git a/doc/ChangeSum b/doc/ChangeSum index f71295bc96..ab3857538d 100644 --- a/doc/ChangeSum +++ b/doc/ChangeSum @@ -1,5 +1,6 @@ Tag Who Date Summary ============================================================================================================================ + ctsm5.1.dev043 slevis 06/03/2021 Refactor of CascadeBGC code in preparation for MIMICS ctsm5.1.dev042 erik 05/28/2021 Small answer changes for double precision constants and soil limits ctsm5.1.dev041 rgknox 05/27/2021 bring FATES API up to sci.1.46.0_api.16.0.0 (methane and cn hooks) ctsm5.1.dev040 slevis 05/20/2021 mksurfdata_map: replace SRC files of various masks with SRC files w no mask diff --git a/src/biogeochem/CNC14DecayMod.F90 b/src/biogeochem/CNC14DecayMod.F90 index 2a4cbfb204..5a172fcb6e 100644 --- a/src/biogeochem/CNC14DecayMod.F90 +++ b/src/biogeochem/CNC14DecayMod.F90 @@ -6,7 +6,7 @@ module CNC14DecayMod ! !USES: use shr_kind_mod , only : r8 => shr_kind_r8 use clm_time_manager , only : get_step_size_real, get_days_per_year - use clm_varpar , only : ndecomp_cascade_transitions, nlevdecomp, ndecomp_pools + use clm_varpar , only : nlevdecomp, ndecomp_pools use clm_varcon , only : secspday use clm_varctl , only : spinup_state use decompMod , only : bounds_type diff --git a/src/biogeochem/CNCIsoFluxMod.F90 b/src/biogeochem/CNCIsoFluxMod.F90 index 922378b01f..09702f21b5 100644 --- a/src/biogeochem/CNCIsoFluxMod.F90 +++ b/src/biogeochem/CNCIsoFluxMod.F90 @@ -8,6 +8,7 @@ module CNCIsoFluxMod use shr_log_mod , only : errMsg => shr_log_errMsg use clm_varpar , only : ndecomp_cascade_transitions, nlevdecomp, ndecomp_pools use clm_varpar , only : max_patch_per_col, maxsoil_patches + use clm_varpar , only : i_litr_min, i_litr_max, i_met_lit use abortutils , only : endrun use pftconMod , only : pftcon use CNVegCarbonStateType , only : cnveg_carbonstate_type @@ -845,7 +846,7 @@ subroutine CIsoFlux3(num_soilc , filter_soilc, num_soilp , filter_soilp, & character(len=*) , intent(in) :: isotope ! 'c13' or 'c14' ! ! !LOCAL VARIABLES: - integer :: pi,pp,l,fc,cc,j + integer :: pi,pp,l,fc,cc,j,i !----------------------------------------------------------------------- associate( & @@ -861,12 +862,8 @@ subroutine CIsoFlux3(num_soilc , filter_soilc, num_soilp , filter_soilp, & iso_cnveg_cf => iso_cnveg_carbonflux_inst , & iso_cnveg_cs => iso_cnveg_carbonstate_inst , & iso_soilbiogeochem_cs => iso_soilbiogeochem_carbonstate_inst , & - lf_flab => pftcon%lf_flab , & ! Input: [real(r8) (:) ] leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: [real(r8) (:) ] leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: [real(r8) (:) ] leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: [real(r8) (:) ] fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: [real(r8) (:) ] fine root litter cellulose fraction - fr_flig => pftcon%fr_flig & ! Input: [real(r8) (:) ] fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: [real(r8) (:,:)] leaf litter fractions + fr_f => pftcon%fr_f & ! Input: [real(r8) (:,:)] fine root litter fractions ) ! patch-level fire mortality fluxes @@ -1132,13 +1129,14 @@ subroutine CIsoFlux3(num_soilc , filter_soilc, num_soilp , filter_soilp, & pp = col%patchi(cc) + pi - 1 if (patch%active(pp)) then do j = 1, nlevdecomp - iso_cnveg_cf%m_c_to_litr_met_fire_col(cc,j) = iso_cnveg_cf%m_c_to_litr_met_fire_col(cc,j) + & - ((iso_cnveg_cf%m_leafc_to_litter_fire_patch(pp)*lf_flab(ivt(pp)) & + iso_cnveg_cf%m_c_to_litr_fire_col(cc,j,i_met_lit) = & + iso_cnveg_cf%m_c_to_litr_fire_col(cc,j,i_met_lit) + & + ((iso_cnveg_cf%m_leafc_to_litter_fire_patch(pp) * lf_f(ivt(pp),i_met_lit) & +iso_cnveg_cf%m_leafc_storage_to_litter_fire_patch(pp) + & iso_cnveg_cf%m_leafc_xfer_to_litter_fire_patch(pp) + & iso_cnveg_cf%m_gresp_storage_to_litter_fire_patch(pp) & +iso_cnveg_cf%m_gresp_xfer_to_litter_fire_patch(pp))*leaf_prof(pp,j) + & - (iso_cnveg_cf%m_frootc_to_litter_fire_patch(pp)*fr_flab(ivt(pp)) & + (iso_cnveg_cf%m_frootc_to_litter_fire_patch(pp) * fr_f(ivt(pp),i_met_lit) & +iso_cnveg_cf%m_frootc_storage_to_litter_fire_patch(pp) + & iso_cnveg_cf%m_frootc_xfer_to_litter_fire_patch(pp))*froot_prof(pp,j) & +(iso_cnveg_cf%m_livestemc_storage_to_litter_fire_patch(pp) + & @@ -1150,13 +1148,15 @@ subroutine CIsoFlux3(num_soilc , filter_soilc, num_soilp , filter_soilp, & +iso_cnveg_cf%m_deadcrootc_storage_to_litter_fire_patch(pp) + & iso_cnveg_cf%m_deadcrootc_xfer_to_litter_fire_patch(pp))* croot_prof(pp,j)) * patch%wtcol(pp) - iso_cnveg_cf%m_c_to_litr_cel_fire_col(cc,j) = iso_cnveg_cf%m_c_to_litr_cel_fire_col(cc,j) + & - (iso_cnveg_cf%m_leafc_to_litter_fire_patch(pp)*lf_fcel(ivt(pp))*leaf_prof(pp,j) + & - iso_cnveg_cf%m_frootc_to_litter_fire_patch(pp)*fr_fcel(ivt(pp))*froot_prof(pp,j)) * patch%wtcol(pp) - - iso_cnveg_cf%m_c_to_litr_lig_fire_col(cc,j) = iso_cnveg_cf%m_c_to_litr_lig_fire_col(cc,j) + & - (iso_cnveg_cf%m_leafc_to_litter_fire_patch(pp)*lf_flig(ivt(pp))*leaf_prof(pp,j) + & - iso_cnveg_cf%m_frootc_to_litter_fire_patch(pp)*fr_flig(ivt(pp))*froot_prof(pp,j)) * patch%wtcol(pp) + ! Here metabolic litter is treated differently than other + ! types of litter, so it remains outside this litter loop, + ! in the line above + do i = i_met_lit+1, i_litr_max + iso_cnveg_cf%m_c_to_litr_fire_col(cc,j,i) = & + iso_cnveg_cf%m_c_to_litr_fire_col(cc,j,i) + & + (iso_cnveg_cf%m_leafc_to_litter_fire_patch(pp) * lf_f(ivt(pp),i) * leaf_prof(pp,j) + & + iso_cnveg_cf%m_frootc_to_litter_fire_patch(pp) * fr_f(ivt(pp),i) * froot_prof(pp,j)) * patch%wtcol(pp) + end do end do end if end if @@ -1188,19 +1188,15 @@ subroutine CNCIsoLitterToColumn (num_soilc, filter_soilc, & type(cnveg_carbonflux_type) , intent(inout) :: iso_cnveg_carbonflux_inst ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j + integer :: fc,c,pi,p,j,i !----------------------------------------------------------------------- associate( & ivt => patch%itype , & ! Input: [integer (:) ] patch vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] weight (relative to column) for this patch (0-1) - lf_flab => pftcon%lf_flab , & ! Input: leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: [real(r8) (:,:) ] leaf litter fractions + fr_f => pftcon%fr_f , & ! Input: [real(r8) (:,:) ] fine root litter fractions leaf_prof => soilbiogeochem_state_inst%leaf_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of leaves froot_prof => soilbiogeochem_state_inst%froot_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of fine roots @@ -1211,9 +1207,7 @@ subroutine CNCIsoLitterToColumn (num_soilc, filter_soilc, & livestemc_to_litter => iso_cnveg_carbonflux_inst%livestemc_to_litter_patch , & ! Input: [real(r8) (:) ] grainc_to_food => iso_cnveg_carbonflux_inst%grainc_to_food_patch , & ! Input: [real(r8) (:) ] !DML - phenology_c_to_litr_met_c => iso_cnveg_carbonflux_inst%phenology_c_to_litr_met_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter metabolic pool (gC/m3/s) - phenology_c_to_litr_cel_c => iso_cnveg_carbonflux_inst%phenology_c_to_litr_cel_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter cellulose pool (gC/m3/s) - phenology_c_to_litr_lig_c => iso_cnveg_carbonflux_inst%phenology_c_to_litr_lig_c_col & ! InOut: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter lignin pool (gC/m3/s) + phenology_c_to_litr_c => iso_cnveg_carbonflux_inst%phenology_c_to_litr_c_col & ! InOut: [real(r8) (:,:,:) ] C fluxes associated with phenology (litterfall and crop) to litter pools (gC/m3/s) ) do j = 1, nlevdecomp @@ -1224,40 +1218,31 @@ subroutine CNCIsoLitterToColumn (num_soilc, filter_soilc, & if ( pi <= col%npatches(c) ) then p = col%patchi(c) + pi - 1 if (patch%active(p)) then - ! leaf litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + ! leaf litter carbon fluxes + leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + & + ! fine root litter carbon fluxes + frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do !DML if (ivt(p) >= npcropmin) then ! add livestemc to litter ! stem litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + livestemc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + livestemc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + livestemc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) + do i = i_litr_min, i_litr_max + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + livestemc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + end do if (.not. use_grainproduct) then - ! grain litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + grainc_to_food(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + grainc_to_food(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + grainc_to_food(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) + ! grain litter carbon fluxes + do i = i_litr_min, i_litr_max + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + grainc_to_food(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + end do end if end if @@ -1289,19 +1274,15 @@ subroutine CNCIsoGapPftToColumn (num_soilc, filter_soilc, & type(cnveg_carbonflux_type) , intent(inout) :: iso_cnveg_carbonflux_inst ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j ! indices + integer :: fc,c,pi,p,j,i ! indices !----------------------------------------------------------------------- associate( & ivt => patch%itype , & ! Input: [integer (:) ] patch vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] patch weight relative to column (0-1) - lf_flab => pftcon%lf_flab , & ! Input: leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: leaf litter fractions + fr_f => pftcon%fr_f , & ! Input: fine root litter fractions leaf_prof => soilbiogeochem_state_inst%leaf_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of leaves froot_prof => soilbiogeochem_state_inst%froot_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of fine roots @@ -1329,9 +1310,7 @@ subroutine CNCIsoGapPftToColumn (num_soilc, filter_soilc, & m_deadcrootc_xfer_to_litter => iso_cnveg_carbonflux_inst%m_deadcrootc_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] m_gresp_xfer_to_litter => iso_cnveg_carbonflux_inst%m_gresp_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] - gap_mortality_c_to_litr_met_c => iso_cnveg_carbonflux_inst%gap_mortality_c_to_litr_met_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter metabolic pool (gC/m3/s) - gap_mortality_c_to_litr_cel_c => iso_cnveg_carbonflux_inst%gap_mortality_c_to_litr_cel_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter cellulose pool (gC/m3/s) - gap_mortality_c_to_litr_lig_c => iso_cnveg_carbonflux_inst%gap_mortality_c_to_litr_lig_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter lignin pool (gC/m3/s) + gap_mortality_c_to_litr_c => iso_cnveg_carbonflux_inst%gap_mortality_c_to_litr_c_col , & ! InOut: [real(r8) (:,:,:) ] C fluxes associated with gap mortality to litter pools (gC/m3/s) gap_mortality_c_to_cwdc => iso_cnveg_carbonflux_inst%gap_mortality_c_to_cwdc_col & ! InOut: [real(r8) (:,:) ] C fluxes associated with gap mortality to CWD pool (gC/m3/s) ) @@ -1345,21 +1324,16 @@ subroutine CNCIsoGapPftToColumn (num_soilc, filter_soilc, & if (patch%active(p)) then - ! leaf gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_cel_c(c,j) = gap_mortality_c_to_litr_cel_c(c,j) + & - m_leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_lig_c(c,j) = gap_mortality_c_to_litr_lig_c(c,j) + & - m_leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_cel_c(c,j) = gap_mortality_c_to_litr_cel_c(c,j) + & - m_frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_lig_c(c,j) = gap_mortality_c_to_litr_lig_c(c,j) + & - m_frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + ! leaf gap mortality carbon fluxes + gap_mortality_c_to_litr_c(c,j,i) = & + gap_mortality_c_to_litr_c(c,j,i) + & + m_leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + ! fine root gap mortality carbon fluxes + gap_mortality_c_to_litr_c(c,j,i) = & + gap_mortality_c_to_litr_c(c,j,i) + & + m_frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood gap mortality carbon fluxes gap_mortality_c_to_cwdc(c,j) = gap_mortality_c_to_cwdc(c,j) + & @@ -1371,37 +1345,27 @@ subroutine CNCIsoGapPftToColumn (num_soilc, filter_soilc, & gap_mortality_c_to_cwdc(c,j) = gap_mortality_c_to_cwdc(c,j) + & m_deadcrootc_to_litter(p) * wtcol(p) * croot_prof(p,j) - ! storage gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - - ! transfer gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + gap_mortality_c_to_litr_c(c,j,i_met_lit) = & + gap_mortality_c_to_litr_c(c,j,i_met_lit) + & + ! storage gap mortality carbon fluxes + m_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + m_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + m_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + m_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + m_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + m_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + m_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + ! transfer gap mortality carbon fluxes + m_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + m_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + m_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + m_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + m_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + m_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + m_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) end if end if @@ -1430,20 +1394,16 @@ subroutine CNCIsoHarvestPftToColumn (num_soilc, filter_soilc, & type(cnveg_carbonflux_type) , intent(inout) :: iso_cnveg_carbonflux_inst ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j ! indices + integer :: fc,c,pi,p,j,i ! indices !----------------------------------------------------------------------- associate( & ivt => patch%itype , & ! Input: [integer (:) ] patch vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] patch weight relative to column (0-1) - lf_flab => pftcon%lf_flab , & ! Input: leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: fine root litter lignin fraction - + lf_f => pftcon%lf_f , & ! Input: leaf litter fractions + fr_f => pftcon%fr_f , & ! Input: fine root litter fractions + leaf_prof => soilbiogeochem_state_inst%leaf_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of leaves froot_prof => soilbiogeochem_state_inst%froot_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of fine roots croot_prof => soilbiogeochem_state_inst%croot_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of coarse roots @@ -1470,9 +1430,7 @@ subroutine CNCIsoHarvestPftToColumn (num_soilc, filter_soilc, & hrv_deadcrootc_xfer_to_litter => iso_cnveg_carbonflux_inst%hrv_deadcrootc_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] hrv_gresp_xfer_to_litter => iso_cnveg_carbonflux_inst%hrv_gresp_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] cwood_harvestc => iso_cnveg_carbonflux_inst%wood_harvestc_col , & ! Output: [real(r8) (:) ] - harvest_c_to_litr_met_c => iso_cnveg_carbonflux_inst%harvest_c_to_litr_met_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with harvest to litter metabolic pool (gC/m3/s) - harvest_c_to_litr_cel_c => iso_cnveg_carbonflux_inst%harvest_c_to_litr_cel_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with harvest to litter cellulose pool (gC/m3/s) - harvest_c_to_litr_lig_c => iso_cnveg_carbonflux_inst%harvest_c_to_litr_lig_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with harvest to litter lignin pool (gC/m3/s) + harvest_c_to_litr_c => iso_cnveg_carbonflux_inst%harvest_c_to_litr_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with harvest to litter pools (gC/m3/s) harvest_c_to_cwdc => iso_cnveg_carbonflux_inst%harvest_c_to_cwdc_col & ! Output: [real(r8) (:,:) ] C fluxes associated with harvest to CWD pool (gC/m3/s) ) @@ -1486,21 +1444,17 @@ subroutine CNCIsoHarvestPftToColumn (num_soilc, filter_soilc, & if (patch%active(p)) then - ! leaf harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_cel_c(c,j) = harvest_c_to_litr_cel_c(c,j) + & - hrv_leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_lig_c(c,j) = harvest_c_to_litr_lig_c(c,j) + & - hrv_leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_cel_c(c,j) = harvest_c_to_litr_cel_c(c,j) + & - hrv_frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_lig_c(c,j) = harvest_c_to_litr_lig_c(c,j) + & - hrv_frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + ! leaf harvest mortality carbon fluxes + harvest_c_to_litr_c(c,j,i) = & + harvest_c_to_litr_c(c,j,i) + & + hrv_leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + + ! fine root harvest mortality carbon fluxes + harvest_c_to_litr_c(c,j,i) = & + harvest_c_to_litr_c(c,j,i) + & + hrv_frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood harvest mortality carbon fluxes harvest_c_to_cwdc(c,j) = harvest_c_to_cwdc(c,j) + & @@ -1510,37 +1464,27 @@ subroutine CNCIsoHarvestPftToColumn (num_soilc, filter_soilc, & harvest_c_to_cwdc(c,j) = harvest_c_to_cwdc(c,j) + & hrv_deadcrootc_to_litter(p) * wtcol(p) * croot_prof(p,j) - ! storage harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - - ! transfer harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + harvest_c_to_litr_c(c,j,i_met_lit) = & + harvest_c_to_litr_c(c,j,i_met_lit) + & + ! storage harvest mortality carbon fluxes + hrv_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + ! transfer harvest mortality carbon fluxes + hrv_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) end if end if diff --git a/src/biogeochem/CNCStateUpdate1Mod.F90 b/src/biogeochem/CNCStateUpdate1Mod.F90 index 5733509539..f7d097ab2b 100644 --- a/src/biogeochem/CNCStateUpdate1Mod.F90 +++ b/src/biogeochem/CNCStateUpdate1Mod.F90 @@ -8,7 +8,7 @@ module CNCStateUpdate1Mod use shr_log_mod , only : errMsg => shr_log_errMsg use clm_varpar , only : ndecomp_cascade_transitions, nlevdecomp use clm_time_manager , only : get_step_size_real - use clm_varpar , only : i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : i_litr_min, i_litr_max, i_cwd use pftconMod , only : npcropmin, nc3crop, pftcon use abortutils , only : endrun use decompMod , only : bounds_type @@ -52,6 +52,7 @@ subroutine CStateUpdateDynPatch(bounds, num_soilc_with_inactive, filter_soilc_wi integer :: fc ! column filter index integer :: g ! gridcell index integer :: j ! level index + integer :: i ! litter pool index real(r8) :: dt ! time step (seconds) character(len=*), parameter :: subname = 'CStateUpdateDynPatch' @@ -69,12 +70,11 @@ subroutine CStateUpdateDynPatch(bounds, num_soilc_with_inactive, filter_soilc_wi do j = 1,nlevdecomp do fc = 1, num_soilc_with_inactive c = filter_soilc_with_inactive(fc) - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) + & - cf_veg%dwt_frootc_to_litr_met_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) + & - cf_veg%dwt_frootc_to_litr_cel_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) + & - cf_veg%dwt_frootc_to_litr_lig_c_col(c,j) * dt + do i = i_litr_min, i_litr_max + cs_soil%decomp_cpools_vr_col(c,j,i) = & + cs_soil%decomp_cpools_vr_col(c,j,i) + & + cf_veg%dwt_frootc_to_litr_c_col(c,j,i) * dt + end do cs_soil%decomp_cpools_vr_col(c,j,i_cwd) = cs_soil%decomp_cpools_vr_col(c,j,i_cwd) + & ( cf_veg%dwt_livecrootc_to_cwdc_col(c,j) + cf_veg%dwt_deadcrootc_to_cwdc_col(c,j) ) * dt end do @@ -87,13 +87,6 @@ subroutine CStateUpdateDynPatch(bounds, num_soilc_with_inactive, filter_soilc_wi end if - ! TODO(wjs, 2017-01-02) Do we need to move some of the FATES fluxes into here (from - ! CStateUpdate1) if use_fates is true? Specifically, some portion or all of the fluxes - ! from these updates in CStateUpdate1: - ! cf_soil%decomp_cpools_sourcesink_col(c,j,i_met_lit) = cf_soil%FATES_c_to_litr_lab_c_col(c,j) * dt - ! cf_soil%decomp_cpools_sourcesink_col(c,j,i_cel_lit) = cf_soil%FATES_c_to_litr_cel_c_col(c,j) * dt - ! cf_soil%decomp_cpools_sourcesink_col(c,j,i_lig_lit) = cf_soil%FATES_c_to_litr_lig_c_col(c,j) * dt - end associate end subroutine CStateUpdateDynPatch @@ -161,7 +154,7 @@ subroutine CStateUpdate1( num_soilc, filter_soilc, num_soilp, filter_soilp, & logical , intent(in) :: dribble_crophrv_xsmrpool_2atm ! ! !LOCAL VARIABLES: - integer :: c,p,j,k,l ! indices + integer :: c,p,j,k,l,i ! indices integer :: fp,fc ! filter indices real(r8) :: dt ! radiation time step (seconds) real(r8) :: check_cpool @@ -195,13 +188,11 @@ subroutine CStateUpdate1( num_soilc, filter_soilc, num_soilp, filter_soilp, & do fc = 1,num_soilc c = filter_soilc(fc) ! phenology and dynamic land cover fluxes - cf_soil%decomp_cpools_sourcesink_col(c,j,i_met_lit) = & - cf_veg%phenology_c_to_litr_met_c_col(c,j) *dt - cf_soil%decomp_cpools_sourcesink_col(c,j,i_cel_lit) = & - cf_veg%phenology_c_to_litr_cel_c_col(c,j) *dt - cf_soil%decomp_cpools_sourcesink_col(c,j,i_lig_lit) = & - cf_veg%phenology_c_to_litr_lig_c_col(c,j) *dt - + do i = i_litr_min, i_litr_max + cf_soil%decomp_cpools_sourcesink_col(c,j,i) = & + cf_veg%phenology_c_to_litr_c_col(c,j,i) * dt + end do + ! NOTE(wjs, 2017-01-02) This used to be set to a non-zero value, but the ! terms have been moved to CStateUpdateDynPatch. I think this is zeroed every ! time step, but to be safe, I'm explicitly setting it to zero here. @@ -215,9 +206,10 @@ subroutine CStateUpdate1( num_soilc, filter_soilc, num_soilp, filter_soilp, & c = filter_soilc(fc) ! TODO(wjs, 2017-01-02) Should some portion or all of the following fluxes ! be moved to the updates in CStateUpdateDynPatch? - cf_soil%decomp_cpools_sourcesink_col(c,j,i_met_lit) = cf_soil%FATES_c_to_litr_lab_c_col(c,j) * dt - cf_soil%decomp_cpools_sourcesink_col(c,j,i_cel_lit) = cf_soil%FATES_c_to_litr_cel_c_col(c,j) * dt - cf_soil%decomp_cpools_sourcesink_col(c,j,i_lig_lit) = cf_soil%FATES_c_to_litr_lig_c_col(c,j) * dt + do i = i_litr_min, i_litr_max + cf_soil%decomp_cpools_sourcesink_col(c,j,i) = & + cf_soil%FATES_c_to_litr_c_col(c,j,i) * dt + end do end do end do endif diff --git a/src/biogeochem/CNCStateUpdate2Mod.F90 b/src/biogeochem/CNCStateUpdate2Mod.F90 index 276141271b..395fc7ee3b 100644 --- a/src/biogeochem/CNCStateUpdate2Mod.F90 +++ b/src/biogeochem/CNCStateUpdate2Mod.F90 @@ -9,7 +9,7 @@ module CNCStateUpdate2Mod use shr_log_mod , only : errMsg => shr_log_errMsg use abortutils , only : endrun use clm_time_manager , only : get_step_size_real - use clm_varpar , only : nlevdecomp, i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : i_litr_min, i_litr_max, nlevdecomp, i_cwd use CNvegCarbonStateType , only : cnveg_carbonstate_type use CNVegCarbonFluxType , only : cnveg_carbonflux_type use SoilBiogeochemCarbonStatetype , only : soilbiogeochem_carbonstate_type @@ -42,7 +42,7 @@ subroutine CStateUpdate2(num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_carbonstate_type) , intent(inout) :: soilbiogeochem_carbonstate_inst ! ! !LOCAL VARIABLES: - integer :: c ,p,j ! indices + integer :: c,p,j,i ! indices integer :: fp,fc ! lake filter indices real(r8) :: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -64,12 +64,13 @@ subroutine CStateUpdate2(num_soilc, filter_soilc, num_soilp, filter_soilp, & c = filter_soilc(fc) ! column gap mortality fluxes - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) + cf_veg%gap_mortality_c_to_litr_met_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) + cf_veg%gap_mortality_c_to_litr_cel_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) + cf_veg%gap_mortality_c_to_litr_lig_c_col(c,j) * dt + do i = i_litr_min, i_litr_max + cs_soil%decomp_cpools_vr_col(c,j,i) = & + cs_soil%decomp_cpools_vr_col(c,j,i) + & + cf_veg%gap_mortality_c_to_litr_c_col(c,j,i) * dt + end do + ! Currently i_cwd .ne. i_litr_max + 1 if .not. fates and + ! i_cwd = 0 if fates, so not including in the i-loop cs_soil%decomp_cpools_vr_col(c,j,i_cwd) = & cs_soil%decomp_cpools_vr_col(c,j,i_cwd) + cf_veg%gap_mortality_c_to_cwdc_col(c,j) * dt @@ -150,7 +151,7 @@ subroutine CStateUpdate2h(num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_carbonstate_type) , intent(inout) :: soilbiogeochem_carbonstate_inst ! ! !LOCAL VARIABLES: - integer :: c,p,j,k,l ! indices + integer :: c,p,j,k,l,i ! indices integer :: fp,fc ! lake filter indices real(r8):: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -170,12 +171,13 @@ subroutine CStateUpdate2h(num_soilc, filter_soilc, num_soilp, filter_soilp, & c = filter_soilc(fc) ! column harvest fluxes - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) + cf_veg%harvest_c_to_litr_met_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) + cf_veg%harvest_c_to_litr_cel_c_col(c,j) * dt - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) = & - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) + cf_veg%harvest_c_to_litr_lig_c_col(c,j) * dt + do i = i_litr_min, i_litr_max + cs_soil%decomp_cpools_vr_col(c,j,i) = & + cs_soil%decomp_cpools_vr_col(c,j,i) + & + cf_veg%harvest_c_to_litr_c_col(c,j,i) * dt + end do + ! Currently i_cwd .ne. i_litr_max + 1 if .not. fates and + ! i_cwd = 0 if fates, so not including in the i-loop cs_soil%decomp_cpools_vr_col(c,j,i_cwd) = & cs_soil%decomp_cpools_vr_col(c,j,i_cwd) + cf_veg%harvest_c_to_cwdc_col(c,j) * dt diff --git a/src/biogeochem/CNCStateUpdate3Mod.F90 b/src/biogeochem/CNCStateUpdate3Mod.F90 index aa5320efc1..8a54a7efc7 100644 --- a/src/biogeochem/CNCStateUpdate3Mod.F90 +++ b/src/biogeochem/CNCStateUpdate3Mod.F90 @@ -9,7 +9,7 @@ module CNCStateUpdate3Mod use shr_log_mod , only : errMsg => shr_log_errMsg use abortutils , only : endrun use clm_time_manager , only : get_step_size_real - use clm_varpar , only : nlevdecomp, ndecomp_pools, i_cwd, i_met_lit, i_cel_lit, i_lig_lit + use clm_varpar , only : nlevdecomp, ndecomp_pools, i_cwd, i_litr_min, i_litr_max use CNVegCarbonStateType , only : cnveg_carbonstate_type use CNVegCarbonFluxType , only : cnveg_carbonflux_type use SoilBiogeochemCarbonStateType , only : soilbiogeochem_carbonstate_type @@ -41,7 +41,7 @@ subroutine CStateUpdate3( num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_carbonstate_type) , intent(inout) :: soilbiogeochem_carbonstate_inst ! ! !LOCAL VARIABLES: - integer :: c,p,j,l,k ! indices + integer :: c,p,j,l,k,i ! indices integer :: fp,fc ! lake filter indices real(r8):: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -64,12 +64,11 @@ subroutine CStateUpdate3( num_soilc, filter_soilc, num_soilp, filter_soilp, & cf_veg%fire_mortality_c_to_cwdc_col(c,j) * dt ! patch-level wood to column-level litter (uncombusted wood) - cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_met_lit) + & - cf_veg%m_c_to_litr_met_fire_col(c,j)* dt - cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_cel_lit) + & - cf_veg%m_c_to_litr_cel_fire_col(c,j)* dt - cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) = cs_soil%decomp_cpools_vr_col(c,j,i_lig_lit) + & - cf_veg%m_c_to_litr_lig_fire_col(c,j)* dt + do i = i_litr_min, i_litr_max + cs_soil%decomp_cpools_vr_col(c,j,i) = & + cs_soil%decomp_cpools_vr_col(c,j,i) + & + cf_veg%m_c_to_litr_fire_col(c,j,i) * dt + end do end do end do diff --git a/src/biogeochem/CNFireBaseMod.F90 b/src/biogeochem/CNFireBaseMod.F90 index 4c83c5a9a5..e929757af6 100644 --- a/src/biogeochem/CNFireBaseMod.F90 +++ b/src/biogeochem/CNFireBaseMod.F90 @@ -445,7 +445,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte use clm_varcon , only: secspday use pftconMod , only: nc3crop use dynSubgridControlMod , only: run_has_transient_landcover - use clm_varpar , only: nlevdecomp_full, ndecomp_pools, nlevdecomp + use clm_varpar , only: nlevdecomp_full, ndecomp_pools, nlevdecomp, i_litr_max, i_met_lit ! ! !ARGUMENTS: class(cnfire_base_type) :: this @@ -470,7 +470,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte real(r8) , intent(out) :: somc_fire_col(bounds%begc:) ! (gC/m2/s) fire C emissions due to peat burning ! ! !LOCAL VARIABLES: - integer :: g,c,p,j,l,kyr, kmo, kda, mcsec ! indices + integer :: i,g,c,p,j,l,kyr, kmo, kda, mcsec ! indices integer :: fp,fc ! filter indices real(r8):: f ! rate for fire effects (1/s) real(r8):: m ! acceleration factor for fuel carbon @@ -524,12 +524,8 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte fm_root => pftcon%fm_root , & ! Input: fm_lroot => pftcon%fm_lroot , & ! Input: fm_droot => pftcon%fm_droot , & ! Input: - lf_flab => pftcon%lf_flab , & ! Input: - lf_fcel => pftcon%lf_fcel , & ! Input: - lf_flig => pftcon%lf_flig , & ! Input: - fr_flab => pftcon%fr_flab , & ! Input: - fr_fcel => pftcon%fr_fcel , & ! Input: - fr_flig => pftcon%fr_flig , & ! Input: + lf_f => pftcon%lf_f , & ! Input: + fr_f => pftcon%fr_f , & ! Input: cmb_cmplt_fact_litter => cnfire_const%cmb_cmplt_fact_litter , & ! Input: [real(r8) (:) ] Combustion completion factor for litter (unitless) cmb_cmplt_fact_cwd => cnfire_const%cmb_cmplt_fact_cwd , & ! Input: [real(r8) (:) ] Combustion completion factor for CWD (unitless) @@ -634,9 +630,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_gresp_storage_to_litter_fire => cnveg_carbonflux_inst%m_gresp_storage_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_gresp_xfer_to_litter_fire => cnveg_carbonflux_inst%m_gresp_xfer_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_decomp_cpools_to_fire_vr => cnveg_carbonflux_inst%m_decomp_cpools_to_fire_vr_col , & ! Output: [real(r8) (:,:,:) ] (gC/m3/s) VR decomp. C fire loss - m_c_to_litr_met_fire => cnveg_carbonflux_inst%m_c_to_litr_met_fire_col , & ! Output: [real(r8) (:,:) ] - m_c_to_litr_cel_fire => cnveg_carbonflux_inst%m_c_to_litr_cel_fire_col , & ! Output: [real(r8) (:,:) ] - m_c_to_litr_lig_fire => cnveg_carbonflux_inst%m_c_to_litr_lig_fire_col , & ! Output: [real(r8) (:,:) ] + m_c_to_litr_fire => cnveg_carbonflux_inst%m_c_to_litr_fire_col , & ! Output: [real(r8) (:,:,:) ] fire_mortality_n_to_cwdn => cnveg_nitrogenflux_inst%fire_mortality_n_to_cwdn_col , & ! Input: [real(r8) (:,:) ] N flux fire mortality to CWD (gN/m3/s) m_leafn_to_fire => cnveg_nitrogenflux_inst%m_leafn_to_fire_patch , & ! Input: [real(r8) (:) ] (gN/m2/s) N emis. leafn @@ -680,9 +674,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_deadcrootn_xfer_to_litter_fire => cnveg_nitrogenflux_inst%m_deadcrootn_xfer_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_retransn_to_litter_fire => cnveg_nitrogenflux_inst%m_retransn_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_decomp_npools_to_fire_vr => cnveg_nitrogenflux_inst%m_decomp_npools_to_fire_vr_col , & ! Output: [real(r8) (:,:,:) ] VR decomp. N fire loss (gN/m3/s) - m_n_to_litr_met_fire => cnveg_nitrogenflux_inst%m_n_to_litr_met_fire_col , & ! Output: [real(r8) (:,:) ] - m_n_to_litr_cel_fire => cnveg_nitrogenflux_inst%m_n_to_litr_cel_fire_col , & ! Output: [real(r8) (:,:) ] - m_n_to_litr_lig_fire => cnveg_nitrogenflux_inst%m_n_to_litr_lig_fire_col & ! Output: [real(r8) (:,:) ] + m_n_to_litr_fire => cnveg_nitrogenflux_inst%m_n_to_litr_fire_col & ! Output: [real(r8) (:,:,:) ] ) transient_landcover = run_has_transient_landcover() @@ -947,13 +939,14 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_livecrootn_to_litter_fire(p) * patch%wtcol(p) * croot_prof(p,j) - m_c_to_litr_met_fire(c,j)=m_c_to_litr_met_fire(c,j) + & - ((m_leafc_to_litter_fire(p)*lf_flab(patch%itype(p)) & + m_c_to_litr_fire(c,j,i_met_lit) = & + m_c_to_litr_fire(c,j,i_met_lit) + & + ((m_leafc_to_litter_fire(p) * lf_f(patch%itype(p),i_met_lit) & +m_leafc_storage_to_litter_fire(p) + & m_leafc_xfer_to_litter_fire(p) + & m_gresp_storage_to_litter_fire(p) & +m_gresp_xfer_to_litter_fire(p))*leaf_prof(p,j) + & - (m_frootc_to_litter_fire(p)*fr_flab(patch%itype(p)) & + (m_frootc_to_litter_fire(p) * fr_f(patch%itype(p),i_met_lit) & +m_frootc_storage_to_litter_fire(p) + & m_frootc_xfer_to_litter_fire(p))*froot_prof(p,j) & +(m_livestemc_storage_to_litter_fire(p) + & @@ -964,34 +957,41 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_livecrootc_xfer_to_litter_fire(p) & +m_deadcrootc_storage_to_litter_fire(p) + & m_deadcrootc_xfer_to_litter_fire(p))* croot_prof(p,j))* patch%wtcol(p) - m_c_to_litr_cel_fire(c,j)=m_c_to_litr_cel_fire(c,j) + & - (m_leafc_to_litter_fire(p)*lf_fcel(patch%itype(p))*leaf_prof(p,j) + & - m_frootc_to_litter_fire(p)*fr_fcel(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - m_c_to_litr_lig_fire(c,j)=m_c_to_litr_lig_fire(c,j) + & - (m_leafc_to_litter_fire(p)*lf_flig(patch%itype(p))*leaf_prof(p,j) + & - m_frootc_to_litter_fire(p)*fr_flig(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - - m_n_to_litr_met_fire(c,j)=m_n_to_litr_met_fire(c,j) + & - ((m_leafn_to_litter_fire(p)*lf_flab(patch%itype(p)) & - +m_leafn_storage_to_litter_fire(p) + & - m_leafn_xfer_to_litter_fire(p)+m_retransn_to_litter_fire(p)) & - *leaf_prof(p,j) +(m_frootn_to_litter_fire(p)*fr_flab(patch%itype(p)) & - +m_frootn_storage_to_litter_fire(p) + & - m_frootn_xfer_to_litter_fire(p))*froot_prof(p,j) & - +(m_livestemn_storage_to_litter_fire(p) + & - m_livestemn_xfer_to_litter_fire(p) & - +m_deadstemn_storage_to_litter_fire(p) + & - m_deadstemn_xfer_to_litter_fire(p))* stem_prof(p,j)& - +(m_livecrootn_storage_to_litter_fire(p) + & - m_livecrootn_xfer_to_litter_fire(p) & - +m_deadcrootn_storage_to_litter_fire(p) + & - m_deadcrootn_xfer_to_litter_fire(p))* croot_prof(p,j))* patch%wtcol(p) - m_n_to_litr_cel_fire(c,j)=m_n_to_litr_cel_fire(c,j) + & - (m_leafn_to_litter_fire(p)*lf_fcel(patch%itype(p))*leaf_prof(p,j) + & - m_frootn_to_litter_fire(p)*fr_fcel(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - m_n_to_litr_lig_fire(c,j)=m_n_to_litr_lig_fire(c,j) + & - (m_leafn_to_litter_fire(p)*lf_flig(patch%itype(p))*leaf_prof(p,j) + & - m_frootn_to_litter_fire(p)*fr_flig(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) + ! Here metabolic litter is treated differently than other + ! types of litter, so it remains outside this litter loop, + ! in the line above + do i = i_met_lit+1, i_litr_max + m_c_to_litr_fire(c,j,i) = m_c_to_litr_fire(c,j,i) + & + (m_leafc_to_litter_fire(p) * lf_f(patch%itype(p),i) * leaf_prof(p,j) + & + m_frootc_to_litter_fire(p) * fr_f(patch%itype(p),i) * froot_prof(p,j)) * patch%wtcol(p) + end do + + m_n_to_litr_fire(c,j,i_met_lit) = & + m_n_to_litr_fire(c,j,i_met_lit) + & + ((m_leafn_to_litter_fire(p) * lf_f(patch%itype(p),i_met_lit) + & + m_leafn_storage_to_litter_fire(p) + & + m_leafn_xfer_to_litter_fire(p) + & + m_retransn_to_litter_fire(p)) * leaf_prof(p,j) + & + (m_frootn_to_litter_fire(p) * fr_f(patch%itype(p),i_met_lit) + & + m_frootn_storage_to_litter_fire(p) + & + m_frootn_xfer_to_litter_fire(p)) * froot_prof(p,j) + & + (m_livestemn_storage_to_litter_fire(p) + & + m_livestemn_xfer_to_litter_fire(p) + & + m_deadstemn_storage_to_litter_fire(p) + & + m_deadstemn_xfer_to_litter_fire(p)) * stem_prof(p,j) + & + (m_livecrootn_storage_to_litter_fire(p) + & + m_livecrootn_xfer_to_litter_fire(p) + & + m_deadcrootn_storage_to_litter_fire(p) + & + m_deadcrootn_xfer_to_litter_fire(p)) * croot_prof(p,j)) * patch%wtcol(p) + ! Here metabolic litter is treated differently than other + ! types of litter, so it remains outside this litter loop, + ! in the line above + do i = i_met_lit+1, i_litr_max + m_n_to_litr_fire(c,j,i) = & + m_n_to_litr_fire(c,j,i) + & + (m_leafn_to_litter_fire(p) * lf_f(patch%itype(p),i) * leaf_prof(p,j) + & + m_frootn_to_litter_fire(p) * fr_f(patch%itype(p),i) * froot_prof(p,j)) * patch%wtcol(p) + end do end do end do ! diff --git a/src/biogeochem/CNFireLi2014Mod.F90 b/src/biogeochem/CNFireLi2014Mod.F90 index a520ba36e1..b9a6f705d0 100644 --- a/src/biogeochem/CNFireLi2014Mod.F90 +++ b/src/biogeochem/CNFireLi2014Mod.F90 @@ -649,6 +649,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte use clm_time_manager , only: get_step_size_real,get_days_per_year,get_curr_date use clm_varctl , only: use_cndv use clm_varcon , only: secspday + use clm_varpar , only: i_met_lit, i_litr_max use pftconMod , only: nc3crop use dynSubgridControlMod , only: run_has_transient_landcover ! @@ -675,7 +676,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte real(r8) , intent(out) :: somc_fire_col(bounds%begc:) ! (gC/m2/s) fire C emissions due to peat burning ! ! !LOCAL VARIABLES: - integer :: g,c,p,j,l,pi,kyr, kmo, kda, mcsec ! indices + integer :: i,g,c,p,j,l,pi,kyr, kmo, kda, mcsec ! indices integer :: fp,fc ! filter indices real(r8):: f ! rate for fire effects (1/s) real(r8):: m ! acceleration factor for fuel carbon @@ -729,12 +730,8 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte fm_root => pftcon%fm_root , & ! Input: fm_lroot => pftcon%fm_lroot , & ! Input: fm_droot => pftcon%fm_droot , & ! Input: - lf_flab => pftcon%lf_flab , & ! Input: - lf_fcel => pftcon%lf_fcel , & ! Input: - lf_flig => pftcon%lf_flig , & ! Input: - fr_flab => pftcon%fr_flab , & ! Input: - fr_fcel => pftcon%fr_fcel , & ! Input: - fr_flig => pftcon%fr_flig , & ! Input: + lf_f => pftcon%lf_f , & ! Input: + fr_f => pftcon%fr_f , & ! Input: nind => dgvs_inst%nind_patch , & ! Input: [real(r8) (:) ] number of individuals (#/m2) @@ -836,9 +833,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_gresp_storage_to_litter_fire => cnveg_carbonflux_inst%m_gresp_storage_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_gresp_xfer_to_litter_fire => cnveg_carbonflux_inst%m_gresp_xfer_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_decomp_cpools_to_fire_vr => cnveg_carbonflux_inst%m_decomp_cpools_to_fire_vr_col , & ! Output: [real(r8) (:,:,:) ] (gC/m3/s) VR decomp. C fire loss - m_c_to_litr_met_fire => cnveg_carbonflux_inst%m_c_to_litr_met_fire_col , & ! Output: [real(r8) (:,:) ] - m_c_to_litr_cel_fire => cnveg_carbonflux_inst%m_c_to_litr_cel_fire_col , & ! Output: [real(r8) (:,:) ] - m_c_to_litr_lig_fire => cnveg_carbonflux_inst%m_c_to_litr_lig_fire_col , & ! Output: [real(r8) (:,:) ] + m_c_to_litr_fire => cnveg_carbonflux_inst%m_c_to_litr_fire_col , & ! Output: [real(r8) (:,:,:) ] fire_mortality_n_to_cwdn => cnveg_nitrogenflux_inst%fire_mortality_n_to_cwdn_col , & ! Input: [real(r8) (:,:) ] N flux fire mortality to CWD (gN/m3/s) m_leafn_to_fire => cnveg_nitrogenflux_inst%m_leafn_to_fire_patch , & ! Input: [real(r8) (:) ] (gN/m2/s) N emis. leafn @@ -882,9 +877,7 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_deadcrootn_xfer_to_litter_fire => cnveg_nitrogenflux_inst%m_deadcrootn_xfer_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_retransn_to_litter_fire => cnveg_nitrogenflux_inst%m_retransn_to_litter_fire_patch , & ! Output: [real(r8) (:) ] m_decomp_npools_to_fire_vr => cnveg_nitrogenflux_inst%m_decomp_npools_to_fire_vr_col , & ! Output: [real(r8) (:,:,:) ] VR decomp. N fire loss (gN/m3/s) - m_n_to_litr_met_fire => cnveg_nitrogenflux_inst%m_n_to_litr_met_fire_col , & ! Output: [real(r8) (:,:) ] - m_n_to_litr_cel_fire => cnveg_nitrogenflux_inst%m_n_to_litr_cel_fire_col , & ! Output: [real(r8) (:,:) ] - m_n_to_litr_lig_fire => cnveg_nitrogenflux_inst%m_n_to_litr_lig_fire_col & ! Output: [real(r8) (:,:) ] + m_n_to_litr_fire => cnveg_nitrogenflux_inst%m_n_to_litr_fire_col & ! Output: [real(r8) (:,:,:) ] ) transient_landcover = run_has_transient_landcover() @@ -1133,13 +1126,14 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_livecrootn_to_litter_fire(p) * patch%wtcol(p) * croot_prof(p,j) - m_c_to_litr_met_fire(c,j)=m_c_to_litr_met_fire(c,j) + & - ((m_leafc_to_litter_fire(p)*lf_flab(patch%itype(p)) & + m_c_to_litr_fire(c,j,i_met_lit) = & + m_c_to_litr_fire(c,j,i_met_lit) + & + ((m_leafc_to_litter_fire(p) * lf_f(patch%itype(p),i_met_lit) & +m_leafc_storage_to_litter_fire(p) + & m_leafc_xfer_to_litter_fire(p) + & m_gresp_storage_to_litter_fire(p) & +m_gresp_xfer_to_litter_fire(p))*leaf_prof(p,j) + & - (m_frootc_to_litter_fire(p)*fr_flab(patch%itype(p)) & + (m_frootc_to_litter_fire(p) * fr_f(patch%itype(p),i_met_lit) & +m_frootc_storage_to_litter_fire(p) + & m_frootc_xfer_to_litter_fire(p))*froot_prof(p,j) & +(m_livestemc_storage_to_litter_fire(p) + & @@ -1150,34 +1144,35 @@ subroutine CNFireFluxes (this, bounds, num_soilc, filter_soilc, num_soilp, filte m_livecrootc_xfer_to_litter_fire(p) & +m_deadcrootc_storage_to_litter_fire(p) + & m_deadcrootc_xfer_to_litter_fire(p))* croot_prof(p,j))* patch%wtcol(p) - m_c_to_litr_cel_fire(c,j)=m_c_to_litr_cel_fire(c,j) + & - (m_leafc_to_litter_fire(p)*lf_fcel(patch%itype(p))*leaf_prof(p,j) + & - m_frootc_to_litter_fire(p)*fr_fcel(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - m_c_to_litr_lig_fire(c,j)=m_c_to_litr_lig_fire(c,j) + & - (m_leafc_to_litter_fire(p)*lf_flig(patch%itype(p))*leaf_prof(p,j) + & - m_frootc_to_litter_fire(p)*fr_flig(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - - m_n_to_litr_met_fire(c,j)=m_n_to_litr_met_fire(c,j) + & - ((m_leafn_to_litter_fire(p)*lf_flab(patch%itype(p)) & - +m_leafn_storage_to_litter_fire(p) + & - m_leafn_xfer_to_litter_fire(p)+m_retransn_to_litter_fire(p)) & - *leaf_prof(p,j) +(m_frootn_to_litter_fire(p)*fr_flab(patch%itype(p)) & - +m_frootn_storage_to_litter_fire(p) + & - m_frootn_xfer_to_litter_fire(p))*froot_prof(p,j) & - +(m_livestemn_storage_to_litter_fire(p) + & - m_livestemn_xfer_to_litter_fire(p) & - +m_deadstemn_storage_to_litter_fire(p) + & - m_deadstemn_xfer_to_litter_fire(p))* stem_prof(p,j)& - +(m_livecrootn_storage_to_litter_fire(p) + & - m_livecrootn_xfer_to_litter_fire(p) & - +m_deadcrootn_storage_to_litter_fire(p) + & - m_deadcrootn_xfer_to_litter_fire(p))* croot_prof(p,j))* patch%wtcol(p) - m_n_to_litr_cel_fire(c,j)=m_n_to_litr_cel_fire(c,j) + & - (m_leafn_to_litter_fire(p)*lf_fcel(patch%itype(p))*leaf_prof(p,j) + & - m_frootn_to_litter_fire(p)*fr_fcel(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) - m_n_to_litr_lig_fire(c,j)=m_n_to_litr_lig_fire(c,j) + & - (m_leafn_to_litter_fire(p)*lf_flig(patch%itype(p))*leaf_prof(p,j) + & - m_frootn_to_litter_fire(p)*fr_flig(patch%itype(p))*froot_prof(p,j))* patch%wtcol(p) + do i = i_met_lit+1, i_litr_max + m_c_to_litr_fire(c,j,i) = m_c_to_litr_fire(c,j,i) + & + (m_leafc_to_litter_fire(p) * lf_f(patch%itype(p),i) * leaf_prof(p,j) + & + m_frootc_to_litter_fire(p) * fr_f(patch%itype(p),i) * froot_prof(p,j)) * patch%wtcol(p) + end do + + m_n_to_litr_fire(c,j,i_met_lit) = & + m_n_to_litr_fire(c,j,i_met_lit) + & + ((m_leafn_to_litter_fire(p) * lf_f(patch%itype(p),i_met_lit) + & + m_leafn_storage_to_litter_fire(p) + & + m_leafn_xfer_to_litter_fire(p) + & + m_retransn_to_litter_fire(p)) * leaf_prof(p,j) + & + (m_frootn_to_litter_fire(p) * fr_f(patch%itype(p),i_met_lit) + & + m_frootn_storage_to_litter_fire(p) + & + m_frootn_xfer_to_litter_fire(p)) * froot_prof(p,j) + & + (m_livestemn_storage_to_litter_fire(p) + & + m_livestemn_xfer_to_litter_fire(p) + & + m_deadstemn_storage_to_litter_fire(p) + & + m_deadstemn_xfer_to_litter_fire(p)) * stem_prof(p,j) + & + (m_livecrootn_storage_to_litter_fire(p) + & + m_livecrootn_xfer_to_litter_fire(p) + & + m_deadcrootn_storage_to_litter_fire(p) + & + m_deadcrootn_xfer_to_litter_fire(p)) * croot_prof(p,j)) * patch%wtcol(p) + do i = i_met_lit+1, i_litr_max + m_n_to_litr_fire(c,j,i) = & + m_n_to_litr_fire(c,j,i) + & + (m_leafn_to_litter_fire(p) * lf_f(patch%itype(p),i) * leaf_prof(p,j) + & + m_frootn_to_litter_fire(p) * fr_f(patch%itype(p),i) * froot_prof(p,j)) * patch%wtcol(p) + end do end do end do ! diff --git a/src/biogeochem/CNGapMortalityMod.F90 b/src/biogeochem/CNGapMortalityMod.F90 index abd64cecc9..060a183688 100644 --- a/src/biogeochem/CNGapMortalityMod.F90 +++ b/src/biogeochem/CNGapMortalityMod.F90 @@ -287,7 +287,7 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & ! assigns them to the three litter pools ! ! !USES: - use clm_varpar , only : maxsoil_patches, nlevdecomp, nlevdecomp_full + use clm_varpar , only : maxsoil_patches, nlevdecomp, nlevdecomp_full, i_litr_min, i_litr_max, i_met_lit ! ! !ARGUMENTS: type(bounds_type) , intent(in) :: bounds @@ -301,7 +301,7 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & real(r8) , intent(in) :: stem_prof_patch(bounds%begp:,1:) ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j ! indices + integer :: fc,c,pi,p,j,i ! indices !----------------------------------------------------------------------- SHR_ASSERT_ALL_FL((ubound(leaf_prof_patch) == (/bounds%endp,nlevdecomp_full/)), sourcefile, __LINE__) @@ -318,12 +318,8 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & ivt => patch%itype , & ! Input: [integer (:) ] patch vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] patch weight relative to column (0-1) - lf_flab => pftcon%lf_flab , & ! Input: [real(r8) (:) ] leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: [real(r8) (:) ] leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: [real(r8) (:) ] leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: [real(r8) (:) ] fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: [real(r8) (:) ] fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: [real(r8) (:) ] fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: [real(r8) (:,:) ] leaf litter fractions + fr_f => pftcon%fr_f , & ! Input: [real(r8) (:,:) ] fine root litter fractions m_leafc_to_litter => cnveg_carbonflux_inst%m_leafc_to_litter_patch , & ! Input: [real(r8) (:) ] m_frootc_to_litter => cnveg_carbonflux_inst%m_frootc_to_litter_patch , & ! Input: [real(r8) (:) ] @@ -345,9 +341,7 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & m_livecrootc_xfer_to_litter => cnveg_carbonflux_inst%m_livecrootc_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] m_deadcrootc_xfer_to_litter => cnveg_carbonflux_inst%m_deadcrootc_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] m_gresp_xfer_to_litter => cnveg_carbonflux_inst%m_gresp_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] - gap_mortality_c_to_litr_met_c => cnveg_carbonflux_inst%gap_mortality_c_to_litr_met_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter metabolic pool (gC/m3/s) - gap_mortality_c_to_litr_cel_c => cnveg_carbonflux_inst%gap_mortality_c_to_litr_cel_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter cellulose pool (gC/m3/s) - gap_mortality_c_to_litr_lig_c => cnveg_carbonflux_inst%gap_mortality_c_to_litr_lig_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with gap mortality to litter lignin pool (gC/m3/s) + gap_mortality_c_to_litr_c => cnveg_carbonflux_inst%gap_mortality_c_to_litr_c_col , & ! Output: [real(r8) (:,:,:) ] C fluxes associated with gap mortality to litter pools (gC/m3/s) gap_mortality_c_to_cwdc => cnveg_carbonflux_inst%gap_mortality_c_to_cwdc_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with gap mortality to CWD pool (gC/m3/s) m_leafn_to_litter => cnveg_nitrogenflux_inst%m_leafn_to_litter_patch , & ! Input: [real(r8) (:) ] @@ -369,9 +363,7 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & m_deadstemn_xfer_to_litter => cnveg_nitrogenflux_inst%m_deadstemn_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] m_livecrootn_xfer_to_litter => cnveg_nitrogenflux_inst%m_livecrootn_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] m_deadcrootn_xfer_to_litter => cnveg_nitrogenflux_inst%m_deadcrootn_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] - gap_mortality_n_to_litr_met_n => cnveg_nitrogenflux_inst%gap_mortality_n_to_litr_met_n_col , & ! Output: [real(r8) (:,:) ] N fluxes associated with gap mortality to litter metabolic pool (gN/m3/s) - gap_mortality_n_to_litr_cel_n => cnveg_nitrogenflux_inst%gap_mortality_n_to_litr_cel_n_col , & ! Output: [real(r8) (:,:) ] N fluxes associated with gap mortality to litter cellulose pool (gN/m3/s) - gap_mortality_n_to_litr_lig_n => cnveg_nitrogenflux_inst%gap_mortality_n_to_litr_lig_n_col , & ! Output: [real(r8) (:,:) ] N fluxes associated with gap mortality to litter lignin pool (gN/m3/s) + gap_mortality_n_to_litr_n => cnveg_nitrogenflux_inst%gap_mortality_n_to_litr_n_col , & ! Output: [real(r8) (:,:,:)] N fluxes associated with gap mortality to litter pools (gN/m3/s) gap_mortality_n_to_cwdn => cnveg_nitrogenflux_inst%gap_mortality_n_to_cwdn_col & ! Output: [real(r8) (:,:) ] N fluxes associated with gap mortality to CWD pool (gN/m3/s) ) @@ -385,21 +377,14 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & if (patch%active(p)) then - ! leaf gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_cel_c(c,j) = gap_mortality_c_to_litr_cel_c(c,j) + & - m_leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_lig_c(c,j) = gap_mortality_c_to_litr_lig_c(c,j) + & - m_leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_cel_c(c,j) = gap_mortality_c_to_litr_cel_c(c,j) + & - m_frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_lig_c(c,j) = gap_mortality_c_to_litr_lig_c(c,j) + & - m_frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + gap_mortality_c_to_litr_c(c,j,i) = & + gap_mortality_c_to_litr_c(c,j,i) + & + ! leaf gap mortality carbon fluxes + m_leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + & + ! fine root gap mortality carbon fluxes + m_frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood gap mortality carbon fluxes gap_mortality_c_to_cwdc(c,j) = gap_mortality_c_to_cwdc(c,j) + & @@ -408,40 +393,30 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & (m_livecrootc_to_litter(p) + m_deadcrootc_to_litter(p)) * wtcol(p) * croot_prof(p,j) ! storage gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_leafc_storage_to_litter(p) + m_gresp_storage_to_litter(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_livestemc_storage_to_litter(p) + m_deadstemc_storage_to_litter(p)) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_livecrootc_storage_to_litter(p) + m_deadcrootc_storage_to_litter(p)) * wtcol(p) * croot_prof(p,j) + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + gap_mortality_c_to_litr_c(c,j,i_met_lit) = & + gap_mortality_c_to_litr_c(c,j,i_met_lit) + & + (m_leafc_storage_to_litter(p) + m_gresp_storage_to_litter(p)) * wtcol(p) * leaf_prof(p,j) + & + m_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + (m_livestemc_storage_to_litter(p) + m_deadstemc_storage_to_litter(p)) * wtcol(p) * stem_prof(p,j) + & + (m_livecrootc_storage_to_litter(p) + m_deadcrootc_storage_to_litter(p)) * wtcol(p) * croot_prof(p,j) + & ! transfer gap mortality carbon fluxes - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_leafc_xfer_to_litter(p) + m_gresp_xfer_to_litter(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - m_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_livestemc_xfer_to_litter(p) + m_deadstemc_xfer_to_litter(p)) * wtcol(p) * stem_prof(p,j) - gap_mortality_c_to_litr_met_c(c,j) = gap_mortality_c_to_litr_met_c(c,j) + & - (m_livecrootc_xfer_to_litter(p) + m_deadcrootc_xfer_to_litter(p)) * wtcol(p) * croot_prof(p,j) - - ! leaf gap mortality nitrogen fluxes - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_leafn_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_n_to_litr_cel_n(c,j) = gap_mortality_n_to_litr_cel_n(c,j) + & - m_leafn_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - gap_mortality_n_to_litr_lig_n(c,j) = gap_mortality_n_to_litr_lig_n(c,j) + & - m_leafn_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root litter nitrogen fluxes - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_frootn_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_n_to_litr_cel_n(c,j) = gap_mortality_n_to_litr_cel_n(c,j) + & - m_frootn_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - gap_mortality_n_to_litr_lig_n(c,j) = gap_mortality_n_to_litr_lig_n(c,j) + & - m_frootn_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + (m_leafc_xfer_to_litter(p) + m_gresp_xfer_to_litter(p)) * wtcol(p) * leaf_prof(p,j) + & + m_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + (m_livestemc_xfer_to_litter(p) + m_deadstemc_xfer_to_litter(p)) * wtcol(p) * stem_prof(p,j) + & + (m_livecrootc_xfer_to_litter(p) + m_deadcrootc_xfer_to_litter(p)) * wtcol(p) * croot_prof(p,j) + + do i = i_litr_min, i_litr_max + gap_mortality_n_to_litr_n(c,j,i) = & + gap_mortality_n_to_litr_n(c,j,i) + & + ! leaf gap mortality nitrogen fluxes + m_leafn_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + & + ! fine root litter nitrogen fluxes + m_frootn_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood gap mortality nitrogen fluxes gap_mortality_n_to_cwdn(c,j) = gap_mortality_n_to_cwdn(c,j) + & @@ -449,30 +424,23 @@ subroutine CNGap_PatchToColumn (bounds, num_soilc, filter_soilc, & gap_mortality_n_to_cwdn(c,j) = gap_mortality_n_to_cwdn(c,j) + & (m_livecrootn_to_litter(p) + m_deadcrootn_to_litter(p)) * wtcol(p) * croot_prof(p,j) - ! retranslocated N pool gap mortality fluxes - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_retransn_to_litter(p) * wtcol(p) * leaf_prof(p,j) - - ! storage gap mortality nitrogen fluxes - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_leafn_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_frootn_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - (m_livestemn_storage_to_litter(p) + m_deadstemn_storage_to_litter(p)) * wtcol(p) * stem_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - (m_livecrootn_storage_to_litter(p) + m_deadcrootn_storage_to_litter(p)) * wtcol(p) * croot_prof(p,j) - - ! transfer gap mortality nitrogen fluxes - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_leafn_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - m_frootn_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - (m_livestemn_xfer_to_litter(p) + m_deadstemn_xfer_to_litter(p)) * wtcol(p) * stem_prof(p,j) - gap_mortality_n_to_litr_met_n(c,j) = gap_mortality_n_to_litr_met_n(c,j) + & - (m_livecrootn_xfer_to_litter(p) + m_deadcrootn_xfer_to_litter(p)) * wtcol(p) * croot_prof(p,j) - + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + gap_mortality_n_to_litr_n(c,j,i_met_lit) = & + gap_mortality_n_to_litr_n(c,j,i_met_lit) + & + ! retranslocated N pool gap mortality fluxes + m_retransn_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + ! storage gap mortality nitrogen fluxes + m_leafn_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + m_frootn_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + (m_livestemn_storage_to_litter(p) + m_deadstemn_storage_to_litter(p)) * wtcol(p) * stem_prof(p,j) + & + (m_livecrootn_storage_to_litter(p) + m_deadcrootn_storage_to_litter(p)) * wtcol(p) * croot_prof(p,j) + & + ! transfer gap mortality nitrogen fluxes + m_leafn_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + m_frootn_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + (m_livestemn_xfer_to_litter(p) + m_deadstemn_xfer_to_litter(p)) * wtcol(p) * stem_prof(p,j) + & + (m_livecrootn_xfer_to_litter(p) + m_deadcrootn_xfer_to_litter(p)) * wtcol(p) * croot_prof(p,j) end if end if diff --git a/src/biogeochem/CNNStateUpdate1Mod.F90 b/src/biogeochem/CNNStateUpdate1Mod.F90 index bee931e7fc..72a7ff64e3 100644 --- a/src/biogeochem/CNNStateUpdate1Mod.F90 +++ b/src/biogeochem/CNNStateUpdate1Mod.F90 @@ -7,8 +7,8 @@ module CNNStateUpdate1Mod ! !USES: use shr_kind_mod , only: r8 => shr_kind_r8 use clm_time_manager , only : get_step_size_real - use clm_varpar , only : nlevdecomp, ndecomp_pools, ndecomp_cascade_transitions - use clm_varpar , only : i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : nlevdecomp + use clm_varpar , only : i_litr_min, i_litr_max, i_cwd use clm_varctl , only : iulog, use_nitrif_denitrif use clm_varcon , only : nitrif_n2o_loss_frac use pftconMod , only : npcropmin, pftcon @@ -49,6 +49,7 @@ subroutine NStateUpdateDynPatch(bounds, num_soilc_with_inactive, filter_soilc_wi integer :: g ! gridcell index integer :: fc ! column filter index integer :: j ! level index + integer :: i ! litter pool index real(r8) :: dt ! time step (seconds) character(len=*), parameter :: subname = 'NStateUpdateDynPatch' @@ -65,12 +66,11 @@ subroutine NStateUpdateDynPatch(bounds, num_soilc_with_inactive, filter_soilc_wi do j = 1, nlevdecomp do fc = 1, num_soilc_with_inactive c = filter_soilc_with_inactive(fc) - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) = ns_soil%decomp_npools_vr_col(c,j,i_met_lit) + & - nf_veg%dwt_frootn_to_litr_met_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) = ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) + & - nf_veg%dwt_frootn_to_litr_cel_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) = ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) + & - nf_veg%dwt_frootn_to_litr_lig_n_col(c,j) * dt + do i = i_litr_min, i_litr_max + ns_soil%decomp_npools_vr_col(c,j,i) = & + ns_soil%decomp_npools_vr_col(c,j,i) + & + nf_veg%dwt_frootn_to_litr_n_col(c,j,i) * dt + end do ns_soil%decomp_npools_vr_col(c,j,i_cwd) = ns_soil%decomp_npools_vr_col(c,j,i_cwd) + & ( nf_veg%dwt_livecrootn_to_cwdn_col(c,j) + nf_veg%dwt_deadcrootn_to_cwdn_col(c,j) ) * dt end do @@ -104,7 +104,7 @@ subroutine NStateUpdate1(num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_nitrogenflux_type) , intent(inout) :: soilbiogeochem_nitrogenflux_inst ! ! !LOCAL VARIABLES: - integer :: c,p,j,l,g,k ! indices + integer :: c,p,j,l,g,k,i ! indices integer :: fp,fc ! lake filter indices real(r8):: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -128,15 +128,10 @@ subroutine NStateUpdate1(num_soilc, filter_soilc, num_soilp, filter_soilp, & do j = 1, nlevdecomp do fc = 1,num_soilc c = filter_soilc(fc) - - nf_soil%decomp_npools_sourcesink_col(c,j,i_met_lit) = & - nf_veg%phenology_n_to_litr_met_n_col(c,j) * dt - - nf_soil%decomp_npools_sourcesink_col(c,j,i_cel_lit) = & - nf_veg%phenology_n_to_litr_cel_n_col(c,j) * dt - - nf_soil%decomp_npools_sourcesink_col(c,j,i_lig_lit) = & - nf_veg%phenology_n_to_litr_lig_n_col(c,j) * dt + do i = i_litr_min, i_litr_max + nf_soil%decomp_npools_sourcesink_col(c,j,i) = & + nf_veg%phenology_n_to_litr_n_col(c,j,i) * dt + end do ! NOTE(wjs, 2017-01-02) This used to be set to a non-zero value, but the ! terms have been moved to CStateUpdateDynPatch. I think this is zeroed every diff --git a/src/biogeochem/CNNStateUpdate2Mod.F90 b/src/biogeochem/CNNStateUpdate2Mod.F90 index b55a10c299..9b0a794a1a 100644 --- a/src/biogeochem/CNNStateUpdate2Mod.F90 +++ b/src/biogeochem/CNNStateUpdate2Mod.F90 @@ -8,7 +8,7 @@ module CNNStateUpdate2Mod use shr_kind_mod , only : r8 => shr_kind_r8 use clm_time_manager , only : get_step_size_real use clm_varpar , only : nlevsoi, nlevdecomp - use clm_varpar , only : i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : i_litr_min, i_litr_max, i_cwd use clm_varctl , only : iulog use CNVegNitrogenStateType , only : cnveg_nitrogenstate_type use CNVegNitrogenFluxType , only : cnveg_nitrogenflux_type @@ -44,7 +44,7 @@ subroutine NStateUpdate2(num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_nitrogenstate_type) , intent(inout) :: soilbiogeochem_nitrogenstate_inst ! ! !LOCAL VARIABLES: - integer :: c,p,j,l ! indices + integer :: c,p,j,l,i ! indices integer :: fp,fc ! lake filter indices real(r8) :: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -63,13 +63,13 @@ subroutine NStateUpdate2(num_soilc, filter_soilc, num_soilp, filter_soilp, & do j = 1, nlevdecomp do fc = 1,num_soilc c = filter_soilc(fc) - - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) + nf_veg%gap_mortality_n_to_litr_met_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) + nf_veg%gap_mortality_n_to_litr_cel_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) + nf_veg%gap_mortality_n_to_litr_lig_n_col(c,j) * dt + do i = i_litr_min, i_litr_max + ns_soil%decomp_npools_vr_col(c,j,i) = & + ns_soil%decomp_npools_vr_col(c,j,i) + & + nf_veg%gap_mortality_n_to_litr_n_col(c,j,i) * dt + end do + ! Currently i_cwd .ne. i_litr_max + 1 if .not. fates and + ! i_cwd = 0 if fates, so not including in the i-loop ns_soil%decomp_npools_vr_col(c,j,i_cwd) = & ns_soil%decomp_npools_vr_col(c,j,i_cwd) + nf_veg%gap_mortality_n_to_cwdn_col(c,j) * dt end do @@ -150,7 +150,7 @@ subroutine NStateUpdate2h(num_soilc, filter_soilc, num_soilp, filter_soilp, & type(soilbiogeochem_nitrogenstate_type) , intent(inout) :: soilbiogeochem_nitrogenstate_inst ! ! !LOCAL VARIABLES: - integer :: c,p,j,l ! indices + integer :: c,p,j,l,i ! indices integer :: fp,fc ! lake filter indices real(r8):: dt ! radiation time step (seconds) !----------------------------------------------------------------------- @@ -169,12 +169,13 @@ subroutine NStateUpdate2h(num_soilc, filter_soilc, num_soilp, filter_soilp, & do j = 1,nlevdecomp do fc = 1,num_soilc c = filter_soilc(fc) - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) + nf_veg%harvest_n_to_litr_met_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) + nf_veg%harvest_n_to_litr_cel_n_col(c,j) * dt - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) = & - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) + nf_veg%harvest_n_to_litr_lig_n_col(c,j) * dt + do i = i_litr_min, i_litr_max + ns_soil%decomp_npools_vr_col(c,j,i) = & + ns_soil%decomp_npools_vr_col(c,j,i) + & + nf_veg%harvest_n_to_litr_n_col(c,j,i) * dt + end do + ! Currently i_cwd .ne. i_litr_max + 1 if .not. fates and + ! i_cwd = 0 if fates, so not including in the i-loop ns_soil%decomp_npools_vr_col(c,j,i_cwd) = & ns_soil%decomp_npools_vr_col(c,j,i_cwd) + nf_veg%harvest_n_to_cwdn_col(c,j) * dt end do diff --git a/src/biogeochem/CNNStateUpdate3Mod.F90 b/src/biogeochem/CNNStateUpdate3Mod.F90 index 64ca7b51eb..d9753957f2 100644 --- a/src/biogeochem/CNNStateUpdate3Mod.F90 +++ b/src/biogeochem/CNNStateUpdate3Mod.F90 @@ -10,7 +10,7 @@ module CNNStateUpdate3Mod use clm_varpar , only: nlevdecomp, ndecomp_pools use clm_time_manager , only : get_step_size_real use clm_varctl , only : iulog, use_nitrif_denitrif - use clm_varpar , only : i_cwd, i_met_lit, i_cel_lit, i_lig_lit + use clm_varpar , only : i_litr_min, i_litr_max, i_cwd use CNVegNitrogenStateType , only : cnveg_nitrogenstate_type use CNVegNitrogenFluxType , only : cnveg_nitrogenflux_type use SoilBiogeochemNitrogenStateType , only : soilbiogeochem_nitrogenstate_type @@ -84,12 +84,11 @@ subroutine NStateUpdate3(num_soilc, filter_soilc, num_soilp, filter_soilp, & nf_veg%fire_mortality_n_to_cwdn_col(c,j) * dt ! patch-level wood to column-level litter (uncombusted wood) - ns_soil%decomp_npools_vr_col(c,j,i_met_lit) = ns_soil%decomp_npools_vr_col(c,j,i_met_lit) + & - nf_veg%m_n_to_litr_met_fire_col(c,j)* dt - ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) = ns_soil%decomp_npools_vr_col(c,j,i_cel_lit) + & - nf_veg%m_n_to_litr_cel_fire_col(c,j)* dt - ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) = ns_soil%decomp_npools_vr_col(c,j,i_lig_lit) + & - nf_veg%m_n_to_litr_lig_fire_col(c,j)* dt + do k = i_litr_min, i_litr_max + ns_soil%decomp_npools_vr_col(c,j,k) = & + ns_soil%decomp_npools_vr_col(c,j,k) + & + nf_veg%m_n_to_litr_fire_col(c,j,k) * dt + end do end do ! end of column loop end do diff --git a/src/biogeochem/CNPhenologyMod.F90 b/src/biogeochem/CNPhenologyMod.F90 index e81883ea91..b01294e45b 100644 --- a/src/biogeochem/CNPhenologyMod.F90 +++ b/src/biogeochem/CNPhenologyMod.F90 @@ -15,6 +15,7 @@ module CNPhenologyMod use shr_sys_mod , only : shr_sys_flush use decompMod , only : bounds_type use clm_varpar , only : maxveg, nlevdecomp_full + use clm_varpar , only : i_litr_min, i_litr_max use clm_varctl , only : iulog, use_cndv use clm_varcon , only : tfrz use abortutils , only : endrun @@ -2914,7 +2915,7 @@ subroutine CNLitterToColumn (bounds, num_soilc, filter_soilc, & real(r8) , intent(in) :: froot_prof_patch(bounds%begp:,1:) ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j ! indices + integer :: fc,c,pi,p,j,i ! indices !----------------------------------------------------------------------- SHR_ASSERT_ALL_FL((ubound(leaf_prof_patch) == (/bounds%endp,nlevdecomp_full/)), sourcefile, __LINE__) @@ -2927,28 +2928,20 @@ subroutine CNLitterToColumn (bounds, num_soilc, filter_soilc, & ivt => patch%itype , & ! Input: [integer (:) ] patch vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] weight (relative to column) for this patch (0-1) - lf_flab => pftcon%lf_flab , & ! Input: leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: leaf litter fractions + fr_f => pftcon%fr_f , & ! Input: fine root litter fractions leafc_to_litter => cnveg_carbonflux_inst%leafc_to_litter_patch , & ! Input: [real(r8) (:) ] leaf C litterfall (gC/m2/s) frootc_to_litter => cnveg_carbonflux_inst%frootc_to_litter_patch , & ! Input: [real(r8) (:) ] fine root N litterfall (gN/m2/s) livestemc_to_litter => cnveg_carbonflux_inst%livestemc_to_litter_patch , & ! Input: [real(r8) (:) ] live stem C litterfall (gC/m2/s) grainc_to_food => cnveg_carbonflux_inst%grainc_to_food_patch , & ! Input: [real(r8) (:) ] grain C to food (gC/m2/s) - phenology_c_to_litr_met_c => cnveg_carbonflux_inst%phenology_c_to_litr_met_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter metabolic pool (gC/m3/s) - phenology_c_to_litr_cel_c => cnveg_carbonflux_inst%phenology_c_to_litr_cel_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter cellulose pool (gC/m3/s) - phenology_c_to_litr_lig_c => cnveg_carbonflux_inst%phenology_c_to_litr_lig_c_col , & ! Output: [real(r8) (:,:) ] C fluxes associated with phenology (litterfall and crop) to litter lignin pool (gC/m3/s) + phenology_c_to_litr_c => cnveg_carbonflux_inst%phenology_c_to_litr_c_col , & ! Output: [real(r8) (:,:,:) ] C fluxes associated with phenology (litterfall and crop) to litter pools (gC/m3/s) livestemn_to_litter => cnveg_nitrogenflux_inst%livestemn_to_litter_patch , & ! Input: [real(r8) (:) ] livestem N to litter (gN/m2/s) grainn_to_food => cnveg_nitrogenflux_inst%grainn_to_food_patch , & ! Input: [real(r8) (:) ] grain N to food (gN/m2/s) leafn_to_litter => cnveg_nitrogenflux_inst%leafn_to_litter_patch , & ! Input: [real(r8) (:) ] leaf N litterfall (gN/m2/s) frootn_to_litter => cnveg_nitrogenflux_inst%frootn_to_litter_patch , & ! Input: [real(r8) (:) ] fine root N litterfall (gN/m2/s) - phenology_n_to_litr_met_n => cnveg_nitrogenflux_inst%phenology_n_to_litr_met_n_col , & ! Output: [real(r8) (:,:) ] N fluxes associated with phenology (litterfall and crop) to litter metabolic pool (gN/m3/s) - phenology_n_to_litr_cel_n => cnveg_nitrogenflux_inst%phenology_n_to_litr_cel_n_col , & ! Output: [real(r8) (:,:) ] N fluxes associated with phenology (litterfall and crop) to litter cellulose pool (gN/m3/s) - phenology_n_to_litr_lig_n => cnveg_nitrogenflux_inst%phenology_n_to_litr_lig_n_col & ! Output: [real(r8) (:,:) ] N fluxes associated with phenology (litterfall and crop) to litter lignin pool (gN/m3/s) + phenology_n_to_litr_n => cnveg_nitrogenflux_inst%phenology_n_to_litr_n_col & ! Output: [real(r8) (:,:,:) ] N fluxes associated with phenology (litterfall and crop) to litter pools (gN/m3/s) ) do j = 1, nlevdecomp @@ -2960,37 +2953,27 @@ subroutine CNLitterToColumn (bounds, num_soilc, filter_soilc, & p = col%patchi(c) + pi - 1 if (patch%active(p)) then - ! leaf litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! leaf litter nitrogen fluxes - phenology_n_to_litr_met_n(c,j) = phenology_n_to_litr_met_n(c,j) & - + leafn_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_cel_n(c,j) = phenology_n_to_litr_cel_n(c,j) & - + leafn_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_lig_n(c,j) = phenology_n_to_litr_lig_n(c,j) & - + leafn_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) - - ! fine root litter nitrogen fluxes - phenology_n_to_litr_met_n(c,j) = phenology_n_to_litr_met_n(c,j) & - + frootn_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_n_to_litr_cel_n(c,j) = phenology_n_to_litr_cel_n(c,j) & - + frootn_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - phenology_n_to_litr_lig_n(c,j) = phenology_n_to_litr_lig_n(c,j) & - + frootn_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + ! leaf litter carbon fluxes + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + + ! leaf litter nitrogen fluxes + phenology_n_to_litr_n(c,j,i) = & + phenology_n_to_litr_n(c,j,i) + & + leafn_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + + ! fine root litter carbon fluxes + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + + ! fine root litter nitrogen fluxes + phenology_n_to_litr_n(c,j,i) = & + phenology_n_to_litr_n(c,j,i) + & + frootn_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! agroibis puts crop stem litter together with leaf litter ! so I've used the leaf lf_f* parameters instead of making @@ -2998,38 +2981,30 @@ subroutine CNLitterToColumn (bounds, num_soilc, filter_soilc, & ! also for simplicity I've put "food" into the litter pools if (ivt(p) >= npcropmin) then ! add livestemc to litter - ! stem litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + livestemc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + livestemc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + livestemc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! stem litter nitrogen fluxes - phenology_n_to_litr_met_n(c,j) = phenology_n_to_litr_met_n(c,j) & - + livestemn_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_cel_n(c,j) = phenology_n_to_litr_cel_n(c,j) & - + livestemn_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_lig_n(c,j) = phenology_n_to_litr_lig_n(c,j) & - + livestemn_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) + do i = i_litr_min, i_litr_max + ! stem litter carbon fluxes + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + livestemc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + + ! stem litter nitrogen fluxes + phenology_n_to_litr_n(c,j,i) = & + phenology_n_to_litr_n(c,j,i) + & + livestemn_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + end do if (.not. use_grainproduct) then - ! grain litter carbon fluxes - phenology_c_to_litr_met_c(c,j) = phenology_c_to_litr_met_c(c,j) & - + grainc_to_food(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_cel_c(c,j) = phenology_c_to_litr_cel_c(c,j) & - + grainc_to_food(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_c_to_litr_lig_c(c,j) = phenology_c_to_litr_lig_c(c,j) & - + grainc_to_food(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) + do i = i_litr_min, i_litr_max + ! grain litter carbon fluxes + phenology_c_to_litr_c(c,j,i) = & + phenology_c_to_litr_c(c,j,i) + & + grainc_to_food(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) - ! grain litter nitrogen fluxes - phenology_n_to_litr_met_n(c,j) = phenology_n_to_litr_met_n(c,j) & - + grainn_to_food(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_cel_n(c,j) = phenology_n_to_litr_cel_n(c,j) & - + grainn_to_food(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - phenology_n_to_litr_lig_n(c,j) = phenology_n_to_litr_lig_n(c,j) & - + grainn_to_food(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) + ! grain litter nitrogen fluxes + phenology_n_to_litr_n(c,j,i) = & + phenology_n_to_litr_n(c,j,i) + & + grainn_to_food(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + end do end if diff --git a/src/biogeochem/CNVegCarbonFluxType.F90 b/src/biogeochem/CNVegCarbonFluxType.F90 index 16b0ada09b..061f3d3366 100644 --- a/src/biogeochem/CNVegCarbonFluxType.F90 +++ b/src/biogeochem/CNVegCarbonFluxType.F90 @@ -11,7 +11,7 @@ module CNVegCarbonFluxType use decompMod , only : bounds_type use SoilBiogeochemDecompCascadeConType , only : decomp_cascade_con use clm_varpar , only : ndecomp_cascade_transitions, ndecomp_pools - use clm_varpar , only : nlevdecomp_full, nlevgrnd, nlevdecomp + use clm_varpar , only : nlevdecomp_full, nlevdecomp, i_litr_min, i_litr_max use clm_varcon , only : spval, dzsoi_decomp use clm_varctl , only : use_cndv, use_c13, use_nitrif_denitrif, use_crop use clm_varctl , only : use_grainproduct @@ -230,23 +230,17 @@ module CNVegCarbonFluxType real(r8), pointer :: livecrootc_to_deadcrootc_patch (:) ! live coarse root C turnover (gC/m2/s) ! phenology: litterfall and crop fluxes - real(r8), pointer :: phenology_c_to_litr_met_c_col (:,:) ! C fluxes associated with phenology (litterfall and crop) to litter metabolic pool (gC/m3/s) - real(r8), pointer :: phenology_c_to_litr_cel_c_col (:,:) ! C fluxes associated with phenology (litterfall and crop) to litter cellulose pool (gC/m3/s) - real(r8), pointer :: phenology_c_to_litr_lig_c_col (:,:) ! C fluxes associated with phenology (litterfall and crop) to litter lignin pool (gC/m3/s) + real(r8), pointer :: phenology_c_to_litr_c_col (:,:,:) ! C fluxes associated with phenology (litterfall and crop) to litter pools (gC/m3/s) ! gap mortality - real(r8), pointer :: gap_mortality_c_to_litr_met_c_col (:,:) ! C fluxes associated with gap mortality to litter metabolic pool (gC/m3/s) - real(r8), pointer :: gap_mortality_c_to_litr_cel_c_col (:,:) ! C fluxes associated with gap mortality to litter cellulose pool (gC/m3/s) - real(r8), pointer :: gap_mortality_c_to_litr_lig_c_col (:,:) ! C fluxes associated with gap mortality to litter lignin pool (gC/m3/s) + real(r8), pointer :: gap_mortality_c_to_litr_c_col (:,:,:) ! C fluxes associated with gap mortality to litter pools (gC/m3/s) real(r8), pointer :: gap_mortality_c_to_cwdc_col (:,:) ! C fluxes associated with gap mortality to CWD pool (gC/m3/s) ! fire real(r8), pointer :: fire_mortality_c_to_cwdc_col (:,:) ! C fluxes associated with fire mortality to CWD pool (gC/m3/s) ! harvest - real(r8), pointer :: harvest_c_to_litr_met_c_col (:,:) ! C fluxes associated with harvest to litter metabolic pool (gC/m3/s) - real(r8), pointer :: harvest_c_to_litr_cel_c_col (:,:) ! C fluxes associated with harvest to litter cellulose pool (gC/m3/s) - real(r8), pointer :: harvest_c_to_litr_lig_c_col (:,:) ! C fluxes associated with harvest to litter lignin pool (gC/m3/s) + real(r8), pointer :: harvest_c_to_litr_c_col (:,:,:) ! C fluxes associated with harvest to litter pools (gC/m3/s) real(r8), pointer :: harvest_c_to_cwdc_col (:,:) ! C fluxes associated with harvest to CWD pool (gC/m3/s) real(r8), pointer :: grainc_to_cropprodc_patch (:) ! grain C to crop product pool (gC/m2/s) real(r8), pointer :: grainc_to_cropprodc_col (:) ! grain C to crop product pool (gC/m2/s) @@ -254,9 +248,7 @@ module CNVegCarbonFluxType ! fire fluxes real(r8), pointer :: m_decomp_cpools_to_fire_vr_col (:,:,:) ! vertically-resolved decomposing C fire loss (gC/m3/s) real(r8), pointer :: m_decomp_cpools_to_fire_col (:,:) ! vertically-integrated (diagnostic) decomposing C fire loss (gC/m2/s) - real(r8), pointer :: m_c_to_litr_met_fire_col (:,:) ! C from leaf, froot, xfer and storage C to litter labile C by fire (gC/m3/s) - real(r8), pointer :: m_c_to_litr_cel_fire_col (:,:) ! C from leaf, froot, xfer and storage C to litter cellulose C by fire (gC/m3/s) - real(r8), pointer :: m_c_to_litr_lig_fire_col (:,:) ! C from leaf, froot, xfer and storage C to litter lignin C by fire (gC/m3/s) + real(r8), pointer :: m_c_to_litr_fire_col (:,:,:) ! C from leaf, froot, xfer and storage C to litter C by fire (gC/m3/s) ! dynamic landcover fluxes real(r8), pointer :: dwt_seedc_to_leaf_patch (:) ! (gC/m2/s) seed source to patch-level; although this is a patch-level flux, it is expressed per unit GRIDCELL area @@ -270,9 +262,7 @@ module CNVegCarbonFluxType real(r8), pointer :: dwt_crop_productc_gain_patch (:) ! (gC/m2/s) addition to crop product pools from landcover change; although this is a patch-level flux, it is expressed per unit GRIDCELL area real(r8), pointer :: dwt_slash_cflux_patch (:) ! (gC/m2/s) conversion slash flux due to landcover change real(r8), pointer :: dwt_slash_cflux_grc (:) ! (gC/m2/s) dwt_slash_cflux_patch summed to the gridcell-level - real(r8), pointer :: dwt_frootc_to_litr_met_c_col (:,:) ! (gC/m3/s) fine root to litter due to landcover change - real(r8), pointer :: dwt_frootc_to_litr_cel_c_col (:,:) ! (gC/m3/s) fine root to litter due to landcover change - real(r8), pointer :: dwt_frootc_to_litr_lig_c_col (:,:) ! (gC/m3/s) fine root to litter due to landcover change + real(r8), pointer :: dwt_frootc_to_litr_c_col (:,:,:) ! (gC/m3/s) fine root to litter due to landcover change real(r8), pointer :: dwt_livecrootc_to_cwdc_col (:,:) ! (gC/m3/s) live coarse root to CWD due to landcover change real(r8), pointer :: dwt_deadcrootc_to_cwdc_col (:,:) ! (gC/m3/s) dead coarse root to CWD due to landcover change @@ -622,31 +612,22 @@ subroutine InitAllocate(this, bounds, carbon_type) allocate(this%woodc_alloc_patch (begp:endp)) ; this%woodc_alloc_patch (:) = nan allocate(this%woodc_loss_patch (begp:endp)) ; this%woodc_loss_patch (:) = nan - allocate(this%phenology_c_to_litr_met_c_col (begc:endc,1:nlevdecomp_full)); - this%phenology_c_to_litr_met_c_col (:,:)=nan - - allocate(this%phenology_c_to_litr_cel_c_col (begc:endc,1:nlevdecomp_full)); this%phenology_c_to_litr_cel_c_col (:,:)=nan - allocate(this%phenology_c_to_litr_lig_c_col (begc:endc,1:nlevdecomp_full)); this%phenology_c_to_litr_lig_c_col (:,:)=nan - - allocate(this%gap_mortality_c_to_litr_met_c_col (begc:endc,1:nlevdecomp_full)); this%gap_mortality_c_to_litr_met_c_col(:,:)=nan - allocate(this%gap_mortality_c_to_litr_cel_c_col (begc:endc,1:nlevdecomp_full)); this%gap_mortality_c_to_litr_cel_c_col(:,:)=nan - allocate(this%gap_mortality_c_to_litr_lig_c_col (begc:endc,1:nlevdecomp_full)); this%gap_mortality_c_to_litr_lig_c_col(:,:)=nan + ! Third dimension not i_litr_max because that parameter may obtain its + ! value after we've been through here + allocate(this%phenology_c_to_litr_c_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)); this%phenology_c_to_litr_c_col (:,:,:)=nan + allocate(this%gap_mortality_c_to_litr_c_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)); this%gap_mortality_c_to_litr_c_col(:,:,:)=nan allocate(this%gap_mortality_c_to_cwdc_col (begc:endc,1:nlevdecomp_full)); this%gap_mortality_c_to_cwdc_col (:,:)=nan allocate(this%fire_mortality_c_to_cwdc_col (begc:endc,1:nlevdecomp_full)); this%fire_mortality_c_to_cwdc_col (:,:)=nan - allocate(this%m_c_to_litr_met_fire_col (begc:endc,1:nlevdecomp_full)); this%m_c_to_litr_met_fire_col (:,:)=nan - allocate(this%m_c_to_litr_cel_fire_col (begc:endc,1:nlevdecomp_full)); this%m_c_to_litr_cel_fire_col (:,:)=nan - allocate(this%m_c_to_litr_lig_fire_col (begc:endc,1:nlevdecomp_full)); this%m_c_to_litr_lig_fire_col (:,:)=nan - allocate(this%harvest_c_to_litr_met_c_col (begc:endc,1:nlevdecomp_full)); this%harvest_c_to_litr_met_c_col (:,:)=nan - allocate(this%harvest_c_to_litr_cel_c_col (begc:endc,1:nlevdecomp_full)); this%harvest_c_to_litr_cel_c_col (:,:)=nan - allocate(this%harvest_c_to_litr_lig_c_col (begc:endc,1:nlevdecomp_full)); this%harvest_c_to_litr_lig_c_col (:,:)=nan + allocate(this%m_c_to_litr_fire_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)); this%m_c_to_litr_fire_col (:,:,:)=nan + allocate(this%harvest_c_to_litr_c_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)); this%harvest_c_to_litr_c_col (:,:,:)=nan allocate(this%harvest_c_to_cwdc_col (begc:endc,1:nlevdecomp_full)); this%harvest_c_to_cwdc_col (:,:)=nan allocate(this%dwt_slash_cflux_patch (begp:endp)) ; this%dwt_slash_cflux_patch (:) =nan allocate(this%dwt_slash_cflux_grc (begg:endg)) ; this%dwt_slash_cflux_grc (:) =nan - allocate(this%dwt_frootc_to_litr_met_c_col (begc:endc,1:nlevdecomp_full)); this%dwt_frootc_to_litr_met_c_col (:,:)=nan - allocate(this%dwt_frootc_to_litr_cel_c_col (begc:endc,1:nlevdecomp_full)); this%dwt_frootc_to_litr_cel_c_col (:,:)=nan - allocate(this%dwt_frootc_to_litr_lig_c_col (begc:endc,1:nlevdecomp_full)); this%dwt_frootc_to_litr_lig_c_col (:,:)=nan + ! Third dimension not i_litr_max because that parameter may obtain its + ! value after we've been through here + allocate(this%dwt_frootc_to_litr_c_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)); this%dwt_frootc_to_litr_c_col (:,:,:)=nan allocate(this%dwt_livecrootc_to_cwdc_col (begc:endc,1:nlevdecomp_full)); this%dwt_livecrootc_to_cwdc_col (:,:)=nan allocate(this%dwt_deadcrootc_to_cwdc_col (begc:endc,1:nlevdecomp_full)); this%dwt_deadcrootc_to_cwdc_col (:,:)=nan @@ -792,7 +773,6 @@ subroutine InitHistory(this, bounds, carbon_type) ! add history fields for all CN variables, always set as default='inactive' ! ! !USES: - use clm_varpar , only : nlevdecomp, nlevdecomp_full, nlevgrnd use clm_varctl , only : hist_wrtch4diag use CNSharedParamsMod, only: use_fun use histFileMod, only : hist_addfld1d, hist_addfld2d, hist_addfld_decomp @@ -803,7 +783,8 @@ subroutine InitHistory(this, bounds, carbon_type) character(len=3) , intent(in) :: carbon_type ! one of ['c12', c13','c14'] ! ! !LOCAL VARIABLES: - integer :: k,l,ii,jj + integer :: k,l,ii,jj + character(1) :: k_str character(8) :: vr_suffix character(10) :: active integer :: begp,endp @@ -2914,20 +2895,16 @@ subroutine InitHistory(this, bounds, carbon_type) '(per-area-gridcell; only makes sense with dov2xy=.false.)', & ptr_patch=this%dwt_slash_cflux_patch, default='inactive') - this%dwt_frootc_to_litr_met_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTC_TO_LITR_MET_C', units='gC/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_met_c_col, default='inactive') - - this%dwt_frootc_to_litr_cel_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTC_TO_LITR_CEL_C', units='gC/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_cel_c_col, default='inactive') - - this%dwt_frootc_to_litr_lig_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTC_TO_LITR_LIG_C', units='gC/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_lig_c_col, default='inactive') + do k = i_litr_min, i_litr_max + write(k_str,'(I1)') k ! convert 1-digit integer to string + this%dwt_frootc_to_litr_c_col(begc:endc,:,k) = spval + data2dptr => this%dwt_frootc_to_litr_c_col(begc:endc,:,k) + fieldname = 'DWT_FROOTC_TO_LITR_'//k_str//'_C' + longname = 'fine root to litter_'//k_str//' due to landcover change' + call hist_addfld_decomp (fname=fieldname, units='gC/m^2/s', type2d='levdcmp', & + avgflag='A', long_name=longname, & + ptr_col=data2dptr, default='inactive') + end do this%dwt_livecrootc_to_cwdc_col(begc:endc,:) = spval call hist_addfld_decomp (fname='DWT_LIVECROOTC_TO_CWDC', units='gC/m^2/s', type2d='levdcmp', & @@ -3097,20 +3074,16 @@ subroutine InitHistory(this, bounds, carbon_type) '(per-area-gridcell; only makes sense with dov2xy=.false.)', & ptr_patch=this%dwt_slash_cflux_patch, default='inactive') - this%dwt_frootc_to_litr_met_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C13_DWT_FROOTC_TO_LITR_MET_C', units='gC13/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C13 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_met_c_col, default='inactive') - - this%dwt_frootc_to_litr_cel_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C13_DWT_FROOTC_TO_LITR_CEL_C', units='gC13/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C13 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_cel_c_col, default='inactive') - - this%dwt_frootc_to_litr_lig_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C13_DWT_FROOTC_TO_LITR_LIG_C', units='gC13/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C13 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_lig_c_col, default='inactive') + do k = i_litr_min, i_litr_max + write(k_str,'(I1)') k ! convert 1-digit integer to string + this%dwt_frootc_to_litr_c_col(begc:endc,:,k) = spval + data2dptr => this%dwt_frootc_to_litr_c_col(begc:endc,:,k) + fieldname = 'C13_DWT_FROOTC_TO_LITR_'//k_str//'_C' + longname = 'C13 fine root to litter_'//k_str//' due to landcover change' + call hist_addfld_decomp (fname=fieldname, units='gC/m^2/s', type2d='levdcmp', & + avgflag='A', long_name=longname, & + ptr_col=data2dptr, default='inactive') + end do this%dwt_livecrootc_to_cwdc_col(begc:endc,:) = spval call hist_addfld_decomp (fname='C13_DWT_LIVECROOTC_TO_CWDC', units='gC13/m^2/s', type2d='levdcmp', & @@ -3262,20 +3235,16 @@ subroutine InitHistory(this, bounds, carbon_type) '(per-area-gridcell; only makes sense with dov2xy=.false.)', & ptr_patch=this%dwt_slash_cflux_patch, default='inactive') - this%dwt_frootc_to_litr_met_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C14_DWT_FROOTC_TO_LITR_MET_C', units='gC14/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C14 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_met_c_col, default='inactive') - - this%dwt_frootc_to_litr_cel_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C14_DWT_FROOTC_TO_LITR_CEL_C', units='gC14/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C14 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_cel_c_col, default='inactive') - - this%dwt_frootc_to_litr_lig_c_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='C14_DWT_FROOTC_TO_LITR_LIG_C', units='gC14/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='C14 fine root to litter due to landcover change', & - ptr_col=this%dwt_frootc_to_litr_lig_c_col, default='inactive') + do k = i_litr_min, i_litr_max + write(k_str,'(I1)') k ! convert 1-digit integer to string + this%dwt_frootc_to_litr_c_col(begc:endc,:,k) = spval + data2dptr => this%dwt_frootc_to_litr_c_col(begc:endc,:,k) + fieldname = 'C14_DWT_FROOTC_TO_LITR_'//k_str//'_C' + longname = 'C14 fine root to litter_'//k_str//' due to landcover change' + call hist_addfld_decomp (fname=fieldname, units='gC/m^2/s', type2d='levdcmp', & + avgflag='A', long_name=longname, & + ptr_col=data2dptr, default='inactive') + end do this%dwt_livecrootc_to_cwdc_col(begc:endc,:) = spval call hist_addfld_decomp (fname='C14_DWT_LIVECROOTC_TO_CWDC', units='gC14/m^2/s', type2d='levdcmp', & @@ -3351,7 +3320,7 @@ subroutine InitCold(this, bounds) type(bounds_type), intent(in) :: bounds ! ! !LOCAL VARIABLES: - integer :: p, c, l, j + integer :: p, c, l, j, i integer :: fc ! filter index integer :: num_special_col ! number of good values in special_col filter integer :: num_special_patch ! number of good values in special_patch filter @@ -3416,9 +3385,9 @@ subroutine InitCold(this, bounds) ! real values on first timestep, prior to calling pftdyn_cnbal if (lun%itype(l) == istsoil .or. lun%itype(l) == istcrop) then do j = 1, nlevdecomp_full - this%dwt_frootc_to_litr_met_c_col(c,j) = 0._r8 - this%dwt_frootc_to_litr_cel_c_col(c,j) = 0._r8 - this%dwt_frootc_to_litr_lig_c_col(c,j) = 0._r8 + do i = i_litr_min, i_litr_max + this%dwt_frootc_to_litr_c_col(c,j,i) = 0._r8 + end do this%dwt_livecrootc_to_cwdc_col(c,j) = 0._r8 this%dwt_deadcrootc_to_cwdc_col(c,j) = 0._r8 end do @@ -3889,25 +3858,15 @@ subroutine SetValues ( this, & do fi = 1,num_column i = filter_column(fi) - this%phenology_c_to_litr_met_c_col(i,j) = value_column - this%phenology_c_to_litr_cel_c_col(i,j) = value_column - this%phenology_c_to_litr_lig_c_col(i,j) = value_column - - this%gap_mortality_c_to_litr_met_c_col(i,j) = value_column - this%gap_mortality_c_to_litr_cel_c_col(i,j) = value_column - this%gap_mortality_c_to_litr_lig_c_col(i,j) = value_column + do k = i_litr_min, i_litr_max + this%phenology_c_to_litr_c_col(i,j,k) = value_column + this%gap_mortality_c_to_litr_c_col(i,j,k) = value_column + this%harvest_c_to_litr_c_col(i,j,k) = value_column + this%m_c_to_litr_fire_col(i,j,k) = value_column + end do this%gap_mortality_c_to_cwdc_col(i,j) = value_column - this%fire_mortality_c_to_cwdc_col(i,j) = value_column - this%m_c_to_litr_met_fire_col(i,j) = value_column - this%m_c_to_litr_cel_fire_col(i,j) = value_column - this%m_c_to_litr_lig_fire_col(i,j) = value_column - - this%harvest_c_to_litr_met_c_col(i,j) = value_column - this%harvest_c_to_litr_cel_c_col(i,j) = value_column - this%harvest_c_to_litr_lig_c_col(i,j) = value_column this%harvest_c_to_cwdc_col(i,j) = value_column - end do end do @@ -4012,7 +3971,7 @@ subroutine ZeroDwt( this, bounds ) type(bounds_type), intent(in) :: bounds ! ! !LOCAL VARIABLES: - integer :: c, g, j ! indices + integer :: c, g, j, i ! indices !----------------------------------------------------------------------- ! set conversion and product pool fluxes to 0 at the beginning of every timestep @@ -4026,9 +3985,9 @@ subroutine ZeroDwt( this, bounds ) do j = 1, nlevdecomp_full do c = bounds%begc,bounds%endc - this%dwt_frootc_to_litr_met_c_col(c,j) = 0._r8 - this%dwt_frootc_to_litr_cel_c_col(c,j) = 0._r8 - this%dwt_frootc_to_litr_lig_c_col(c,j) = 0._r8 + do i = i_litr_min, i_litr_max + this%dwt_frootc_to_litr_c_col(c,j,i) = 0._r8 + end do this%dwt_livecrootc_to_cwdc_col(c,j) = 0._r8 this%dwt_deadcrootc_to_cwdc_col(c,j) = 0._r8 end do diff --git a/src/biogeochem/CNVegNitrogenFluxType.F90 b/src/biogeochem/CNVegNitrogenFluxType.F90 index 1da724382b..68952b5048 100644 --- a/src/biogeochem/CNVegNitrogenFluxType.F90 +++ b/src/biogeochem/CNVegNitrogenFluxType.F90 @@ -4,7 +4,7 @@ module CNVegNitrogenFluxType use shr_infnan_mod , only : nan => shr_infnan_nan, assignment(=) use shr_log_mod , only : errMsg => shr_log_errMsg use clm_varpar , only : ndecomp_cascade_transitions, ndecomp_pools - use clm_varpar , only : nlevdecomp_full, nlevdecomp + use clm_varpar , only : nlevdecomp_full, nlevdecomp, i_litr_min, i_litr_max use clm_varcon , only : spval, ispval, dzsoi_decomp use clm_varctl , only : use_nitrif_denitrif, use_vertsoilc, use_crop use CNSharedParamsMod , only : use_fun @@ -63,12 +63,8 @@ module CNVegNitrogenFluxType real(r8), pointer :: hrv_retransn_to_litter_patch (:) ! patch retranslocated N pool harvest mortality (gN/m2/s) real(r8), pointer :: grainn_to_cropprodn_patch (:) ! patch grain N to crop product pool (gN/m2/s) real(r8), pointer :: grainn_to_cropprodn_col (:) ! col grain N to crop product pool (gN/m2/s) - real(r8), pointer :: m_n_to_litr_met_fire_col (:,:) ! col N from leaf, froot, xfer and storage N to litter labile N by fire (gN/m3/s) - real(r8), pointer :: m_n_to_litr_cel_fire_col (:,:) ! col N from leaf, froot, xfer and storage N to litter cellulose N by fire (gN/m3/s) - real(r8), pointer :: m_n_to_litr_lig_fire_col (:,:) ! col N from leaf, froot, xfer and storage N to litter lignin N by fire (gN/m3/s) - real(r8), pointer :: harvest_n_to_litr_met_n_col (:,:) ! col N fluxes associated with harvest to litter metabolic pool (gN/m3/s) - real(r8), pointer :: harvest_n_to_litr_cel_n_col (:,:) ! col N fluxes associated with harvest to litter cellulose pool (gN/m3/s) - real(r8), pointer :: harvest_n_to_litr_lig_n_col (:,:) ! col N fluxes associated with harvest to litter lignin pool (gN/m3/s) + real(r8), pointer :: m_n_to_litr_fire_col (:,:,:) ! col N from leaf, froot, xfer and storage N to litter N by fire (gN/m3/s) + real(r8), pointer :: harvest_n_to_litr_n_col (:,:,:) ! col N fluxes associated with harvest to litter pools (gN/m3/s) real(r8), pointer :: harvest_n_to_cwdn_col (:,:) ! col N fluxes associated with harvest to CWD pool (gN/m3/s) ! fire N fluxes @@ -181,14 +177,10 @@ module CNVegNitrogenFluxType real(r8), pointer :: wood_harvestn_patch (:) ! patch total N losses to wood product pools (gN/m2/s) real(r8), pointer :: wood_harvestn_col (:) ! col total N losses to wood product pools (gN/m2/s) (p2c) ! phenology: litterfall and crop fluxes - real(r8), pointer :: phenology_n_to_litr_met_n_col (:,:) ! col N fluxes associated with phenology (litterfall and crop) to litter metabolic pool (gN/m3/s) - real(r8), pointer :: phenology_n_to_litr_cel_n_col (:,:) ! col N fluxes associated with phenology (litterfall and crop) to litter cellulose pool (gN/m3/s) - real(r8), pointer :: phenology_n_to_litr_lig_n_col (:,:) ! col N fluxes associated with phenology (litterfall and crop) to litter lignin pool (gN/m3/s) + real(r8), pointer :: phenology_n_to_litr_n_col (:,:,:) ! col N fluxes associated with phenology (litterfall and crop) to litter pools (gN/m3/s) ! gap mortality fluxes - real(r8), pointer :: gap_mortality_n_to_litr_met_n_col (:,:) ! col N fluxes associated with gap mortality to litter metabolic pool (gN/m3/s) - real(r8), pointer :: gap_mortality_n_to_litr_cel_n_col (:,:) ! col N fluxes associated with gap mortality to litter cellulose pool (gN/m3/s) - real(r8), pointer :: gap_mortality_n_to_litr_lig_n_col (:,:) ! col N fluxes associated with gap mortality to litter lignin pool (gN/m3/s) + real(r8), pointer :: gap_mortality_n_to_litr_n_col (:,:,:) ! col N fluxes associated with gap mortality to litter pools (gN/m3/s) real(r8), pointer :: gap_mortality_n_to_cwdn_col (:,:) ! col N fluxes associated with gap mortality to CWD pool (gN/m3/s) ! dynamic landcover fluxes @@ -200,9 +192,7 @@ module CNVegNitrogenFluxType real(r8), pointer :: dwt_conv_nflux_grc (:) ! (gN/m2/s) dwt_conv_nflux_patch summed to the gridcell-level real(r8), pointer :: dwt_wood_productn_gain_patch (:) ! patch (gN/m2/s) addition to wood product pools from landcover change; even though this is a patch-level flux, it is expressed per unit GRIDCELL area real(r8), pointer :: dwt_crop_productn_gain_patch (:) ! patch (gN/m2/s) addition to crop product pool from landcover change; even though this is a patch-level flux, it is expressed per unit GRIDCELL area - real(r8), pointer :: dwt_frootn_to_litr_met_n_col (:,:) ! col (gN/m3/s) fine root to litter due to landcover change - real(r8), pointer :: dwt_frootn_to_litr_cel_n_col (:,:) ! col (gN/m3/s) fine root to litter due to landcover change - real(r8), pointer :: dwt_frootn_to_litr_lig_n_col (:,:) ! col (gN/m3/s) fine root to litter due to landcover change + real(r8), pointer :: dwt_frootn_to_litr_n_col (:,:,:) ! col (gN/m3/s) fine root to litter due to landcover change real(r8), pointer :: dwt_livecrootn_to_cwdn_col (:,:) ! col (gN/m3/s) live coarse root to CWD due to landcover change real(r8), pointer :: dwt_deadcrootn_to_cwdn_col (:,:) ! col (gN/m3/s) dead coarse root to CWD due to landcover change @@ -430,9 +420,7 @@ subroutine InitAllocate(this, bounds) allocate(this%fire_nloss_col (begc:endc)) ; this%fire_nloss_col (:) = nan allocate(this%fire_nloss_p2c_col (begc:endc)) ; this%fire_nloss_p2c_col (:) = nan - allocate(this%m_n_to_litr_met_fire_col (begc:endc,1:nlevdecomp_full)) ; this%m_n_to_litr_met_fire_col (:,:) = nan - allocate(this%m_n_to_litr_cel_fire_col (begc:endc,1:nlevdecomp_full)) ; this%m_n_to_litr_cel_fire_col (:,:) = nan - allocate(this%m_n_to_litr_lig_fire_col (begc:endc,1:nlevdecomp_full)) ; this%m_n_to_litr_lig_fire_col (:,:) = nan + allocate(this%m_n_to_litr_fire_col (begc:endc,1:nlevdecomp_full,1:ndecomp_pools)) ; this%m_n_to_litr_fire_col (:,:,:) = nan allocate(this%dwt_seedn_to_leaf_patch (begp:endp)) ; this%dwt_seedn_to_leaf_patch (:) = nan allocate(this%dwt_seedn_to_leaf_grc (begg:endg)) ; this%dwt_seedn_to_leaf_grc (:) = nan @@ -444,9 +432,7 @@ subroutine InitAllocate(this, bounds) allocate(this%dwt_crop_productn_gain_patch (begp:endp)) ; this%dwt_crop_productn_gain_patch (:) = nan allocate(this%wood_harvestn_col (begc:endc)) ; this%wood_harvestn_col (:) = nan - allocate(this%dwt_frootn_to_litr_met_n_col (begc:endc,1:nlevdecomp_full)) ; this%dwt_frootn_to_litr_met_n_col (:,:) = nan - allocate(this%dwt_frootn_to_litr_cel_n_col (begc:endc,1:nlevdecomp_full)) ; this%dwt_frootn_to_litr_cel_n_col (:,:) = nan - allocate(this%dwt_frootn_to_litr_lig_n_col (begc:endc,1:nlevdecomp_full)) ; this%dwt_frootn_to_litr_lig_n_col (:,:) = nan + allocate(this%dwt_frootn_to_litr_n_col (begc:endc,1:nlevdecomp_full,1:i_litr_max)) ; this%dwt_frootn_to_litr_n_col (:,:,:) = nan allocate(this%dwt_livecrootn_to_cwdn_col (begc:endc,1:nlevdecomp_full)) ; this%dwt_livecrootn_to_cwdn_col (:,:) = nan allocate(this%dwt_deadcrootn_to_cwdn_col (begc:endc,1:nlevdecomp_full)) ; this%dwt_deadcrootn_to_cwdn_col (:,:) = nan @@ -458,30 +444,18 @@ subroutine InitAllocate(this, bounds) this%m_decomp_npools_to_fire_vr_col (:,:,:) = nan this%m_decomp_npools_to_fire_col (:,:) = nan - allocate(this%phenology_n_to_litr_met_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%phenology_n_to_litr_cel_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%phenology_n_to_litr_lig_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%gap_mortality_n_to_litr_met_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%gap_mortality_n_to_litr_cel_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%gap_mortality_n_to_litr_lig_n_col (begc:endc, 1:nlevdecomp_full)) + allocate(this%phenology_n_to_litr_n_col (begc:endc, 1:nlevdecomp_full, 1:ndecomp_pools)) + allocate(this%gap_mortality_n_to_litr_n_col (begc:endc, 1:nlevdecomp_full, 1:ndecomp_pools)) allocate(this%gap_mortality_n_to_cwdn_col (begc:endc, 1:nlevdecomp_full)) allocate(this%fire_mortality_n_to_cwdn_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%harvest_n_to_litr_met_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%harvest_n_to_litr_cel_n_col (begc:endc, 1:nlevdecomp_full)) - allocate(this%harvest_n_to_litr_lig_n_col (begc:endc, 1:nlevdecomp_full)) + allocate(this%harvest_n_to_litr_n_col (begc:endc, 1:nlevdecomp_full, 1:ndecomp_pools)) allocate(this%harvest_n_to_cwdn_col (begc:endc, 1:nlevdecomp_full)) - this%phenology_n_to_litr_met_n_col (:,:) = nan - this%phenology_n_to_litr_cel_n_col (:,:) = nan - this%phenology_n_to_litr_lig_n_col (:,:) = nan - this%gap_mortality_n_to_litr_met_n_col (:,:) = nan - this%gap_mortality_n_to_litr_cel_n_col (:,:) = nan - this%gap_mortality_n_to_litr_lig_n_col (:,:) = nan + this%phenology_n_to_litr_n_col (:,:,:) = nan + this%gap_mortality_n_to_litr_n_col (:,:,:) = nan this%gap_mortality_n_to_cwdn_col (:,:) = nan this%fire_mortality_n_to_cwdn_col (:,:) = nan - this%harvest_n_to_litr_met_n_col (:,:) = nan - this%harvest_n_to_litr_cel_n_col (:,:) = nan - this%harvest_n_to_litr_lig_n_col (:,:) = nan + this%harvest_n_to_litr_n_col (:,:,:) = nan this%harvest_n_to_cwdn_col (:,:) = nan allocate(this%plant_ndemand_patch (begp:endp)) ; this%plant_ndemand_patch (:) = nan @@ -544,6 +518,7 @@ subroutine InitHistory(this, bounds) integer :: begp, endp integer :: begc, endc integer :: begg, endg + character(1) :: k_str character(10) :: active character(24) :: fieldname character(100) :: longname @@ -1037,20 +1012,16 @@ subroutine InitHistory(this, bounds) '(per-area-gridcell; only makes sense with dov2xy=.false.)', & ptr_patch=this%dwt_conv_nflux_patch, default='inactive') - this%dwt_frootn_to_litr_met_n_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTN_TO_LITR_MET_N', units='gN/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootn_to_litr_met_n_col, default='inactive') - - this%dwt_frootn_to_litr_cel_n_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTN_TO_LITR_CEL_N', units='gN/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootn_to_litr_cel_n_col, default='inactive') - - this%dwt_frootn_to_litr_lig_n_col(begc:endc,:) = spval - call hist_addfld_decomp (fname='DWT_FROOTN_TO_LITR_LIG_N', units='gN/m^2/s', type2d='levdcmp', & - avgflag='A', long_name='fine root to litter due to landcover change', & - ptr_col=this%dwt_frootn_to_litr_lig_n_col, default='inactive') + do k = i_litr_min, i_litr_max + write(k_str,'(I1)') k ! convert 1-digit integer to string + this%dwt_frootn_to_litr_n_col(begc:endc,:,k) = spval + data2dptr => this%dwt_frootn_to_litr_n_col(begc:endc,:,k) + fieldname = 'DWT_FROOTN_TO_LITR_'//k_str//'_N' + longname = 'fine root N to litter_'//k_str//' due to landcover change' + call hist_addfld_decomp (fname=fieldname, units='gN/m^2/s', type2d='levdcmp', & + avgflag='A', long_name=longname, & + ptr_col=data2dptr, default='inactive') + end do this%dwt_livecrootn_to_cwdn_col(begc:endc,:) = spval call hist_addfld_decomp (fname='DWT_LIVECROOTN_TO_CWDN', units='gN/m^2/s', type2d='levdcmp', & @@ -1699,27 +1670,15 @@ subroutine SetValues ( this, & do fi = 1,num_column i = filter_column(fi) - ! phenology: litterfall and crop fluxes associated wit - this%phenology_n_to_litr_met_n_col(i,j) = value_column - this%phenology_n_to_litr_cel_n_col(i,j) = value_column - this%phenology_n_to_litr_lig_n_col(i,j) = value_column + do k = i_litr_min, i_litr_max + this%phenology_n_to_litr_n_col(i,j,k) = value_column + this%gap_mortality_n_to_litr_n_col(i,j,k) = value_column + this%harvest_n_to_litr_n_col(i,j,k) = value_column + this%m_n_to_litr_fire_col(i,j,k) = value_column + end do - ! gap mortality - this%gap_mortality_n_to_litr_met_n_col(i,j) = value_column - this%gap_mortality_n_to_litr_cel_n_col(i,j) = value_column - this%gap_mortality_n_to_litr_lig_n_col(i,j) = value_column this%gap_mortality_n_to_cwdn_col(i,j) = value_column - - ! fire this%fire_mortality_n_to_cwdn_col(i,j) = value_column - this%m_n_to_litr_met_fire_col(i,j) = value_column - this%m_n_to_litr_cel_fire_col(i,j) = value_column - this%m_n_to_litr_lig_fire_col(i,j) = value_column - - ! harvest - this%harvest_n_to_litr_met_n_col(i,j) = value_column - this%harvest_n_to_litr_cel_n_col(i,j) = value_column - this%harvest_n_to_litr_lig_n_col(i,j) = value_column this%harvest_n_to_cwdn_col(i,j) = value_column end do end do @@ -1764,7 +1723,7 @@ subroutine ZeroDwt( this, bounds ) type(bounds_type), intent(in) :: bounds ! ! !LOCAL VARIABLES: - integer :: c, g, j ! indices + integer :: c, g, j, i ! indices !----------------------------------------------------------------------- do g = bounds%begg, bounds%endg @@ -1775,9 +1734,9 @@ subroutine ZeroDwt( this, bounds ) do j = 1, nlevdecomp_full do c = bounds%begc,bounds%endc - this%dwt_frootn_to_litr_met_n_col(c,j) = 0._r8 - this%dwt_frootn_to_litr_cel_n_col(c,j) = 0._r8 - this%dwt_frootn_to_litr_lig_n_col(c,j) = 0._r8 + do i = i_litr_min, i_litr_max + this%dwt_frootn_to_litr_n_col(c,j,i) = 0._r8 + end do this%dwt_livecrootn_to_cwdn_col(c,j) = 0._r8 this%dwt_deadcrootn_to_cwdn_col(c,j) = 0._r8 end do diff --git a/src/biogeochem/dynConsBiogeochemMod.F90 b/src/biogeochem/dynConsBiogeochemMod.F90 index 32cd2b9577..f8cff29911 100644 --- a/src/biogeochem/dynConsBiogeochemMod.F90 +++ b/src/biogeochem/dynConsBiogeochemMod.F90 @@ -58,7 +58,7 @@ subroutine dyn_cnbal_patch(bounds, & ! !USES: use shr_const_mod , only : SHR_CONST_PDB use landunit_varcon , only : istsoil, istcrop - use clm_varpar , only : nlevdecomp + use clm_varpar , only : nlevdecomp, i_litr_min, i_litr_max use clm_varcon , only : c13ratio, c14ratio, c3_r2, c4_r2 use clm_time_manager , only : get_step_size_real use dynPriorWeightsMod , only : prior_weights_type @@ -85,7 +85,7 @@ subroutine dyn_cnbal_patch(bounds, & type(soilbiogeochem_state_type) , intent(in) :: soilbiogeochem_state_inst ! ! !LOCAL VARIABLES: - integer :: p,c,l,g,j ! indices + integer :: p,c,l,g,j,i ! indices integer :: begp, endp integer :: ier ! error code real(r8) :: dt ! land model time step (sec) @@ -593,36 +593,20 @@ subroutine dyn_cnbal_patch(bounds, & c = patch%column(p) ! fine root litter carbon fluxes - cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) = & - cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) + & - (dwt_frootc_to_litter(p)*pftcon%fr_flab(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) = & - cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) + & - (dwt_frootc_to_litter(p)*pftcon%fr_fcel(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) = & - cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) + & - (dwt_frootc_to_litter(p)*pftcon%fr_flig(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - + do i = i_litr_min, i_litr_max + cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) = & + cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) + & + (dwt_frootc_to_litter(p)*pftcon%fr_f(patch%itype(p),i)) / dt & + * soilbiogeochem_state_inst%froot_prof_patch(p,j) + end do ! fine root litter nitrogen fluxes - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_met_n_col(c,j) = & - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_met_n_col(c,j) + & - (dwt_frootn_to_litter(p)*pftcon%fr_flab(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_cel_n_col(c,j) = & - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_cel_n_col(c,j) + & - (dwt_frootn_to_litter(p)*pftcon%fr_fcel(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_lig_n_col(c,j) = & - cnveg_nitrogenflux_inst%dwt_frootn_to_litr_lig_n_col(c,j) + & - (dwt_frootn_to_litter(p)*pftcon%fr_flig(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) + do i = i_litr_min, i_litr_max + cnveg_nitrogenflux_inst%dwt_frootn_to_litr_n_col(c,j,i) = & + cnveg_nitrogenflux_inst%dwt_frootn_to_litr_n_col(c,j,i) + & + (dwt_frootn_to_litter(p) * pftcon%fr_f(patch%itype(p),i)) / dt & + * soilbiogeochem_state_inst%froot_prof_patch(p,j) + end do ! livecroot fluxes to cwd cnveg_carbonflux_inst%dwt_livecrootc_to_cwdc_col(c,j) = & @@ -644,20 +628,12 @@ subroutine dyn_cnbal_patch(bounds, & if ( use_c13 ) then ! C13 fine root litter fluxes - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) = & - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) + & - (dwt_frootc13_to_litter(p)*pftcon%fr_flab(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) = & - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) + & - (dwt_frootc13_to_litter(p)*pftcon%fr_fcel(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) = & - c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) + & - (dwt_frootc13_to_litter(p)*pftcon%fr_flig(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) + do i = i_litr_min, i_litr_max + c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) = & + c13_cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) + & + (dwt_frootc13_to_litter(p)*pftcon%fr_f(patch%itype(p),i)) / dt & + * soilbiogeochem_state_inst%froot_prof_patch(p,j) + end do ! livecroot fluxes to cwd c13_cnveg_carbonflux_inst%dwt_livecrootc_to_cwdc_col(c,j) = & @@ -673,20 +649,12 @@ subroutine dyn_cnbal_patch(bounds, & if ( use_c14 ) then ! C14 fine root litter fluxes - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) = & - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_met_c_col(c,j) + & - (dwt_frootc14_to_litter(p)*pftcon%fr_flab(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) = & - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_cel_c_col(c,j) + & - (dwt_frootc14_to_litter(p)*pftcon%fr_fcel(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) - - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) = & - c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_lig_c_col(c,j) + & - (dwt_frootc14_to_litter(p)*pftcon%fr_flig(patch%itype(p)))/dt & - * soilbiogeochem_state_inst%froot_prof_patch(p,j) + do i = i_litr_min, i_litr_max + c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) = & + c14_cnveg_carbonflux_inst%dwt_frootc_to_litr_c_col(c,j,i) + & + (dwt_frootc14_to_litter(p)*pftcon%fr_f(patch%itype(p),i)) / dt & + * soilbiogeochem_state_inst%froot_prof_patch(p,j) + end do ! livecroot fluxes to cwd c14_cnveg_carbonflux_inst%dwt_livecrootc_to_cwdc_col(c,j) = & diff --git a/src/dyn_subgrid/dynHarvestMod.F90 b/src/dyn_subgrid/dynHarvestMod.F90 index db5b0d25e1..c16c15906c 100644 --- a/src/dyn_subgrid/dynHarvestMod.F90 +++ b/src/dyn_subgrid/dynHarvestMod.F90 @@ -467,7 +467,7 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & ! to the column level and assign them to the three litter pools ! ! !USES: - use clm_varpar , only : nlevdecomp, maxsoil_patches + use clm_varpar , only : nlevdecomp, maxsoil_patches, i_litr_min, i_litr_max, i_met_lit ! ! !ARGUMENTS: integer , intent(in) :: num_soilc ! number of soil columns in filter @@ -477,19 +477,15 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & type(cnveg_nitrogenflux_type) , intent(inout) :: cnveg_nitrogenflux_inst ! ! !LOCAL VARIABLES: - integer :: fc,c,pi,p,j ! indices + integer :: fc,c,pi,p,j,i ! indices !----------------------------------------------------------------------- associate( & ivt => patch%itype , & ! Input: [integer (:) ] pft vegetation type wtcol => patch%wtcol , & ! Input: [real(r8) (:) ] pft weight relative to column (0-1) - lf_flab => pftcon%lf_flab , & ! Input: leaf litter labile fraction - lf_fcel => pftcon%lf_fcel , & ! Input: leaf litter cellulose fraction - lf_flig => pftcon%lf_flig , & ! Input: leaf litter lignin fraction - fr_flab => pftcon%fr_flab , & ! Input: fine root litter labile fraction - fr_fcel => pftcon%fr_fcel , & ! Input: fine root litter cellulose fraction - fr_flig => pftcon%fr_flig , & ! Input: fine root litter lignin fraction + lf_f => pftcon%lf_f , & ! Input: leaf litter fraction + fr_f => pftcon%fr_f , & ! Input: fine root litter fraction leaf_prof => soilbiogeochem_state_inst%leaf_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of leaves froot_prof => soilbiogeochem_state_inst%froot_prof_patch , & ! Input: [real(r8) (:,:) ] (1/m) profile of fine roots @@ -517,9 +513,7 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & hrv_deadcrootc_xfer_to_litter => cnveg_carbonflux_inst%hrv_deadcrootc_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] hrv_gresp_xfer_to_litter => cnveg_carbonflux_inst%hrv_gresp_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] cwood_harvestc => cnveg_carbonflux_inst%wood_harvestc_col , & ! InOut: [real(r8) (:) ] - harvest_c_to_litr_met_c => cnveg_carbonflux_inst%harvest_c_to_litr_met_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with harvest to litter metabolic pool (gC/m3/s) - harvest_c_to_litr_cel_c => cnveg_carbonflux_inst%harvest_c_to_litr_cel_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with harvest to litter cellulose pool (gC/m3/s) - harvest_c_to_litr_lig_c => cnveg_carbonflux_inst%harvest_c_to_litr_lig_c_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with harvest to litter lignin pool (gC/m3/s) + harvest_c_to_litr_c => cnveg_carbonflux_inst%harvest_c_to_litr_c_col , & ! InOut: [real(r8) (:,:,:) ] C fluxes associated with harvest to litter pools (gC/m3/s) harvest_c_to_cwdc => cnveg_carbonflux_inst%harvest_c_to_cwdc_col , & ! InOut: [real(r8) (:,:) ] C fluxes associated with harvest to CWD pool (gC/m3/s) hrv_leafn_to_litter => cnveg_nitrogenflux_inst%hrv_leafn_to_litter_patch , & ! Input: [real(r8) (:) ] @@ -542,9 +536,7 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & hrv_livecrootn_xfer_to_litter => cnveg_nitrogenflux_inst%hrv_livecrootn_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] hrv_deadcrootn_xfer_to_litter => cnveg_nitrogenflux_inst%hrv_deadcrootn_xfer_to_litter_patch , & ! Input: [real(r8) (:) ] cwood_harvestn => cnveg_nitrogenflux_inst%wood_harvestn_col , & ! InOut: [real(r8) (:) ] - harvest_n_to_litr_met_n => cnveg_nitrogenflux_inst%harvest_n_to_litr_met_n_col , & ! InOut: [real(r8) (:,:) ] N fluxes associated with harvest to litter metabolic pool (gN/m3/s) - harvest_n_to_litr_cel_n => cnveg_nitrogenflux_inst%harvest_n_to_litr_cel_n_col , & ! InOut: [real(r8) (:,:) ] N fluxes associated with harvest to litter cellulose pool (gN/m3/s) - harvest_n_to_litr_lig_n => cnveg_nitrogenflux_inst%harvest_n_to_litr_lig_n_col , & ! InOut: [real(r8) (:,:) ] N fluxes associated with harvest to litter lignin pool (gN/m3/s) + harvest_n_to_litr_n => cnveg_nitrogenflux_inst%harvest_n_to_litr_n_col , & ! InOut: [real(r8) (:,:,:)] N fluxes associated with harvest to litter pools (gN/m3/s) harvest_n_to_cwdn => cnveg_nitrogenflux_inst%harvest_n_to_cwdn_col & ! InOut: [real(r8) (:,:) ] N fluxes associated with harvest to CWD pool (gN/m3/s) ) @@ -558,21 +550,17 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & if (patch%active(p)) then - ! leaf harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_cel_c(c,j) = harvest_c_to_litr_cel_c(c,j) + & - hrv_leafc_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_lig_c(c,j) = harvest_c_to_litr_lig_c(c,j) + & - hrv_leafc_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_cel_c(c,j) = harvest_c_to_litr_cel_c(c,j) + & - hrv_frootc_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_lig_c(c,j) = harvest_c_to_litr_lig_c(c,j) + & - hrv_frootc_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + do i = i_litr_min, i_litr_max + ! leaf harvest mortality carbon fluxes + harvest_c_to_litr_c(c,j,i) = & + harvest_c_to_litr_c(c,j,i) + & + hrv_leafc_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + + ! fine root harvest mortality carbon fluxes + harvest_c_to_litr_c(c,j,i) = & + harvest_c_to_litr_c(c,j,i) + & + hrv_frootc_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood harvest mortality carbon fluxes harvest_c_to_cwdc(c,j) = harvest_c_to_cwdc(c,j) + & @@ -583,52 +571,36 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & hrv_deadcrootc_to_litter(p) * wtcol(p) * croot_prof(p,j) ! storage harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + harvest_c_to_litr_c(c,j,i_met_lit) = & + harvest_c_to_litr_c(c,j,i_met_lit) + & + hrv_leafc_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootc_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemc_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootc_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_gresp_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & ! transfer harvest mortality carbon fluxes - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_c_to_litr_met_c(c,j) = harvest_c_to_litr_met_c(c,j) + & - hrv_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - - ! leaf harvest mortality nitrogen fluxes - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_leafn_to_litter(p) * lf_flab(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_n_to_litr_cel_n(c,j) = harvest_n_to_litr_cel_n(c,j) + & - hrv_leafn_to_litter(p) * lf_fcel(ivt(p)) * wtcol(p) * leaf_prof(p,j) - harvest_n_to_litr_lig_n(c,j) = harvest_n_to_litr_lig_n(c,j) + & - hrv_leafn_to_litter(p) * lf_flig(ivt(p)) * wtcol(p) * leaf_prof(p,j) - - ! fine root litter nitrogen fluxes - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_frootn_to_litter(p) * fr_flab(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_n_to_litr_cel_n(c,j) = harvest_n_to_litr_cel_n(c,j) + & - hrv_frootn_to_litter(p) * fr_fcel(ivt(p)) * wtcol(p) * froot_prof(p,j) - harvest_n_to_litr_lig_n(c,j) = harvest_n_to_litr_lig_n(c,j) + & - hrv_frootn_to_litter(p) * fr_flig(ivt(p)) * wtcol(p) * froot_prof(p,j) + hrv_leafc_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootc_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemc_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootc_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_gresp_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + + do i = i_litr_min, i_litr_max + harvest_n_to_litr_n(c,j,i) = & + harvest_n_to_litr_n(c,j,i) + & + ! leaf harvest mortality nitrogen fluxes + hrv_leafn_to_litter(p) * lf_f(ivt(p),i) * wtcol(p) * leaf_prof(p,j) + & + ! fine root litter nitrogen fluxes + hrv_frootn_to_litter(p) * fr_f(ivt(p),i) * wtcol(p) * froot_prof(p,j) + end do ! wood harvest mortality nitrogen fluxes harvest_n_to_cwdn(c,j) = harvest_n_to_cwdn(c,j) + & @@ -638,37 +610,27 @@ subroutine CNHarvestPftToColumn (num_soilc, filter_soilc, & harvest_n_to_cwdn(c,j) = harvest_n_to_cwdn(c,j) + & hrv_deadcrootn_to_litter(p) * wtcol(p) * croot_prof(p,j) - ! retranslocated N pool harvest mortality fluxes - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_retransn_to_litter(p) * wtcol(p) * leaf_prof(p,j) - - ! storage harvest mortality nitrogen fluxes - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_leafn_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_frootn_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_livestemn_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_deadstemn_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_livecrootn_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_deadcrootn_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) - - ! transfer harvest mortality nitrogen fluxes - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_leafn_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_frootn_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_livestemn_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_deadstemn_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_livecrootn_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) - harvest_n_to_litr_met_n(c,j) = harvest_n_to_litr_met_n(c,j) + & - hrv_deadcrootn_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + ! Metabolic litter is treated differently than other types + ! of litter, so it gets this additional line after the + ! most recent loop over all litter types + harvest_n_to_litr_n(c,j,i_met_lit) = & + harvest_n_to_litr_n(c,j,i_met_lit) + & + ! retranslocated N pool harvest mortality fluxes + hrv_retransn_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + ! storage harvest mortality nitrogen fluxes + hrv_leafn_storage_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootn_storage_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemn_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemn_storage_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootn_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootn_storage_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + ! transfer harvest mortality nitrogen fluxes + hrv_leafn_xfer_to_litter(p) * wtcol(p) * leaf_prof(p,j) + & + hrv_frootn_xfer_to_litter(p) * wtcol(p) * froot_prof(p,j) + & + hrv_livestemn_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_deadstemn_xfer_to_litter(p) * wtcol(p) * stem_prof(p,j) + & + hrv_livecrootn_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) + & + hrv_deadcrootn_xfer_to_litter(p) * wtcol(p) * croot_prof(p,j) end if end if diff --git a/src/main/clm_varpar.F90 b/src/main/clm_varpar.F90 index 7594a2bf13..5a18d52d0e 100644 --- a/src/main/clm_varpar.F90 +++ b/src/main/clm_varpar.F90 @@ -63,11 +63,17 @@ module clm_varpar ! constants for decomposition cascade - integer, public, parameter :: i_met_lit = 1 - integer, public, parameter :: i_cel_lit = i_met_lit + 1 - integer, public, parameter :: i_lig_lit = i_cel_lit + 1 - integer, public :: i_cwd + integer, public, parameter :: i_litr1 = 1 ! TEMPORARY FOR CascadeCN TO BUILD + integer, public :: i_litr2 = -9 ! TEMPORARY FOR CascadeCN TO BUILD + integer, public :: i_litr3 = -9 ! TEMPORARY FOR CascadeCN TO BUILD + ! The code currently expects i_litr_min = i_met_lit = 1 and + ! i_litr_max = 2 or 3 + integer, public :: i_litr_min = -9 ! min index of litter pools; overwritten in SoilBiogeochemDecompCascade*Mod + integer, public :: i_litr_max = -9 ! max index of litter pools; overwritten in SoilBiogeochemDecompCascade*Mod + integer, public :: i_met_lit = -9 ! index of metabolic litter pool; overwritten in SoilBiogeochemDecompCascade*Mod + integer, public :: i_cwd = -9 ! index of cwd pool; overwritten in SoilBiogeochemDecompCascade*Mod + integer, public :: ndecomp_pools_max integer, public :: ndecomp_pools integer, public :: ndecomp_cascade_transitions @@ -227,25 +233,33 @@ subroutine clm_varpar_init(actual_maxsoil_patches, actual_numcft) write(iulog, *) end if + ! We hardwire these parameters here because we use them + ! in InitAllocate (in SoilBiogeochemStateType) which is called earlier than + ! init_decompcascade_bgc where they might have otherwise been derived on the + ! fly. For reference, if they were determined in init_decompcascade_bgc: + ! ndecomp_pools would get the value of i_avl_som or i_cwd and + ! ndecomp_cascade_transitions would get the value of i_s3s1 or i_cwdl3 + ! depending on how use_fates is set. if ( use_fates ) then - i_cwd = 0 if (use_century_decomp) then ndecomp_pools = 6 ndecomp_cascade_transitions = 8 - else + else ! TODO slevis: Currently for CN. MIMICS will get its own. ndecomp_pools = 7 ndecomp_cascade_transitions = 7 end if else - i_cwd = 4 if (use_century_decomp) then ndecomp_pools = 7 ndecomp_cascade_transitions = 10 - else + else ! TODO slevis: Currently for CN. MIMICS will get its own. ndecomp_pools = 8 ndecomp_cascade_transitions = 9 end if endif + ! The next param also appears as a dimension in the params files dated + ! c210418.nc and later + ndecomp_pools_max = 8 ! largest ndecomp_pools value above end subroutine clm_varpar_init diff --git a/src/main/controlMod.F90 b/src/main/controlMod.F90 index 98363867a3..a5dd42d89c 100644 --- a/src/main/controlMod.F90 +++ b/src/main/controlMod.F90 @@ -119,7 +119,6 @@ subroutine control_init(dtime) use CNMRespMod , only : CNMRespReadNML use LunaMod , only : LunaReadNML use CNNDynamicsMod , only : CNNDynamicsReadNML - use SoilBiogeochemDecompCascadeBGCMod, only : DecompCascadeBGCreadNML use CNPhenologyMod , only : CNPhenologyReadNML use landunit_varcon , only : max_lunit ! @@ -532,9 +531,6 @@ subroutine control_init(dtime) call CNNDynamicsReadNML ( NLFilename ) call CNPhenologyReadNML ( NLFilename ) end if - if ( use_century_decomp ) then - call DecompCascadeBGCreadNML( NLFilename ) - end if ! ---------------------------------------------------------------------- ! consistency checks diff --git a/src/main/pftconMod.F90 b/src/main/pftconMod.F90 index 3645a6f63a..27c6375344 100644 --- a/src/main/pftconMod.F90 +++ b/src/main/pftconMod.F90 @@ -8,7 +8,7 @@ module pftconMod ! !USES: use shr_kind_mod, only : r8 => shr_kind_r8 use abortutils , only : endrun - use clm_varpar , only : mxpft, numrad, ivis, inir, cft_lb, cft_ub + use clm_varpar , only : mxpft, numrad, ivis, inir, cft_lb, cft_ub, ndecomp_pools use clm_varctl , only : iulog, use_cndv, use_vertsoilc, use_crop ! ! !PUBLIC TYPES: @@ -200,6 +200,8 @@ module pftconMod real(r8), allocatable :: flivewd (:) ! allocation parameter: fraction of new wood that is live (phloem and ray parenchyma) (no units) real(r8), allocatable :: fcur (:) ! allocation parameter: fraction of allocation that goes to currently displayed growth, remainder to storage real(r8), allocatable :: fcurdv (:) ! alternate fcur for use with cndv + real(r8), allocatable :: lf_f (:,:) ! leaf litter fractions + real(r8), allocatable :: fr_f (:,:) ! fine root litter fractions real(r8), allocatable :: lf_flab (:) ! leaf litter labile fraction real(r8), allocatable :: lf_fcel (:) ! leaf litter cellulose fraction real(r8), allocatable :: lf_flig (:) ! leaf litter lignin fraction @@ -415,6 +417,10 @@ subroutine InitAllocate (this) allocate( this%flivewd (0:mxpft) ) allocate( this%fcur (0:mxpft) ) allocate( this%fcurdv (0:mxpft) ) + ! Second dimension not i_litr_max because that parameter may obtain its + ! value after we've been through here + allocate( this%lf_f (0:mxpft, 1:ndecomp_pools) ) + allocate( this%fr_f (0:mxpft, 1:ndecomp_pools) ) allocate( this%lf_flab (0:mxpft) ) allocate( this%lf_fcel (0:mxpft) ) allocate( this%lf_flig (0:mxpft) ) @@ -755,6 +761,16 @@ subroutine InitRead(this) call ncd_io('fr_flig', this%fr_flig, 'read', ncid, readvar=readv, posNOTonfile=.true.) if ( .not. readv ) call endrun(msg=' ERROR: error in reading in pft data'//errMsg(sourcefile, __LINE__)) + ! Three hardwired fr_f* and lf_f* values: We pass them to 2d arrays for use + ! in do-loops. While executing the next few lines, we do not yet have access + ! to i_litr_min, i_litr_max. + this%fr_f(:,1) = this%fr_flab + this%fr_f(:,2) = this%fr_fcel + this%fr_f(:,3) = this%fr_flig + this%lf_f(:,1) = this%lf_flab + this%lf_f(:,2) = this%lf_fcel + this%lf_f(:,3) = this%lf_flig + call ncd_io('leaf_long', this%leaf_long, 'read', ncid, readvar=readv, posNOTonfile=.true.) if ( .not. readv ) call endrun(msg=' ERROR: error in reading in pft data'//errMsg(sourcefile, __LINE__)) @@ -1411,9 +1427,11 @@ subroutine Clean(this) deallocate( this%flivewd) deallocate( this%fcur) deallocate( this%fcurdv) + deallocate( this%lf_f ) deallocate( this%lf_flab) deallocate( this%lf_fcel) deallocate( this%lf_flig) + deallocate( this%fr_f ) deallocate( this%fr_flab) deallocate( this%fr_fcel) deallocate( this%fr_flig) diff --git a/src/soilbiogeochem/SoilBiogeochemCarbonFluxType.F90 b/src/soilbiogeochem/SoilBiogeochemCarbonFluxType.F90 index f1f2019397..9c43dd4fce 100644 --- a/src/soilbiogeochem/SoilBiogeochemCarbonFluxType.F90 +++ b/src/soilbiogeochem/SoilBiogeochemCarbonFluxType.F90 @@ -48,6 +48,7 @@ module SoilBiogeochemCarbonFluxType real(r8), pointer :: soilc_change_col (:) ! (gC/m2/s) FUN used soil C ! fluxes to receive carbon inputs from FATES + real(r8), pointer :: FATES_c_to_litr_c_col (:,:,:) ! total litter coming from ED. gC/m3/s real(r8), pointer :: FATES_c_to_litr_lab_c_col (:,:) ! total labile litter coming from ED. gC/m3/s real(r8), pointer :: FATES_c_to_litr_cel_c_col (:,:) ! total cellulose litter coming from ED. gC/m3/s real(r8), pointer :: FATES_c_to_litr_lig_c_col (:,:) ! total lignin litter coming from ED. gC/m3/s @@ -136,6 +137,9 @@ subroutine InitAllocate(this, bounds) if ( use_fates ) then ! initialize these variables to be zero rather than a bad number since they are not zeroed every timestep (due to a need for them to persist) + allocate(this%FATES_c_to_litr_c_col(begc:endc,1:nlevdecomp_full,1:ndecomp_pools)) + this%FATES_c_to_litr_c_col(begc:endc,1:nlevdecomp_full,1:ndecomp_pools) = 0._r8 + allocate(this%FATES_c_to_litr_lab_c_col(begc:endc,1:nlevdecomp_full)) this%FATES_c_to_litr_lab_c_col(begc:endc,1:nlevdecomp_full) = 0._r8 @@ -641,6 +645,14 @@ subroutine Restart(this, bounds, ncid, flag) interpinic_flag='interp', readvar=readvar, data=ptr1d) end if + + ! Copy last 3 variables to an array of litter pools for use in do loops. + ! Repeat copy in src/utils/clmfates_interfaceMod.F90. + ! Keep the three originals to avoid backwards compatibility issues with + ! restart files. + this%FATES_c_to_litr_c_col(:,:,1) = this%FATES_c_to_litr_lab_c_col(:,:) + this%FATES_c_to_litr_c_col(:,:,2) = this%FATES_c_to_litr_cel_c_col(:,:) + this%FATES_c_to_litr_c_col(:,:,3) = this%FATES_c_to_litr_lig_c_col(:,:) end if diff --git a/src/soilbiogeochem/SoilBiogeochemDecompCascadeBGCMod.F90 b/src/soilbiogeochem/SoilBiogeochemDecompCascadeBGCMod.F90 index 56f6748761..589263aa74 100644 --- a/src/soilbiogeochem/SoilBiogeochemDecompCascadeBGCMod.F90 +++ b/src/soilbiogeochem/SoilBiogeochemDecompCascadeBGCMod.F90 @@ -9,8 +9,9 @@ module SoilBiogeochemDecompCascadeBGCMod use shr_kind_mod , only : r8 => shr_kind_r8 use shr_const_mod , only : SHR_CONST_TKFRZ use shr_log_mod , only : errMsg => shr_log_errMsg - use clm_varpar , only : nlevsoi, nlevgrnd, nlevdecomp, ndecomp_cascade_transitions, ndecomp_pools - use clm_varpar , only : i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : nlevsoi, nlevgrnd + use clm_varpar , only : nlevdecomp, ndecomp_cascade_transitions, ndecomp_pools, ndecomp_pools_max + use clm_varpar , only : i_litr_min, i_litr_max, i_met_lit, i_cwd use clm_varctl , only : iulog, spinup_state, anoxia, use_lch4, use_vertsoilc, use_fates use clm_varcon , only : zsoi use decompMod , only : bounds_type @@ -32,7 +33,6 @@ module SoilBiogeochemDecompCascadeBGCMod private ! ! !PUBLIC MEMBER FUNCTIONS: - public :: DecompCascadeBGCreadNML ! Read in namelist public :: readParams ! Read in parameters from params file public :: init_decompcascade_bgc ! Initialization public :: decomp_rate_constants_bgc ! Figure out decomposition rates @@ -43,14 +43,11 @@ module SoilBiogeochemDecompCascadeBGCMod real(r8), public :: normalization_tref = 15._r8 ! reference temperature for normalizaion (degrees C) ! ! !PRIVATE DATA MEMBERS - - integer, private :: i_soil1 = -9 ! Soil Organic Matter (SOM) first pool - integer, private :: i_soil2 = -9 ! SOM second pool - integer, private :: i_soil3 = -9 ! SOM third pool - integer, private, parameter :: nsompools = 3 ! Number of SOM pools - integer, private, parameter :: i_litr1 = i_met_lit ! First litter pool, metobolic - integer, private, parameter :: i_litr2 = i_cel_lit ! Second litter pool, cellulose - integer, private, parameter :: i_litr3 = i_lig_lit ! Third litter pool, lignin + integer, private :: i_pro_som ! index of protected Soil Organic Matter (SOM) + integer, private :: i_rec_som ! index of recalcitrant SOM + integer, private :: i_avl_som ! index of available SOM + integer, private :: i_cel_lit ! index of cellulose litter pool + integer, private :: i_lig_lit ! index of lignin litter pool type, private :: params_type real(r8):: cn_s1_bgc !C:N for SOM 1 @@ -76,13 +73,12 @@ module SoilBiogeochemDecompCascadeBGCMod real(r8):: tau_cwd_bgc ! corrected fragmentation rate constant CWD, century leaves wood decomposition rates open, within range of 0 - 0.5 yr^-1 (1/0.3) (1/yr) real(r8) :: cwd_fcel_bgc !cellulose fraction for CWD - real(r8) :: cwd_flig_bgc ! + real(r8) :: cwd_flig - real(r8) :: k_frag_bgc !fragmentation rate for CWD real(r8) :: minpsi_bgc !minimum soil water potential for heterotrophic resp real(r8) :: maxpsi_bgc !maximum soil water potential for heterotrophic resp - real(r8) :: initial_Cstocks(nsompools) ! Initial Carbon stocks for a cold-start + real(r8), allocatable :: initial_Cstocks(:) ! Initial Carbon stocks for a cold-start real(r8) :: initial_Cstocks_depth ! Soil depth for initial Carbon stocks for a cold-start end type params_type @@ -96,71 +92,6 @@ module SoilBiogeochemDecompCascadeBGCMod contains - !----------------------------------------------------------------------- - subroutine DecompCascadeBGCreadNML( NLFilename ) - ! - ! !DESCRIPTION: - ! Read the namelist for soil BGC Decomposition Cascade - ! - ! !USES: - use fileutils , only : getavu, relavu, opnfil - use shr_nl_mod , only : shr_nl_find_group_name - use spmdMod , only : masterproc, mpicom - use shr_mpi_mod , only : shr_mpi_bcast - use clm_varctl , only : iulog - use shr_log_mod , only : errMsg => shr_log_errMsg - use abortutils , only : endrun - ! - ! !ARGUMENTS: - character(len=*), intent(in) :: NLFilename ! Namelist filename - ! - ! !LOCAL VARIABLES: - integer :: ierr ! error code - integer :: unitn ! unit for namelist file - - character(len=*), parameter :: subname = 'DecompCascadeBGCreadNML' - character(len=*), parameter :: nmlname = 'CENTURY_soilBGCDecompCascade' - !----------------------------------------------------------------------- - real(r8) :: initial_Cstocks(nsompools), initial_Cstocks_depth - namelist /CENTURY_soilBGCDecompCascade/ initial_Cstocks, initial_Cstocks_depth - - ! Initialize options to default values, in case they are not specified in - ! the namelist - - initial_Cstocks(:) = 200._r8 - initial_Cstocks_depth = 0.3 - - if (masterproc) then - unitn = getavu() - write(iulog,*) 'Read in '//nmlname//' namelist' - call opnfil (NLFilename, unitn, 'F') - call shr_nl_find_group_name(unitn, nmlname, status=ierr) - if (ierr == 0) then - read(unitn, nml=CENTURY_soilBGCDecompCascade, iostat=ierr) - if (ierr /= 0) then - call endrun(msg="ERROR reading "//nmlname//"namelist"//errmsg(__FILE__, __LINE__)) - end if - else - call endrun(msg="ERROR could NOT find "//nmlname//"namelist"//errmsg(__FILE__, __LINE__)) - end if - call relavu( unitn ) - end if - - call shr_mpi_bcast (initial_Cstocks , mpicom) - call shr_mpi_bcast (initial_Cstocks_depth, mpicom) - - if (masterproc) then - write(iulog,*) ' ' - write(iulog,*) nmlname//' settings:' - write(iulog,nml=CENTURY_soilBGCDecompCascade) - write(iulog,*) ' ' - end if - - params_inst%initial_Cstocks(:) = initial_Cstocks(:) - params_inst%initial_Cstocks_depth = initial_Cstocks_depth - - end subroutine DecompCascadeBGCreadNML - !----------------------------------------------------------------------- subroutine readParams ( ncid ) ! @@ -206,7 +137,7 @@ subroutine readParams ( ncid ) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) params_inst%tau_s3_bgc=tempr - tString='tau_cwd' + tString='tau_cwd_bgc' call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) params_inst%tau_cwd_bgc=tempr @@ -271,11 +202,6 @@ subroutine readParams ( ncid ) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) params_inst%cwd_fcel_bgc=tempr - tString='k_frag' - call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) - if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) - params_inst%k_frag_bgc=tempr - tString='minpsi_hr' call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) @@ -289,8 +215,18 @@ subroutine readParams ( ncid ) tString='cwd_flig' call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) - params_inst%cwd_flig_bgc=tempr + params_inst%cwd_flig=tempr + allocate(params_inst%initial_Cstocks(ndecomp_pools_max)) + tString='initial_Cstocks_bgc' + call ncd_io(trim(tString), params_inst%initial_Cstocks(:), 'read', ncid, readvar=readv) + if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) + + tString='initial_Cstocks_depth_bgc' + call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) + if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) + params_inst%initial_Cstocks_depth=tempr + end subroutine readParams !----------------------------------------------------------------------- @@ -395,7 +331,7 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i ! set the cellulose and lignin fractions for coarse woody debris cwd_fcel = params_inst%cwd_fcel_bgc - cwd_flig = params_inst%cwd_flig_bgc + cwd_flig = params_inst%cwd_flig ! set path fractions f_s2s1 = 0.42_r8/(0.45_r8) @@ -414,50 +350,110 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i initial_stock_soildepth = params_inst%initial_Cstocks_depth !------------------- list of pools and their attributes ------------ - floating_cn_ratio_decomp_pools(i_litr1) = .true. - decomp_cascade_con%decomp_pool_name_restart(i_litr1) = 'litr1' - decomp_cascade_con%decomp_pool_name_history(i_litr1) = 'LITR1' - decomp_cascade_con%decomp_pool_name_long(i_litr1) = 'litter 1' - decomp_cascade_con%decomp_pool_name_short(i_litr1) = 'L1' - is_litter(i_litr1) = .true. - is_soil(i_litr1) = .false. - is_cwd(i_litr1) = .false. - initial_cn_ratio(i_litr1) = 90._r8 - initial_stock(i_litr1) = 0._r8 - is_metabolic(i_litr1) = .true. - is_cellulose(i_litr1) = .false. - is_lignin(i_litr1) = .false. - - floating_cn_ratio_decomp_pools(i_litr2) = .true. - decomp_cascade_con%decomp_pool_name_restart(i_litr2) = 'litr2' - decomp_cascade_con%decomp_pool_name_history(i_litr2) = 'LITR2' - decomp_cascade_con%decomp_pool_name_long(i_litr2) = 'litter 2' - decomp_cascade_con%decomp_pool_name_short(i_litr2) = 'L2' - is_litter(i_litr2) = .true. - is_soil(i_litr2) = .false. - is_cwd(i_litr2) = .false. - initial_cn_ratio(i_litr2) = 90._r8 - initial_stock(i_litr2) = 0._r8 - is_metabolic(i_litr2) = .false. - is_cellulose(i_litr2) = .true. - is_lignin(i_litr2) = .false. - - floating_cn_ratio_decomp_pools(i_litr3) = .true. - decomp_cascade_con%decomp_pool_name_restart(i_litr3) = 'litr3' - decomp_cascade_con%decomp_pool_name_history(i_litr3) = 'LITR3' - decomp_cascade_con%decomp_pool_name_long(i_litr3) = 'litter 3' - decomp_cascade_con%decomp_pool_name_short(i_litr3) = 'L3' - is_litter(i_litr3) = .true. - is_soil(i_litr3) = .false. - is_cwd(i_litr3) = .false. - initial_cn_ratio(i_litr3) = 90._r8 - initial_stock(i_litr3) = 0._r8 - is_metabolic(i_litr3) = .false. - is_cellulose(i_litr3) = .false. - is_lignin(i_litr3) = .true. + i_litr_min = 1 + i_met_lit = i_litr_min + floating_cn_ratio_decomp_pools(i_met_lit) = .true. + decomp_cascade_con%decomp_pool_name_restart(i_met_lit) = 'litr1' + decomp_cascade_con%decomp_pool_name_history(i_met_lit) = 'LITR1' + decomp_cascade_con%decomp_pool_name_long(i_met_lit) = 'litter 1' + decomp_cascade_con%decomp_pool_name_short(i_met_lit) = 'L1' + is_litter(i_met_lit) = .true. + is_soil(i_met_lit) = .false. + is_cwd(i_met_lit) = .false. + initial_cn_ratio(i_met_lit) = 90._r8 + initial_stock(i_met_lit) = params_inst%initial_Cstocks(i_met_lit) + is_metabolic(i_met_lit) = .true. + is_cellulose(i_met_lit) = .false. + is_lignin(i_met_lit) = .false. + + i_cel_lit = i_met_lit + 1 + floating_cn_ratio_decomp_pools(i_cel_lit) = .true. + decomp_cascade_con%decomp_pool_name_restart(i_cel_lit) = 'litr2' + decomp_cascade_con%decomp_pool_name_history(i_cel_lit) = 'LITR2' + decomp_cascade_con%decomp_pool_name_long(i_cel_lit) = 'litter 2' + decomp_cascade_con%decomp_pool_name_short(i_cel_lit) = 'L2' + is_litter(i_cel_lit) = .true. + is_soil(i_cel_lit) = .false. + is_cwd(i_cel_lit) = .false. + initial_cn_ratio(i_cel_lit) = 90._r8 + initial_stock(i_cel_lit) = params_inst%initial_Cstocks(i_cel_lit) + is_metabolic(i_cel_lit) = .false. + is_cellulose(i_cel_lit) = .true. + is_lignin(i_cel_lit) = .false. + + i_lig_lit = i_cel_lit + 1 + floating_cn_ratio_decomp_pools(i_lig_lit) = .true. + decomp_cascade_con%decomp_pool_name_restart(i_lig_lit) = 'litr3' + decomp_cascade_con%decomp_pool_name_history(i_lig_lit) = 'LITR3' + decomp_cascade_con%decomp_pool_name_long(i_lig_lit) = 'litter 3' + decomp_cascade_con%decomp_pool_name_short(i_lig_lit) = 'L3' + is_litter(i_lig_lit) = .true. + is_soil(i_lig_lit) = .false. + is_cwd(i_lig_lit) = .false. + initial_cn_ratio(i_lig_lit) = 90._r8 + initial_stock(i_lig_lit) = params_inst%initial_Cstocks(i_lig_lit) + is_metabolic(i_lig_lit) = .false. + is_cellulose(i_lig_lit) = .false. + is_lignin(i_lig_lit) = .true. + + i_litr_max = i_lig_lit + if (i_litr_min /= 1 .or. i_litr_max < 2 .or. i_litr_max > 3) then + write(iulog,*) 'Expecting i_litr_min = 1 and i_litr_max = 2 or 3.' + write(iulog,*) 'See pftconMod, SoilBiogeochemCarbonFluxType, and' + write(iulog,*) 'clmfates_interfaceMod for ramifications of changing' + write(iulog,*) 'this assumption.' + call endrun(msg='ERROR: i_litr_min and/or i_litr_max out of range '// & + errMsg(sourcefile, __LINE__)) + end if + + i_pro_som = i_lig_lit + 1 + floating_cn_ratio_decomp_pools(i_pro_som) = .false. + decomp_cascade_con%decomp_pool_name_restart(i_pro_som) = 'soil1' + decomp_cascade_con%decomp_pool_name_history(i_pro_som) = 'SOIL1' + decomp_cascade_con%decomp_pool_name_long(i_pro_som) = 'soil 1' + decomp_cascade_con%decomp_pool_name_short(i_pro_som) = 'S1' + is_litter(i_pro_som) = .false. + is_soil(i_pro_som) = .true. + is_cwd(i_pro_som) = .false. + initial_cn_ratio(i_pro_som) = cn_s1 + initial_stock(i_pro_som) = params_inst%initial_Cstocks(i_pro_som) + is_metabolic(i_pro_som) = .false. + is_cellulose(i_pro_som) = .false. + is_lignin(i_pro_som) = .false. + + i_rec_som = i_pro_som + 1 + floating_cn_ratio_decomp_pools(i_rec_som) = .false. + decomp_cascade_con%decomp_pool_name_restart(i_rec_som) = 'soil2' + decomp_cascade_con%decomp_pool_name_history(i_rec_som) = 'SOIL2' + decomp_cascade_con%decomp_pool_name_long(i_rec_som) = 'soil 2' + decomp_cascade_con%decomp_pool_name_short(i_rec_som) = 'S2' + is_litter(i_rec_som) = .false. + is_soil(i_rec_som) = .true. + is_cwd(i_rec_som) = .false. + initial_cn_ratio(i_rec_som) = cn_s2 + initial_stock(i_rec_som) = params_inst%initial_Cstocks(i_rec_som) + is_metabolic(i_rec_som) = .false. + is_cellulose(i_rec_som) = .false. + is_lignin(i_rec_som) = .false. + + i_avl_som = i_rec_som + 1 + floating_cn_ratio_decomp_pools(i_avl_som) = .false. + decomp_cascade_con%decomp_pool_name_restart(i_avl_som) = 'soil3' + decomp_cascade_con%decomp_pool_name_history(i_avl_som) = 'SOIL3' + decomp_cascade_con%decomp_pool_name_long(i_avl_som) = 'soil 3' + decomp_cascade_con%decomp_pool_name_short(i_avl_som) = 'S3' + is_litter(i_avl_som) = .false. + is_soil(i_avl_som) = .true. + is_cwd(i_avl_som) = .false. + initial_cn_ratio(i_avl_som) = cn_s3 + initial_stock(i_avl_som) = params_inst%initial_Cstocks(i_avl_som) + is_metabolic(i_avl_som) = .false. + is_cellulose(i_avl_som) = .false. + is_lignin(i_avl_som) = .false. if (.not. use_fates) then ! CWD + i_cwd = i_avl_som + 1 floating_cn_ratio_decomp_pools(i_cwd) = .true. decomp_cascade_con%decomp_pool_name_restart(i_cwd) = 'cwd' decomp_cascade_con%decomp_pool_name_history(i_cwd) = 'CWD' @@ -467,86 +463,28 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i is_soil(i_cwd) = .false. is_cwd(i_cwd) = .true. initial_cn_ratio(i_cwd) = 90._r8 - initial_stock(i_cwd) = 0._r8 + initial_stock(i_cwd) = params_inst%initial_Cstocks(i_cwd) is_metabolic(i_cwd) = .false. is_cellulose(i_cwd) = .false. is_lignin(i_cwd) = .false. endif - if (.not. use_fates) then - i_soil1 = 5 - else - i_soil1 = 4 - endif - floating_cn_ratio_decomp_pools(i_soil1) = .false. - decomp_cascade_con%decomp_pool_name_restart(i_soil1) = 'soil1' - decomp_cascade_con%decomp_pool_name_history(i_soil1) = 'SOIL1' - decomp_cascade_con%decomp_pool_name_long(i_soil1) = 'soil 1' - decomp_cascade_con%decomp_pool_name_short(i_soil1) = 'S1' - is_litter(i_soil1) = .false. - is_soil(i_soil1) = .true. - is_cwd(i_soil1) = .false. - initial_cn_ratio(i_soil1) = cn_s1 - initial_stock(i_soil1) = params_inst%initial_Cstocks(1) - is_metabolic(i_soil1) = .false. - is_cellulose(i_soil1) = .false. - is_lignin(i_soil1) = .false. - - if (.not. use_fates) then - i_soil2 = 6 - else - i_soil2 = 5 - endif - floating_cn_ratio_decomp_pools(i_soil2) = .false. - decomp_cascade_con%decomp_pool_name_restart(i_soil2) = 'soil2' - decomp_cascade_con%decomp_pool_name_history(i_soil2) = 'SOIL2' - decomp_cascade_con%decomp_pool_name_long(i_soil2) = 'soil 2' - decomp_cascade_con%decomp_pool_name_short(i_soil2) = 'S2' - is_litter(i_soil2) = .false. - is_soil(i_soil2) = .true. - is_cwd(i_soil2) = .false. - initial_cn_ratio(i_soil2) = cn_s2 - initial_stock(i_soil2) = params_inst%initial_Cstocks(2) - is_metabolic(i_soil2) = .false. - is_cellulose(i_soil2) = .false. - is_lignin(i_soil2) = .false. - - if (.not. use_fates) then - i_soil3 = 7 - else - i_soil3 = 6 - endif - floating_cn_ratio_decomp_pools(i_soil3) = .false. - decomp_cascade_con%decomp_pool_name_restart(i_soil3) = 'soil3' - decomp_cascade_con%decomp_pool_name_history(i_soil3) = 'SOIL3' - decomp_cascade_con%decomp_pool_name_long(i_soil3) = 'soil 3' - decomp_cascade_con%decomp_pool_name_short(i_soil3) = 'S3' - is_litter(i_soil3) = .false. - is_soil(i_soil3) = .true. - is_cwd(i_soil3) = .false. - initial_cn_ratio(i_soil3) = cn_s3 - initial_stock(i_soil3) = params_inst%initial_Cstocks(3) - is_metabolic(i_soil3) = .false. - is_cellulose(i_soil3) = .false. - is_lignin(i_soil3) = .false. - - speedup_fac = 1._r8 !lit1 - spinup_factor(i_litr1) = 1._r8 + spinup_factor(i_met_lit) = 1._r8 !lit2,3 - spinup_factor(i_litr2) = 1._r8 - spinup_factor(i_litr3) = 1._r8 + spinup_factor(i_cel_lit) = 1._r8 + spinup_factor(i_lig_lit) = 1._r8 !CWD if (.not. use_fates) then spinup_factor(i_cwd) = max(1._r8, (speedup_fac * params_inst%tau_cwd_bgc / 2._r8 )) end if !som1 - spinup_factor(i_soil1) = 1._r8 + spinup_factor(i_pro_som) = 1._r8 !som2,3 - spinup_factor(i_soil2) = max(1._r8, (speedup_fac * params_inst%tau_s2_bgc)) - spinup_factor(i_soil3) = max(1._r8, (speedup_fac * params_inst%tau_s3_bgc)) + spinup_factor(i_rec_som) = max(1._r8, (speedup_fac * params_inst%tau_s2_bgc)) + spinup_factor(i_avl_som) = max(1._r8, (speedup_fac * params_inst%tau_s3_bgc)) if ( masterproc ) then write(iulog,*) 'Spinup_state ',spinup_state @@ -557,57 +495,57 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i i_l1s1 = 1 decomp_cascade_con%cascade_step_name(i_l1s1) = 'L1S1' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l1s1) = rf_l1s1 - cascade_donor_pool(i_l1s1) = i_litr1 - cascade_receiver_pool(i_l1s1) = i_soil1 + cascade_donor_pool(i_l1s1) = i_met_lit + cascade_receiver_pool(i_l1s1) = i_pro_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l1s1) = 1.0_r8 i_l2s1 = 2 decomp_cascade_con%cascade_step_name(i_l2s1) = 'L2S1' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l2s1) = rf_l2s1 - cascade_donor_pool(i_l2s1) = i_litr2 - cascade_receiver_pool(i_l2s1) = i_soil1 + cascade_donor_pool(i_l2s1) = i_cel_lit + cascade_receiver_pool(i_l2s1) = i_pro_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l2s1)= 1.0_r8 i_l3s2 = 3 decomp_cascade_con%cascade_step_name(i_l3s2) = 'L3S2' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l3s2) = rf_l3s2 - cascade_donor_pool(i_l3s2) = i_litr3 - cascade_receiver_pool(i_l3s2) = i_soil2 + cascade_donor_pool(i_l3s2) = i_lig_lit + cascade_receiver_pool(i_l3s2) = i_rec_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_l3s2) = 1.0_r8 i_s1s2 = 4 decomp_cascade_con%cascade_step_name(i_s1s2) = 'S1S2' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s1s2) = rf_s1s2(bounds%begc:bounds%endc,1:nlevdecomp) - cascade_donor_pool(i_s1s2) = i_soil1 - cascade_receiver_pool(i_s1s2) = i_soil2 + cascade_donor_pool(i_s1s2) = i_pro_som + cascade_receiver_pool(i_s1s2) = i_rec_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s1s2) = f_s1s2(bounds%begc:bounds%endc,1:nlevdecomp) i_s1s3 = 5 decomp_cascade_con%cascade_step_name(i_s1s3) = 'S1S3' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s1s3) = rf_s1s3(bounds%begc:bounds%endc,1:nlevdecomp) - cascade_donor_pool(i_s1s3) = i_soil1 - cascade_receiver_pool(i_s1s3) = i_soil3 + cascade_donor_pool(i_s1s3) = i_pro_som + cascade_receiver_pool(i_s1s3) = i_avl_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s1s3) = f_s1s3(bounds%begc:bounds%endc,1:nlevdecomp) i_s2s1 = 6 decomp_cascade_con%cascade_step_name(i_s2s1) = 'S2S1' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s2s1) = rf_s2s1 - cascade_donor_pool(i_s2s1) = i_soil2 - cascade_receiver_pool(i_s2s1) = i_soil1 + cascade_donor_pool(i_s2s1) = i_rec_som + cascade_receiver_pool(i_s2s1) = i_pro_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s2s1) = f_s2s1 i_s2s3 = 7 decomp_cascade_con%cascade_step_name(i_s2s3) = 'S2S3' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s2s3) = rf_s2s3 - cascade_donor_pool(i_s2s3) = i_soil2 - cascade_receiver_pool(i_s2s3) = i_soil3 + cascade_donor_pool(i_s2s3) = i_rec_som + cascade_receiver_pool(i_s2s3) = i_avl_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s2s3) = f_s2s3 i_s3s1 = 8 decomp_cascade_con%cascade_step_name(i_s3s1) = 'S3S1' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s3s1) = rf_s3s1 - cascade_donor_pool(i_s3s1) = i_soil3 - cascade_receiver_pool(i_s3s1) = i_soil1 + cascade_donor_pool(i_s3s1) = i_avl_som + cascade_receiver_pool(i_s3s1) = i_pro_som pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_s3s1) = 1.0_r8 if (.not. use_fates) then @@ -615,14 +553,14 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i decomp_cascade_con%cascade_step_name(i_cwdl2) = 'CWDL2' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_cwdl2) = rf_cwdl2 cascade_donor_pool(i_cwdl2) = i_cwd - cascade_receiver_pool(i_cwdl2) = i_litr2 + cascade_receiver_pool(i_cwdl2) = i_cel_lit pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_cwdl2) = cwd_fcel i_cwdl3 = 10 decomp_cascade_con%cascade_step_name(i_cwdl3) = 'CWDL3' rf_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_cwdl3) = rf_cwdl3 cascade_donor_pool(i_cwdl3) = i_cwd - cascade_receiver_pool(i_cwdl3) = i_litr3 + cascade_receiver_pool(i_cwdl3) = i_lig_lit pathfrac_decomp_cascade(bounds%begc:bounds%endc,1:nlevdecomp,i_cwdl3) = cwd_flig end if @@ -630,6 +568,7 @@ subroutine init_decompcascade_bgc(bounds, soilbiogeochem_state_inst, soilstate_i deallocate(rf_s1s3) deallocate(f_s1s2) deallocate(f_s1s3) + deallocate(params_inst%initial_Cstocks) end associate @@ -744,14 +683,14 @@ subroutine decomp_rate_constants_bgc(bounds, num_soilc, filter_soilc, & do fc = 1,num_soilc c = filter_soilc(fc) ! - if ( abs(spinup_factor(i_litr1) - 1._r8) .gt. .000001_r8) then - spinup_geogterm_l1(c) = spinup_factor(i_litr1) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) + if ( abs(spinup_factor(i_met_lit) - 1._r8) .gt. .000001_r8) then + spinup_geogterm_l1(c) = spinup_factor(i_met_lit) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) else spinup_geogterm_l1(c) = 1._r8 endif ! - if ( abs(spinup_factor(i_litr2) - 1._r8) .gt. .000001_r8) then - spinup_geogterm_l23(c) = spinup_factor(i_litr2) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) + if ( abs(spinup_factor(i_cel_lit) - 1._r8) .gt. .000001_r8) then + spinup_geogterm_l23(c) = spinup_factor(i_cel_lit) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) else spinup_geogterm_l23(c) = 1._r8 endif @@ -764,20 +703,20 @@ subroutine decomp_rate_constants_bgc(bounds, num_soilc, filter_soilc, & endif endif ! - if ( abs(spinup_factor(i_soil1) - 1._r8) .gt. .000001_r8) then - spinup_geogterm_s1(c) = spinup_factor(i_soil1) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) + if ( abs(spinup_factor(i_pro_som) - 1._r8) .gt. .000001_r8) then + spinup_geogterm_s1(c) = spinup_factor(i_pro_som) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) else spinup_geogterm_s1(c) = 1._r8 endif ! - if ( abs(spinup_factor(i_soil2) - 1._r8) .gt. .000001_r8) then - spinup_geogterm_s2(c) = spinup_factor(i_soil2) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) + if ( abs(spinup_factor(i_rec_som) - 1._r8) .gt. .000001_r8) then + spinup_geogterm_s2(c) = spinup_factor(i_rec_som) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) else spinup_geogterm_s2(c) = 1._r8 endif ! - if ( abs(spinup_factor(i_soil3) - 1._r8) .gt. .000001_r8) then - spinup_geogterm_s3(c) = spinup_factor(i_soil3) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) + if ( abs(spinup_factor(i_avl_som) - 1._r8) .gt. .000001_r8) then + spinup_geogterm_s3(c) = spinup_factor(i_avl_som) * get_spinup_latitude_term(grc%latdeg(col%gridcell(c))) else spinup_geogterm_s3(c) = 1._r8 endif @@ -986,70 +925,43 @@ subroutine decomp_rate_constants_bgc(bounds, num_soilc, filter_soilc, & end do endif - if (use_vertsoilc) then - ! add a term to reduce decomposition rate at depth - ! for now used a fixed e-folding depth - do j = 1, nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - depth_scalar(c,j) = exp(-zsoi(j)/decomp_depth_efolding) - end do + ! add a term to reduce decomposition rate at depth + ! for now used a fixed e-folding depth + do j = 1, nlevdecomp + do fc = 1, num_soilc + c = filter_soilc(fc) + if (use_vertsoilc) then + depth_scalar(c,j) = exp(-zsoi(j) / decomp_depth_efolding) + else + depth_scalar(c,j) = 1.0_r8 + end if end do - end if + end do ! calculate rate constants for all litter and som pools - if (use_vertsoilc) then - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_litr1) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_l1(c) - decomp_k(c,j,i_litr2) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_l23(c) - decomp_k(c,j,i_litr3) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_l23(c) - decomp_k(c,j,i_soil1) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_s1(c) - decomp_k(c,j,i_soil2) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_s2(c) - decomp_k(c,j,i_soil3) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) & - * spinup_geogterm_s3(c) - end do - end do - else - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_litr1) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l1(c) - decomp_k(c,j,i_litr2) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l23(c) - decomp_k(c,j,i_litr3) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l23(c) - decomp_k(c,j,i_soil1) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s1(c) - decomp_k(c,j,i_soil2) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s2(c) - decomp_k(c,j,i_soil3) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s3(c) - end do + do j = 1,nlevdecomp + do fc = 1,num_soilc + c = filter_soilc(fc) + decomp_k(c,j,i_met_lit) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l1(c) + decomp_k(c,j,i_cel_lit) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l23(c) + decomp_k(c,j,i_lig_lit) = k_l2_l3 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_l23(c) + decomp_k(c,j,i_pro_som) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s1(c) + decomp_k(c,j,i_rec_som) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s2(c) + decomp_k(c,j,i_avl_som) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_s3(c) + ! same for cwd but only if fates is not enabled; fates handles CWD + ! on its own structure + if (.not. use_fates) then + decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) * spinup_geogterm_cwd(c) + end if end do - end if - - ! do the same for cwd, but only if fates is not enabled, because fates handles CWD on its own structure - if (.not. use_fates) then - if (use_vertsoilc) then - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * & - o_scalar(c,j) * spinup_geogterm_cwd(c) - end do - end do - else - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * & - o_scalar(c,j) * spinup_geogterm_cwd(c) - end do - end do - end if - end if + end do end associate diff --git a/src/soilbiogeochem/SoilBiogeochemDecompCascadeCNMod.F90 b/src/soilbiogeochem/SoilBiogeochemDecompCascadeCNMod.F90 index 8305fcefe6..5a198483e5 100644 --- a/src/soilbiogeochem/SoilBiogeochemDecompCascadeCNMod.F90 +++ b/src/soilbiogeochem/SoilBiogeochemDecompCascadeCNMod.F90 @@ -10,7 +10,7 @@ module SoilBiogeochemDecompCascadeCNMod use shr_const_mod , only : SHR_CONST_TKFRZ use shr_log_mod , only : errMsg => shr_log_errMsg use clm_varpar , only : nlevsoi, nlevgrnd, nlevdecomp, ndecomp_cascade_transitions, ndecomp_pools - use clm_varpar , only : i_met_lit, i_cel_lit, i_lig_lit, i_cwd + use clm_varpar , only : i_litr1, i_litr2, i_litr3, i_cwd use clm_varctl , only : iulog, spinup_state, anoxia, use_lch4, use_vertsoilc, use_fates use clm_varcon , only : zsoi use decompMod , only : bounds_type @@ -33,6 +33,12 @@ module SoilBiogeochemDecompCascadeCNMod public :: init_decompcascade_cn public :: decomp_rate_constants_cn + ! !PRIVATE DATA MEMBERS + integer, private :: i_soil1 = -9 ! Soil Organic Matter (SOM) first pool + integer, private :: i_soil2 = -9 ! SOM second pool + integer, private :: i_soil3 = -9 ! SOM third pool + integer, private :: i_soil4 = -9 ! SOM fourth pool + type, private :: params_type real(r8):: cn_s1_cn !C:N for SOM 1 real(r8):: cn_s2_cn !C:N for SOM 2 @@ -194,7 +200,7 @@ subroutine readParams ( ncid ) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) params_inst%k_s4_cn=tempr - tString='k_frag' + tString='k_frag_cn' call ncd_io(trim(tString),tempr, 'read', ncid, readvar=readv) if ( .not. readv ) call endrun(msg=trim(errCode)//trim(tString)//errMsg(sourcefile, __LINE__)) params_inst%k_frag_cn=tempr @@ -244,13 +250,6 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) real(r8) :: cn_s3 real(r8) :: cn_s4 - integer :: i_litr1 - integer :: i_litr2 - integer :: i_litr3 - integer :: i_soil1 - integer :: i_soil2 - integer :: i_soil3 - integer :: i_soil4 integer :: i_l1s1 integer :: i_l2s2 integer :: i_l3s3 @@ -302,7 +301,6 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) !------------------- list of pools and their attributes ------------ - i_litr1 = i_met_lit floating_cn_ratio_decomp_pools(i_litr1) = .true. decomp_cascade_con%decomp_pool_name_restart(i_litr1) = 'litr1' decomp_cascade_con%decomp_pool_name_history(i_litr1) = 'LITR1' @@ -317,7 +315,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_litr1) = .false. is_lignin(i_litr1) = .false. - i_litr2 = i_cel_lit + i_litr2 = i_litr1 + 1 floating_cn_ratio_decomp_pools(i_litr2) = .true. decomp_cascade_con%decomp_pool_name_restart(i_litr2) = 'litr2' decomp_cascade_con%decomp_pool_name_history(i_litr2) = 'LITR2' @@ -332,7 +330,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_litr2) = .true. is_lignin(i_litr2) = .false. - i_litr3 = i_lig_lit + i_litr3 = i_litr2 + 1 floating_cn_ratio_decomp_pools(i_litr3) = .true. decomp_cascade_con%decomp_pool_name_restart(i_litr3) = 'litr3' decomp_cascade_con%decomp_pool_name_history(i_litr3) = 'LITR3' @@ -347,27 +345,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_litr3) = .false. is_lignin(i_litr3) = .true. - if (.not. use_fates) then - floating_cn_ratio_decomp_pools(i_cwd) = .true. - decomp_cascade_con%decomp_pool_name_restart(i_cwd) = 'cwd' - decomp_cascade_con%decomp_pool_name_history(i_cwd) = 'CWD' - decomp_cascade_con%decomp_pool_name_long(i_cwd) = 'coarse woody debris' - decomp_cascade_con%decomp_pool_name_short(i_cwd) = 'CWD' - is_litter(i_cwd) = .false. - is_soil(i_cwd) = .false. - is_cwd(i_cwd) = .true. - initial_cn_ratio(i_cwd) = 500._r8 - initial_stock(i_cwd) = 0._r8 - is_metabolic(i_cwd) = .false. - is_cellulose(i_cwd) = .false. - is_lignin(i_cwd) = .false. - end if - - if ( .not. use_fates ) then - i_soil1 = 5 - else - i_soil1 = 4 - endif + i_soil1 = i_litr3 + 1 floating_cn_ratio_decomp_pools(i_soil1) = .false. decomp_cascade_con%decomp_pool_name_restart(i_soil1) = 'soil1' decomp_cascade_con%decomp_pool_name_history(i_soil1) = 'SOIL1' @@ -382,11 +360,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_soil1) = .false. is_lignin(i_soil1) = .false. - if ( .not. use_fates ) then - i_soil2 = 6 - else - i_soil2 = 5 - endif + i_soil2 = i_soil1 + 1 floating_cn_ratio_decomp_pools(i_soil2) = .false. decomp_cascade_con%decomp_pool_name_restart(i_soil2) = 'soil2' decomp_cascade_con%decomp_pool_name_history(i_soil2) = 'SOIL2' @@ -401,11 +375,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_soil2) = .false. is_lignin(i_soil2) = .false. - if ( .not. use_fates ) then - i_soil3 = 7 - else - i_soil3 = 6 - endif + i_soil3 = i_soil2 + 1 floating_cn_ratio_decomp_pools(i_soil3) = .false. decomp_cascade_con%decomp_pool_name_restart(i_soil3) = 'soil3' decomp_cascade_con%decomp_pool_name_history(i_soil3) = 'SOIL3' @@ -420,11 +390,7 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_soil3) = .false. is_lignin(i_soil3) = .false. - if ( .not. use_fates ) then - i_soil4 = 8 - else - i_soil4 = 7 - endif + i_soil4 = i_soil3 + 1 floating_cn_ratio_decomp_pools(i_soil4) = .false. decomp_cascade_con%decomp_pool_name_restart(i_soil4) = 'soil4' decomp_cascade_con%decomp_pool_name_history(i_soil4) = 'SOIL4' @@ -439,6 +405,23 @@ subroutine init_decompcascade_cn(bounds, soilbiogeochem_state_inst) is_cellulose(i_soil4) = .false. is_lignin(i_soil4) = .false. + if (.not. use_fates) then + i_cwd = i_soil4 + 1 + floating_cn_ratio_decomp_pools(i_cwd) = .true. + decomp_cascade_con%decomp_pool_name_restart(i_cwd) = 'cwd' + decomp_cascade_con%decomp_pool_name_history(i_cwd) = 'CWD' + decomp_cascade_con%decomp_pool_name_long(i_cwd) = 'coarse woody debris' + decomp_cascade_con%decomp_pool_name_short(i_cwd) = 'CWD' + is_litter(i_cwd) = .false. + is_soil(i_cwd) = .false. + is_cwd(i_cwd) = .true. + initial_cn_ratio(i_cwd) = 500._r8 + initial_stock(i_cwd) = 0._r8 + is_metabolic(i_cwd) = .false. + is_cellulose(i_cwd) = .false. + is_lignin(i_cwd) = .false. + end if + floating_cn_ratio_decomp_pools(i_atm) = .false. decomp_cascade_con%decomp_pool_name_restart(i_atm) = 'atmosphere' decomp_cascade_con%decomp_pool_name_history(i_atm) = 'atmosphere' @@ -576,23 +559,6 @@ subroutine decomp_rate_constants_cn(bounds, & real(r8):: k_s3 ! decomposition rate constant SOM 3 real(r8):: k_s4 ! decomposition rate constant SOM 4 real(r8):: k_frag ! fragmentation rate constant CWD - real(r8):: ck_l1 ! corrected decomposition rate constant litter 1 - real(r8):: ck_l2 ! corrected decomposition rate constant litter 2 - real(r8):: ck_l3 ! corrected decomposition rate constant litter 3 - real(r8):: ck_s1 ! corrected decomposition rate constant SOM 1 - real(r8):: ck_s2 ! corrected decomposition rate constant SOM 2 - real(r8):: ck_s3 ! corrected decomposition rate constant SOM 3 - real(r8):: ck_s4 ! corrected decomposition rate constant SOM 4 - real(r8):: ck_frag ! corrected fragmentation rate constant CWD - real(r8):: cwdc_loss ! fragmentation rate for CWD carbon (gC/m2/s) - real(r8):: cwdn_loss ! fragmentation rate for CWD nitrogen (gN/m2/s) - integer :: i_litr1 - integer :: i_litr2 - integer :: i_litr3 - integer :: i_soil1 - integer :: i_soil2 - integer :: i_soil3 - integer :: i_soil4 integer :: c, fc, j, k, l real(r8):: Q10 ! temperature dependence real(r8):: froz_q10 ! separate q10 for frozen soil respiration rates. default to same as above zero rates @@ -679,21 +645,6 @@ subroutine decomp_rate_constants_cn(bounds, & k_s4 = k_s4 * params_inst%spinup_vector(4) endif - i_litr1 = 1 - i_litr2 = 2 - i_litr3 = 3 - if (use_fates) then - i_soil1 = 4 - i_soil2 = 5 - i_soil3 = 6 - i_soil4 = 7 - else - i_soil1 = 5 - i_soil2 = 6 - i_soil3 = 7 - i_soil4 = 8 - endif - !--- time dependent coefficients-----! if ( nlevdecomp .eq. 1 ) then @@ -857,64 +808,45 @@ subroutine decomp_rate_constants_cn(bounds, & o_scalar(bounds%begc:bounds%endc,1:nlevdecomp) = 1._r8 end if - if (use_vertsoilc) then - ! add a term to reduce decomposition rate at depth - ! for now used a fixed e-folding depth - do j = 1, nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - depth_scalar(c,j) = exp(-zsoi(j)/decomp_depth_efolding) - end do - end do - end if - - ! calculate rate constants for all litter and som pools - if (use_vertsoilc) then - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_litr1) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_litr2) = k_l2 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_litr3) = k_l3 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil1) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil2) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil3) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil4) = k_s4 * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - end do + ! add a term to reduce decomposition rate at depth + ! for now used a fixed e-folding depth + do j = 1, nlevdecomp + do fc = 1, num_soilc + c = filter_soilc(fc) + if (use_vertsoilc) then + depth_scalar(c,j) = exp(-zsoi(j) / decomp_depth_efolding) + else + depth_scalar(c,j) = 1.0_r8 + end if end do - else - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_litr1) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_litr2) = k_l2 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_litr3) = k_l3 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil1) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil2) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil3) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - decomp_k(c,j,i_soil4) = k_s4 * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - end do + end do + + ! calculate rate constants for all litter and som pools + do j = 1,nlevdecomp + do fc = 1,num_soilc + c = filter_soilc(fc) + decomp_k(c,j,i_litr1) = k_l1 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_litr2) = k_l2 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_litr3) = k_l3 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_soil1) = k_s1 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_soil2) = k_s2 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_soil3) = k_s3 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + decomp_k(c,j,i_soil4) = k_s4 * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + ! same for cwd but only if fates is not enabled; fates handles CWD + ! on its own structure + if (.not. use_fates) then + decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * & + depth_scalar(c,j) * o_scalar(c,j) / dt + end if end do - end if - - ! do the same for cwd, but only if fates is not enabled (because fates handles CWD on its own structure - if (.not. use_fates) then - if (use_vertsoilc) then - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * depth_scalar(c,j) * o_scalar(c,j) / dt - end do - end do - else - do j = 1,nlevdecomp - do fc = 1,num_soilc - c = filter_soilc(fc) - decomp_k(c,j,i_cwd) = k_frag * t_scalar(c,j) * w_scalar(c,j) * o_scalar(c,j) / dt - end do - end do - end if - end if + end do end associate diff --git a/src/soilbiogeochem/SoilBiogeochemNStateUpdate1Mod.F90 b/src/soilbiogeochem/SoilBiogeochemNStateUpdate1Mod.F90 index c3bc61a315..3d99d93755 100644 --- a/src/soilbiogeochem/SoilBiogeochemNStateUpdate1Mod.F90 +++ b/src/soilbiogeochem/SoilBiogeochemNStateUpdate1Mod.F90 @@ -7,9 +7,9 @@ module SoilBiogeochemNStateUpdate1Mod ! !USES: use shr_kind_mod , only: r8 => shr_kind_r8 use clm_time_manager , only : get_step_size_real - use clm_varpar , only : nlevdecomp, ndecomp_pools, ndecomp_cascade_transitions + use clm_varpar , only : nlevdecomp, ndecomp_cascade_transitions use clm_varctl , only : iulog, use_nitrif_denitrif, use_crop - use clm_varcon , only : nitrif_n2o_loss_frac, dzsoi_decomp + use clm_varcon , only : nitrif_n2o_loss_frac use SoilBiogeochemStateType , only : soilbiogeochem_state_type use SoilBiogeochemNitrogenStateType , only : soilbiogeochem_nitrogenstate_type use SoilBiogeochemNitrogenfluxType , only : soilbiogeochem_nitrogenflux_type @@ -43,7 +43,7 @@ subroutine SoilBiogeochemNStateUpdate1(num_soilc, filter_soilc, & ! ! !LOCAL VARIABLES: integer :: c,p,j,l,k ! indices - integer :: fp,fc ! lake filter indices + integer :: fc ! lake filter indices real(r8):: dt ! radiation time step (seconds) !----------------------------------------------------------------------- diff --git a/src/utils/clmfates_interfaceMod.F90 b/src/utils/clmfates_interfaceMod.F90 index eeadd41f49..223cdc6970 100644 --- a/src/utils/clmfates_interfaceMod.F90 +++ b/src/utils/clmfates_interfaceMod.F90 @@ -926,6 +926,17 @@ subroutine dynamics_driv(this, nc, bounds_clump, & soilbiogeochem_carbonflux_inst%FATES_c_to_litr_lig_c_col(c,1:nld_si) = & this%fates(nc)%bc_out(s)%litt_flux_lig_c_si(1:nld_si) + ! Copy last 3 variables to an array of litter pools for use in do loops + ! and repeat copy in soilbiogeochem/SoilBiogeochemCarbonFluxType.F90. + ! Keep the three originals to avoid backwards compatibility issues with + ! restart files. + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_c_col(c,1:nld_si,1) = & + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_lab_c_col(c,1:nld_si) + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_c_col(c,1:nld_si,2) = & + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_cel_c_col(c,1:nld_si) + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_c_col(c,1:nld_si,3) = & + soilbiogeochem_carbonflux_inst%FATES_c_to_litr_lig_c_col(c,1:nld_si) + end do