1 | #define WRF_PORT |
---|
2 | |
---|
3 | module physconst |
---|
4 | !------------------------------------------------------------------------ |
---|
5 | ! Based on physconst.F90 from CAM |
---|
6 | ! Ported to WRF by William.Gustafson@pnl.gov, Nov. 2009 |
---|
7 | ! Updated to version from CESM 1.0.1 Nov. 2010 |
---|
8 | !------------------------------------------------------------------------ |
---|
9 | |
---|
10 | ! Physical constants. Use CCSM shared values whenever available. |
---|
11 | |
---|
12 | use shr_kind_mod, only: r8 => shr_kind_r8 |
---|
13 | use shr_const_mod, only: shr_const_g, shr_const_stebol, shr_const_tkfrz, & |
---|
14 | shr_const_mwdair, shr_const_rdair, shr_const_mwwv, & |
---|
15 | shr_const_latice, shr_const_latvap, shr_const_cpdair, & |
---|
16 | shr_const_rhofw, shr_const_cpwv, shr_const_rgas, & |
---|
17 | shr_const_karman, shr_const_pstd, shr_const_rhodair,& |
---|
18 | shr_const_avogad, shr_const_boltz, shr_const_cpfw, & |
---|
19 | shr_const_rwv, shr_const_zvir, shr_const_pi, & |
---|
20 | shr_const_rearth, shr_const_sday, shr_const_cday, & |
---|
21 | shr_const_spval |
---|
22 | implicit none |
---|
23 | private |
---|
24 | public :: physconst_readnl |
---|
25 | save |
---|
26 | ! Constants based off share code or defined in physconst |
---|
27 | |
---|
28 | real(r8), public, parameter :: avogad = shr_const_avogad ! Avogadro's number (molecules/kmole) |
---|
29 | real(r8), public, parameter :: boltz = shr_const_boltz ! Boltzman's constant (J/K/molecule) |
---|
30 | real(r8), public, parameter :: cday = shr_const_cday ! sec in calendar day ~ sec |
---|
31 | real(r8), public, parameter :: cpair = shr_const_cpdair ! specific heat of dry air (J/K/kg) |
---|
32 | real(r8), public, parameter :: cpliq = shr_const_cpfw ! specific heat of fresh h2o (J/K/kg) |
---|
33 | real(r8), public, parameter :: karman = shr_const_karman ! Von Karman constant |
---|
34 | real(r8), public, parameter :: latice = shr_const_latice ! Latent heat of fusion (J/kg) |
---|
35 | real(r8), public, parameter :: latvap = shr_const_latvap ! Latent heat of vaporization (J/kg) |
---|
36 | real(r8), public, parameter :: pi = shr_const_pi ! 3.14... |
---|
37 | real(r8), public, parameter :: pstd = shr_const_pstd ! Standard pressure (Pascals) |
---|
38 | real(r8), public, parameter :: r_universal = shr_const_rgas ! Universal gas constant (J/K/kmol) |
---|
39 | real(r8), public, parameter :: rhoh2o = shr_const_rhofw ! Density of liquid water (STP) |
---|
40 | real(r8), public, parameter :: spval = shr_const_spval !special value |
---|
41 | real(r8), public, parameter :: stebol = shr_const_stebol ! Stefan-Boltzmann's constant (W/m^2/K^4) |
---|
42 | real(r8), public, parameter :: tmelt = shr_const_tkfrz ! Freezing point of water (K) |
---|
43 | |
---|
44 | real(r8), public, parameter :: c0 = 2.99792458e8_r8 ! Speed of light in a vacuum (m/s) |
---|
45 | real(r8), public, parameter :: planck = 6.6260755e-34_r8 ! Planck's constant (J.s) |
---|
46 | |
---|
47 | ! Molecular weights |
---|
48 | real(r8), public, parameter :: mwco2 = 44._r8 ! molecular weight co2 |
---|
49 | real(r8), public, parameter :: mwn2o = 44._r8 ! molecular weight n2o |
---|
50 | real(r8), public, parameter :: mwch4 = 16._r8 ! molecular weight ch4 |
---|
51 | real(r8), public, parameter :: mwf11 = 136._r8 ! molecular weight cfc11 |
---|
52 | real(r8), public, parameter :: mwf12 = 120._r8 ! molecular weight cfc12 |
---|
53 | real(r8), public, parameter :: mwo3 = 48._r8 ! molecular weight O3 |
---|
54 | real(r8), public, parameter :: mwso2 = 64._r8 |
---|
55 | real(r8), public, parameter :: mwso4 = 96._r8 |
---|
56 | real(r8), public, parameter :: mwh2o2 = 34._r8 |
---|
57 | real(r8), public, parameter :: mwdms = 62._r8 |
---|
58 | |
---|
59 | |
---|
60 | ! modifiable physical constants for aquaplanet |
---|
61 | |
---|
62 | real(r8), public :: gravit = shr_const_g ! gravitational acceleration (m/s**2) |
---|
63 | real(r8), public :: sday = shr_const_sday ! sec in siderial day ~ sec |
---|
64 | real(r8), public :: mwh2o = shr_const_mwwv ! molecular weight h2o |
---|
65 | real(r8), public :: cpwv = shr_const_cpwv ! specific heat of water vapor (J/K/kg) |
---|
66 | real(r8), public :: mwdry = shr_const_mwdair! molecular weight dry air |
---|
67 | real(r8), public :: rearth = shr_const_rearth! radius of earth (m) |
---|
68 | |
---|
69 | !--------------- Variables below here are derived from those above ----------------------- |
---|
70 | |
---|
71 | real(r8), public :: rga = 1._r8/shr_const_g ! reciprocal of gravit |
---|
72 | real(r8), public :: ra = 1._r8/shr_const_rearth ! reciprocal of earth radius |
---|
73 | real(r8), public :: omega = 2.0_R8*shr_const_pi/shr_const_sday! earth rot ~ rad/sec |
---|
74 | real(r8), public :: rh2o = shr_const_rgas/shr_const_mwwv ! Water vapor gas constant ~ J/K/kg |
---|
75 | real(r8), public :: rair = shr_const_rdair ! Dry air gas constant ~ J/K/kg |
---|
76 | real(r8), public :: epsilo = shr_const_mwwv/shr_const_mwdair ! ratio of h2o to dry air molecular weights |
---|
77 | real(r8), public :: zvir = (shr_const_rwv/shr_const_rdair)-1.0_R8 ! (rh2o/rair) - 1 |
---|
78 | real(r8), public :: cpvir = (shr_const_cpwv/shr_const_cpdair)-1.0_R8 ! CPWV/CPDAIR - 1.0 |
---|
79 | real(r8), public :: rhodair = shr_const_pstd/(shr_const_rdair*shr_const_tkfrz) |
---|
80 | real(r8), public :: cappa = (shr_const_rgas/shr_const_mwdair)/shr_const_cpdair ! R/Cp |
---|
81 | real(r8), public :: ez ! Coriolis expansion coeff -> omega/sqrt(0.375) |
---|
82 | real(r8), public :: Cpd_on_Cpv = shr_const_cpdair/shr_const_cpwv |
---|
83 | |
---|
84 | |
---|
85 | !================================================================================================ |
---|
86 | contains |
---|
87 | !================================================================================================ |
---|
88 | |
---|
89 | ! Read namelist variables. |
---|
90 | subroutine physconst_readnl(nlfile) |
---|
91 | #ifndef WRF_PORT |
---|
92 | use namelist_utils, only: find_group_name |
---|
93 | use units, only: getunit, freeunit |
---|
94 | use mpishorthand |
---|
95 | use spmd_utils, only: masterproc |
---|
96 | use abortutils, only: endrun |
---|
97 | use cam_logfile, only: iulog |
---|
98 | #endif |
---|
99 | character(len=*), intent(in) :: nlfile ! filepath for file containing namelist input |
---|
100 | #ifndef WRF_PORT |
---|
101 | ! Local variables |
---|
102 | integer :: unitn, ierr |
---|
103 | character(len=*), parameter :: subname = 'physconst_readnl' |
---|
104 | logical newg, newsday, newmwh2o, newcpwv, newmwdry, newrearth |
---|
105 | |
---|
106 | ! Physical constants needing to be reset (ie. for aqua planet experiments) |
---|
107 | namelist /physconst_nl/ cpwv, gravit, mwdry, mwh2o, rearth, sday |
---|
108 | |
---|
109 | !----------------------------------------------------------------------------- |
---|
110 | |
---|
111 | if (masterproc) then |
---|
112 | unitn = getunit() |
---|
113 | open( unitn, file=trim(nlfile), status='old' ) |
---|
114 | call find_group_name(unitn, 'physconst_nl', status=ierr) |
---|
115 | if (ierr == 0) then |
---|
116 | read(unitn, physconst_nl, iostat=ierr) |
---|
117 | if (ierr /= 0) then |
---|
118 | call endrun(subname // ':: ERROR reading namelist') |
---|
119 | end if |
---|
120 | end if |
---|
121 | close(unitn) |
---|
122 | call freeunit(unitn) |
---|
123 | end if |
---|
124 | |
---|
125 | #ifdef SPMD |
---|
126 | ! Broadcast namelist variables |
---|
127 | call mpibcast(cpwv, 1, mpir8, 0, mpicom) |
---|
128 | call mpibcast(gravit, 1, mpir8, 0, mpicom) |
---|
129 | call mpibcast(mwdry, 1, mpir8, 0, mpicom) |
---|
130 | call mpibcast(mwh2o, 1, mpir8, 0, mpicom) |
---|
131 | call mpibcast(rearth, 1, mpir8, 0, mpicom) |
---|
132 | call mpibcast(sday, 1, mpir8, 0, mpicom) |
---|
133 | #endif |
---|
134 | |
---|
135 | |
---|
136 | |
---|
137 | newg = gravit .ne. shr_const_g |
---|
138 | newsday = sday .ne. shr_const_sday |
---|
139 | newmwh2o = mwh2o .ne. shr_const_mwwv |
---|
140 | newcpwv = cpwv .ne. shr_const_cpwv |
---|
141 | newmwdry = mwdry .ne. shr_const_mwdair |
---|
142 | newrearth= rearth .ne. shr_const_rearth |
---|
143 | |
---|
144 | |
---|
145 | |
---|
146 | if (newg .or. newsday .or. newmwh2o .or. newcpwv .or. newmwdry .or. newrearth) then |
---|
147 | if (masterproc) then |
---|
148 | write(iulog,*)'****************************************************************************' |
---|
149 | write(iulog,*)'*** New Physical Constant Values set via namelist ***' |
---|
150 | write(iulog,*)'*** ***' |
---|
151 | write(iulog,*)'*** Physical Constant Old Value New Value ***' |
---|
152 | if (newg) write(iulog,*)'*** GRAVITY ',shr_const_g,gravit,'***' |
---|
153 | if (newsday) write(iulog,*)'*** SDAY ',shr_const_sday,sday,'***' |
---|
154 | if (newmwh2o) write(iulog,*)'*** MWH20 ',shr_const_mwwv,mwh2o,'***' |
---|
155 | if (newcpwv) write(iulog,*)'*** CPWV ',shr_const_cpwv,cpwv,'***' |
---|
156 | if (newmwdry) write(iulog,*)'*** MWDRY ',shr_const_mwdair,mwdry,'***' |
---|
157 | if (newrearth) write(iulog,*)'*** REARTH ',shr_const_rearth,rearth,'***' |
---|
158 | write(iulog,*)'****************************************************************************' |
---|
159 | end if |
---|
160 | rga = 1._r8/gravit |
---|
161 | ra = 1._r8/rearth |
---|
162 | omega = 2.0_R8*pi/sday |
---|
163 | cpvir = cpwv/cpair - 1._r8 |
---|
164 | epsilo = mwh2o/mwdry |
---|
165 | |
---|
166 | ! rair and rh2o have to be defined before any of the variables that use them |
---|
167 | |
---|
168 | rair = r_universal/mwdry |
---|
169 | rh2o = r_universal/mwh2o |
---|
170 | |
---|
171 | cappa = rair/cpair |
---|
172 | rhodair = pstd/(rair*tmelt) |
---|
173 | zvir = (rh2o/rair)-1.0_R8 |
---|
174 | ez = omega / sqrt(0.375_r8) |
---|
175 | Cpd_on_Cpv = cpair/cpwv |
---|
176 | |
---|
177 | else |
---|
178 | ez = omega / sqrt(0.375_r8) |
---|
179 | end if |
---|
180 | #endif |
---|
181 | end subroutine physconst_readnl |
---|
182 | |
---|
183 | end module physconst |
---|