New URL for NEMO forge!   http://forge.nemo-ocean.eu

Since March 2022 along with NEMO 4.2 release, the code development moved to a self-hosted GitLab.
This present forge is now archived and remained online for history.
sedchem.F90 in NEMO/branches/2019/dev_r11233_AGRIF-05_jchanut_vert_coord_interp/src/TOP/PISCES/SED – NEMO

source: NEMO/branches/2019/dev_r11233_AGRIF-05_jchanut_vert_coord_interp/src/TOP/PISCES/SED/sedchem.F90 @ 11610

Last change on this file since 11610 was 11610, checked in by jchanut, 5 years ago

#2222, fixes to enable compiling AGRIF with TOP

  • Property svn:keywords set to Id
File size: 31.9 KB
Line 
1MODULE sedchem
2
3   !!======================================================================
4   !!                        ***  Module sedchem  ***
5   !! sediment :   Variable for chemistry of the CO2 cycle
6   !!======================================================================
7   !!   modules used
8   USE sed     ! sediment global variable
9   USE sedarr
10   USE eosbn2, ONLY : neos
11   USE lib_mpp         ! distribued memory computing library
12   USE par_sed
13
14   IMPLICIT NONE
15   PRIVATE
16
17   !! * Accessibility
18   PUBLIC sed_chem
19   PUBLIC ahini_for_at_sed     !
20   PUBLIC solve_at_general_sed !
21
22   ! Maximum number of iterations for each method
23   INTEGER, PARAMETER :: jp_maxniter_atgen    = 20
24   REAL(wp), PARAMETER :: pp_rdel_ah_target = 1.E-4_wp
25
26   !! * Module variables
27   REAL(wp) :: &
28      calcon = 1.03E-2        ! mean calcite concentration [Ca2+] in sea water [mole/kg solution]
29
30   REAL(wp) ::   rgas   = 83.14472      ! universal gas constants
31
32   ! coeff. for density of sea water (Millero & Poisson 1981)
33   REAL(wp), DIMENSION(5)  :: Adsw                       
34   DATA Adsw/8.24493E-1, -4.0899E-3, 7.6438E-5 , -8.246E-7, 5.3875E-9 /
35
36   REAL(wp), DIMENSION(3)  :: Bdsw 
37   DATA Bdsw / -5.72466E-3, 1.0227E-4, -1.6546E-6 /
38
39   REAL(wp)  :: Cdsw = 4.8314E-4
40
41   REAL(wp), DIMENSION(6)  :: Ddsw                   
42   DATA Ddsw / 999.842594 , 6.793952E-2 , -9.095290E-3, 1.001685E-4, -1.120083E-6, 6.536332E-9/
43
44  REAL(wp) :: devk10  = -25.5
45   REAL(wp) :: devk11  = -15.82
46   REAL(wp) :: devk12  = -29.48
47   REAL(wp) :: devk13  = -20.02
48   REAL(wp) :: devk14  = -18.03
49   REAL(wp) :: devk15  = -9.78
50   REAL(wp) :: devk16  = -48.76
51   REAL(wp) :: devk17  = -14.51
52   REAL(wp) :: devk18  = -23.12
53   REAL(wp) :: devk19  = -26.57
54   REAL(wp) :: devk110  = -29.48
55   !
56   REAL(wp) :: devk20  = 0.1271
57   REAL(wp) :: devk21  = -0.0219
58   REAL(wp) :: devk22  = 0.1622
59   REAL(wp) :: devk23  = 0.1119
60   REAL(wp) :: devk24  = 0.0466
61   REAL(wp) :: devk25  = -0.0090
62   REAL(wp) :: devk26  = 0.5304
63   REAL(wp) :: devk27  = 0.1211
64   REAL(wp) :: devk28  = 0.1758
65   REAL(wp) :: devk29  = 0.2020
66   REAL(wp) :: devk210  = 0.1622
67   !
68   REAL(wp) :: devk30  = 0.
69   REAL(wp) :: devk31  = 0.
70   REAL(wp) :: devk32  = 2.608E-3
71   REAL(wp) :: devk33  = -1.409e-3
72   REAL(wp) :: devk34  = 0.316e-3
73   REAL(wp) :: devk35  = -0.942e-3
74   REAL(wp) :: devk36  = 0.
75   REAL(wp) :: devk37  = -0.321e-3
76   REAL(wp) :: devk38  = -2.647e-3
77   REAL(wp) :: devk39  = -3.042e-3
78   REAL(wp) :: devk310  = -2.6080e-3
79   !
80   REAL(wp) :: devk40  = -3.08E-3
81   REAL(wp) :: devk41  = 1.13E-3
82   REAL(wp) :: devk42  = -2.84E-3
83   REAL(wp) :: devk43  = -5.13E-3
84   REAL(wp) :: devk44  = -4.53e-3
85   REAL(wp) :: devk45  = -3.91e-3
86   REAL(wp) :: devk46  = -11.76e-3
87   REAL(wp) :: devk47  = -2.67e-3
88   REAL(wp) :: devk48  = -5.15e-3
89   REAL(wp) :: devk49  = -4.08e-3
90   REAL(wp) :: devk410  = -2.84e-3
91   !
92   REAL(wp) :: devk50  = 0.0877E-3
93   REAL(wp) :: devk51  = -0.1475E-3
94   REAL(wp) :: devk52  = 0.
95   REAL(wp) :: devk53  = 0.0794E-3
96   REAL(wp) :: devk54  = 0.09e-3
97   REAL(wp) :: devk55  = 0.054e-3
98   REAL(wp) :: devk56  = 0.3692E-3
99   REAL(wp) :: devk57  = 0.0427e-3
100   REAL(wp) :: devk58  = 0.09e-3
101   REAL(wp) :: devk59  = 0.0714e-3
102   REAL(wp) :: devk510  = 0.0
103
104   !! $Id$
105CONTAINS
106
107   SUBROUTINE sed_chem( kt )
108      !!----------------------------------------------------------------------
109      !!                   ***  ROUTINE sed_chem  ***
110      !!
111      !! ** Purpose :   set chemical constants
112      !!
113      !!   History :
114      !!        !  04-10  (N. Emprin, M. Gehlen )  Original code
115      !!        !  06-04  (C. Ethe)  Re-organization
116      !!----------------------------------------------------------------------
117      !!* Arguments
118      INTEGER, INTENT(in) :: kt                     ! time step
119
120      INTEGER  :: ji, jj, ikt
121      REAL(wp) :: ztc, ztc2
122      REAL(wp) :: zsal, zsal15 
123      REAL(wp) :: zdens0, zaw, zbw, zcw   
124      REAL(wp), DIMENSION(jpi,jpj,15) ::   zchem_data
125      !!----------------------------------------------------------------------
126
127
128      IF( ln_timing )  CALL timing_start('sed_chem')
129
130      IF (lwp) WRITE(numsed,*) ' Getting Chemical constants from tracer model at time kt = ', kt
131      IF (lwp) WRITE(numsed,*) ' '
132
133      ! reading variables
134      zchem_data(:,:,:) = rtrn
135
136      IF (ln_sediment_offline) THEN
137         CALL sed_chem_cst
138      ELSE
139         DO jj = 1,jpj
140            DO ji = 1, jpi
141               ikt = mbkt(ji,jj) 
142               IF ( tmask(ji,jj,ikt) == 1 ) THEN
143                  zchem_data(ji,jj,1) = ak13  (ji,jj,ikt)
144                  zchem_data(ji,jj,2) = ak23  (ji,jj,ikt)
145                  zchem_data(ji,jj,3) = akb3  (ji,jj,ikt)
146                  zchem_data(ji,jj,4) = akw3  (ji,jj,ikt)
147                  zchem_data(ji,jj,5) = aksp  (ji,jj,ikt)
148                  zchem_data(ji,jj,6) = borat (ji,jj,ikt)
149                  zchem_data(ji,jj,7) = ak1p3 (ji,jj,ikt)
150                  zchem_data(ji,jj,8) = ak2p3 (ji,jj,ikt)
151                  zchem_data(ji,jj,9) = ak3p3 (ji,jj,ikt)
152                  zchem_data(ji,jj,10)= aksi3 (ji,jj,ikt)
153                  zchem_data(ji,jj,11)= sio3eq(ji,jj,ikt)
154                  zchem_data(ji,jj,12)= aks3  (ji,jj,ikt)
155                  zchem_data(ji,jj,13)= akf3  (ji,jj,ikt)
156                  zchem_data(ji,jj,14)= sulfat(ji,jj,ikt)
157                  zchem_data(ji,jj,15)= fluorid(ji,jj,ikt)
158               ENDIF
159            ENDDO
160         ENDDO
161
162         CALL pack_arr ( jpoce, ak1s  (1:jpoce), zchem_data(1:jpi,1:jpj,1) , iarroce(1:jpoce) )
163         CALL pack_arr ( jpoce, ak2s  (1:jpoce), zchem_data(1:jpi,1:jpj,2) , iarroce(1:jpoce) )
164         CALL pack_arr ( jpoce, akbs  (1:jpoce), zchem_data(1:jpi,1:jpj,3) , iarroce(1:jpoce) )
165         CALL pack_arr ( jpoce, akws  (1:jpoce), zchem_data(1:jpi,1:jpj,4) , iarroce(1:jpoce) )
166         CALL pack_arr ( jpoce, aksps (1:jpoce), zchem_data(1:jpi,1:jpj,5) , iarroce(1:jpoce) )
167         CALL pack_arr ( jpoce, borats(1:jpoce), zchem_data(1:jpi,1:jpj,6) , iarroce(1:jpoce) )
168         CALL pack_arr ( jpoce, ak1ps (1:jpoce), zchem_data(1:jpi,1:jpj,7) , iarroce(1:jpoce) )
169         CALL pack_arr ( jpoce, ak2ps (1:jpoce), zchem_data(1:jpi,1:jpj,8) , iarroce(1:jpoce) )
170         CALL pack_arr ( jpoce, ak3ps (1:jpoce), zchem_data(1:jpi,1:jpj,9) , iarroce(1:jpoce) )
171         CALL pack_arr ( jpoce, aksis (1:jpoce), zchem_data(1:jpi,1:jpj,10), iarroce(1:jpoce) )
172         CALL pack_arr ( jpoce, sieqs (1:jpoce), zchem_data(1:jpi,1:jpj,11), iarroce(1:jpoce) )
173         CALL pack_arr ( jpoce, aks3s (1:jpoce), zchem_data(1:jpi,1:jpj,12), iarroce(1:jpoce) )
174         CALL pack_arr ( jpoce, akf3s (1:jpoce), zchem_data(1:jpi,1:jpj,13), iarroce(1:jpoce) )
175         CALL pack_arr ( jpoce, sulfats(1:jpoce), zchem_data(1:jpi,1:jpj,14), iarroce(1:jpoce) )
176         CALL pack_arr ( jpoce, fluorids(1:jpoce), zchem_data(1:jpi,1:jpj,15), iarroce(1:jpoce) )
177      ENDIF
178
179      DO ji = 1, jpoce
180         ztc     = temp(ji)
181         ztc2    = ztc * ztc
182         ! zqtt    = ztkel * 0.01
183         zsal    = salt(ji)
184         zsal15  = SQRT( zsal ) * zsal
185
186         ! Density of Sea Water - F(temp,sal) [kg/m3]
187         zdens0 =  Ddsw(1) + Ddsw(2) * ztc + Ddsw(3) * ztc2 &
188                  + Ddsw(4) * ztc * ztc2 + Ddsw(5) * ztc2 * ztc2 &
189                  + Ddsw(6) * ztc * ztc2 * ztc2
190         zaw =  Adsw(1) + Adsw(2) * ztc + Adsw(3)* ztc2 + Adsw(4) * ztc * ztc2 &
191              + Adsw(5) * ztc2 * ztc2
192         zbw =  Bdsw(1) + Bdsw(2) * ztc + Bdsw(3) * ztc2
193         zcw =  Cdsw
194         densSW(ji) = zdens0 + zaw * zsal + zbw * zsal15 + zcw * zsal * zsal
195         densSW(ji) = densSW(ji) * 1E-3   ! to get dens in [kg/l]
196
197         ak12s  (ji) = ak1s (ji) * ak2s (ji)
198         ak12ps (ji) = ak1ps(ji) * ak2ps(ji)
199         ak123ps(ji) = ak1ps(ji) * ak2ps(ji) * ak3ps(ji)
200
201         calcon2(ji) = 0.01028 * ( salt(ji) / 35. ) * densSW(ji)
202      ENDDO
203       
204      IF( ln_timing )  CALL timing_stop('sed_chem')
205
206   END SUBROUTINE sed_chem
207
208   SUBROUTINE ahini_for_at_sed(p_hini)
209      !!---------------------------------------------------------------------
210      !!                     ***  ROUTINE ahini_for_at  ***
211      !!
212      !! Subroutine returns the root for the 2nd order approximation of the
213      !! DIC -- B_T -- A_CB equation for [H+] (reformulated as a cubic
214      !! polynomial) around the local minimum, if it exists.
215      !! Returns * 1E-03_wp if p_alkcb <= 0
216      !!         * 1E-10_wp if p_alkcb >= 2*p_dictot + p_bortot
217      !!         * 1E-07_wp if 0 < p_alkcb < 2*p_dictot + p_bortot
218      !!                    and the 2nd order approximation does not have
219      !!                    a solution
220      !!---------------------------------------------------------------------
221      REAL(wp), DIMENSION(jpoce,jpksed), INTENT(OUT)  ::  p_hini
222      INTEGER  ::   ji, jk
223      REAL(wp)  ::  zca1, zba1
224      REAL(wp)  ::  zd, zsqrtd, zhmin
225      REAL(wp)  ::  za2, za1, za0
226      REAL(wp)  ::  p_dictot, p_bortot, p_alkcb
227
228      IF( ln_timing )  CALL timing_start('ahini_for_at_sed')
229      !
230      DO jk = 1, jpksed
231         DO ji = 1, jpoce
232            p_alkcb  = pwcp(ji,jk,jwalk) / densSW(ji)
233            p_dictot = pwcp(ji,jk,jwdic) / densSW(ji) 
234            p_bortot = borats(ji) / densSW(ji)
235            IF (p_alkcb <= 0.) THEN
236                p_hini(ji,jk) = 1.e-3
237            ELSEIF (p_alkcb >= (2.*p_dictot + p_bortot)) THEN
238                p_hini(ji,jk) = 1.e-10_wp
239            ELSE
240                zca1 = p_dictot/( p_alkcb + rtrn )
241                zba1 = p_bortot/ (p_alkcb + rtrn )
242           ! Coefficients of the cubic polynomial
243                za2 = aKbs(ji)*(1. - zba1) + ak1s(ji)*(1.-zca1)
244                za1 = ak1s(ji)*akbs(ji)*(1. - zba1 - zca1)    &
245                &     + ak1s(ji)*ak2s(ji)*(1. - (zca1+zca1))
246                za0 = ak1s(ji)*ak2s(ji)*akbs(ji)*(1. - zba1 - (zca1+zca1))
247                                        ! Taylor expansion around the minimum
248                zd = za2*za2 - 3.*za1   ! Discriminant of the quadratic equation
249                                        ! for the minimum close to the root
250
251                IF(zd > 0.) THEN        ! If the discriminant is positive
252                  zsqrtd = SQRT(zd)
253                  IF(za2 < 0) THEN
254                    zhmin = (-za2 + zsqrtd)/3.
255                  ELSE
256                    zhmin = -za1/(za2 + zsqrtd)
257                  ENDIF
258                  p_hini(ji,jk) = zhmin + SQRT(-(za0 + zhmin*(za1 + zhmin*(za2 + zhmin)))/zsqrtd)
259                ELSE
260                  p_hini(ji,jk) = 1.e-7
261                ENDIF
262             !
263            ENDIF
264         END DO
265      END DO
266      !
267      IF( ln_timing )  CALL timing_stop('ahini_for_at_sed')
268      !
269   END SUBROUTINE ahini_for_at_sed
270
271   !===============================================================================
272   SUBROUTINE anw_infsup_sed( p_alknw_inf, p_alknw_sup )
273
274   ! Subroutine returns the lower and upper bounds of "non-water-selfionization"
275   ! contributions to total alkalinity (the infimum and the supremum), i.e
276   ! inf(TA - [OH-] + [H+]) and sup(TA - [OH-] + [H+])
277
278   ! Argument variables
279   INTEGER :: jk
280   REAL(wp), DIMENSION(jpoce,jpksed), INTENT(OUT) :: p_alknw_inf
281   REAL(wp), DIMENSION(jpoce,jpksed), INTENT(OUT) :: p_alknw_sup
282
283   DO jk = 1, jpksed
284      p_alknw_inf(:,jk) =  -pwcp(:,jk,jwpo4) / densSW(:)
285      p_alknw_sup(:,jk) =   (2. * pwcp(:,jk,jwdic) + 2. * pwcp(:,jk,jwpo4) + pwcp(:,jk,jwsil)     &
286   &                        + borats(:) ) / densSW(:)
287   END DO
288
289   END SUBROUTINE anw_infsup_sed
290
291
292   SUBROUTINE solve_at_general_sed( p_hini, zhi )
293
294   ! Universal pH solver that converges from any given initial value,
295   ! determines upper an lower bounds for the solution if required
296
297   ! Argument variables
298   !--------------------
299   REAL(wp), DIMENSION(jpoce,jpksed), INTENT(IN)   :: p_hini
300   REAL(wp), DIMENSION(jpoce,jpksed), INTENT(OUT)  :: zhi
301
302   ! Local variables
303   !-----------------
304   INTEGER   ::  ji, jk, jn
305   REAL(wp)  ::  zh_ini, zh, zh_prev, zh_lnfactor
306   REAL(wp)  ::  zdelta, zh_delta
307   REAL(wp)  ::  zeqn, zdeqndh, zalka
308   REAL(wp)  ::  aphscale
309   REAL(wp)  ::  znumer_dic, zdnumer_dic, zdenom_dic, zalk_dic, zdalk_dic
310   REAL(wp)  ::  znumer_bor, zdnumer_bor, zdenom_bor, zalk_bor, zdalk_bor
311   REAL(wp)  ::  znumer_po4, zdnumer_po4, zdenom_po4, zalk_po4, zdalk_po4
312   REAL(wp)  ::  znumer_sil, zdnumer_sil, zdenom_sil, zalk_sil, zdalk_sil
313   REAL(wp)  ::  znumer_so4, zdnumer_so4, zdenom_so4, zalk_so4, zdalk_so4
314   REAL(wp)  ::  znumer_flu, zdnumer_flu, zdenom_flu, zalk_flu, zdalk_flu
315   REAL(wp)  ::  zalk_wat, zdalk_wat
316   REAL(wp)  ::  zfact, p_alktot, zdic, zbot, zpt, zst, zft, zsit
317   LOGICAL   ::  l_exitnow
318   REAL(wp), PARAMETER :: pz_exp_threshold = 1.0
319   REAL(wp), DIMENSION(jpoce,jpksed) :: zalknw_inf, zalknw_sup, rmask, zh_min, zh_max, zeqn_absmin
320
321   IF( ln_timing )  CALL timing_start('solve_at_general_sed')
322      !  Allocate temporary workspace
323   CALL anw_infsup_sed( zalknw_inf, zalknw_sup )
324
325   rmask(:,:) = 1.0
326   zhi(:,:)   = 0.
327
328   ! TOTAL H+ scale: conversion factor for Htot = aphscale * Hfree
329   DO jk = 1, jpksed
330      DO ji = 1, jpoce
331         IF (rmask(ji,jk) == 1.) THEN
332            p_alktot = pwcp(ji,jk,jwalk) / densSW(ji)
333            aphscale = 1. + sulfats(ji)/aks3s(ji)
334            zh_ini = p_hini(ji,jk)
335
336            zdelta = (p_alktot-zalknw_inf(ji,jk))**2 + 4.*akws(ji) / aphscale
337
338            IF(p_alktot >= zalknw_inf(ji,jk)) THEN
339               zh_min(ji,jk) = 2.*akws(ji) /( p_alktot-zalknw_inf(ji,jk) + SQRT(zdelta) )
340            ELSE
341               zh_min(ji,jk) = aphscale * (-(p_alktot-zalknw_inf(ji,jk)) + SQRT(zdelta) ) / 2.
342            ENDIF
343
344            zdelta = (p_alktot-zalknw_sup(ji,jk))**2 + 4.*akws(ji) / aphscale
345
346            IF(p_alktot <= zalknw_sup(ji,jk)) THEN
347               zh_max(ji,jk) = aphscale * (-(p_alktot-zalknw_sup(ji,jk)) + SQRT(zdelta) ) / 2.
348            ELSE
349               zh_max(ji,jk) = 2.*akws(ji) /( p_alktot-zalknw_sup(ji,jk) + SQRT(zdelta) )
350            ENDIF
351
352            zhi(ji,jk) = MAX(MIN(zh_max(ji,jk), zh_ini), zh_min(ji,jk))
353         ENDIF
354      END DO
355   END DO
356
357   zeqn_absmin(:,:) = HUGE(1._wp)
358
359   DO jn = 1, jp_maxniter_atgen
360   DO jk = 1, jpksed
361      DO ji = 1, jpoce
362         IF (rmask(ji,jk) == 1.) THEN
363
364            p_alktot = pwcp(ji,jk,jwalk) / densSW(ji)
365            zdic  = pwcp(ji,jk,jwdic) / densSW(ji)
366            zbot  = borats(ji) / densSW(ji)
367            zpt =  pwcp(ji,jk,jwpo4) / densSW(ji)
368            zsit = pwcp(ji,jk,jwsil) / densSW(ji)
369            zst = sulfats(ji)
370            zft = fluorids(ji)
371            aphscale = 1. + sulfats(ji)/aks3s(ji)
372            zh = zhi(ji,jk)
373            zh_prev = zh
374
375            ! H2CO3 - HCO3 - CO3 : n=2, m=0
376            znumer_dic = 2.*ak1s(ji)*ak2s(ji) + zh*ak1s(ji)
377            zdenom_dic = ak1s(ji)*ak2s(ji) + zh*(ak1s(ji) + zh)
378            zalk_dic   = zdic * (znumer_dic/zdenom_dic)
379            zdnumer_dic = ak1s(ji)*ak1s(ji)*ak2s(ji) + zh     &
380                          *(4.*ak1s(ji)*ak2s(ji) + zh*ak1s(ji))
381            zdalk_dic   = -zdic*(zdnumer_dic/zdenom_dic**2)
382
383
384            ! B(OH)3 - B(OH)4 : n=1, m=0
385            znumer_bor = akbs(ji)
386            zdenom_bor = akbs(ji) + zh
387            zalk_bor   = zbot * (znumer_bor/zdenom_bor)
388            zdnumer_bor = akbs(ji)
389            zdalk_bor   = -zbot*(zdnumer_bor/zdenom_bor**2)
390
391
392            ! H3PO4 - H2PO4 - HPO4 - PO4 : n=3, m=1
393            znumer_po4 = 3.*ak1ps(ji)*ak2ps(ji)*ak3ps(ji)  &
394            &            + zh*(2.*ak1ps(ji)*ak2ps(ji) + zh* ak1ps(ji))
395            zdenom_po4 = ak1ps(ji)*ak2ps(ji)*ak3ps(ji)     &
396            &            + zh*( ak1ps(ji)*ak2ps(ji) + zh*(ak1ps(ji) + zh))
397            zalk_po4   = zpt * (znumer_po4/zdenom_po4 - 1.) ! Zero level of H3PO4 = 1
398            zdnumer_po4 = ak1ps(ji)*ak2ps(ji)*ak1ps(ji)*ak2ps(ji)*ak3ps(ji)  &
399            &             + zh*(4.*ak1ps(ji)*ak1ps(ji)*ak2ps(ji)*ak3ps(ji)         &
400            &             + zh*(9.*ak1ps(ji)*ak2ps(ji)*ak3ps(ji)                         &
401            &             + ak1ps(ji)*ak1ps(ji)*ak2ps(ji)                                &
402            &             + zh*(4.*ak1ps(ji)*ak2ps(ji) + zh * ak1ps(ji) ) ) )
403            zdalk_po4   = -zpt * (zdnumer_po4/zdenom_po4**2)
404
405            ! H4SiO4 - H3SiO4 : n=1, m=0
406            znumer_sil = aksis(ji)
407            zdenom_sil = aksis(ji) + zh
408            zalk_sil   = zsit * (znumer_sil/zdenom_sil)
409            zdnumer_sil = aksis(ji)
410            zdalk_sil   = -zsit * (zdnumer_sil/zdenom_sil**2)
411
412            ! HSO4 - SO4 : n=1, m=1
413            aphscale = 1.0 + zst/aks3s(ji)
414            znumer_so4 = aks3s(ji) * aphscale
415            zdenom_so4 = aks3s(ji) * aphscale + zh
416            zalk_so4   = zst * (znumer_so4/zdenom_so4 - 1.)
417            zdnumer_so4 = aks3s(ji) * aphscale
418            zdalk_so4   = -zst * (zdnumer_so4/zdenom_so4**2)
419
420            ! HF - F : n=1, m=1
421            znumer_flu =  akf3s(ji)
422            zdenom_flu =  akf3s(ji) + zh
423            zalk_flu   =  zft * (znumer_flu/zdenom_flu - 1.)
424            zdnumer_flu = akf3s(ji)
425            zdalk_flu   = -zft * (zdnumer_flu/zdenom_flu**2)
426
427            ! H2O - OH
428            zalk_wat   = akws(ji)/zh - zh/aphscale
429            zdalk_wat  = -akws(ji)/zh**2 - 1./aphscale
430
431            ! CALCULATE [ALK]([CO3--], [HCO3-])
432            zeqn = zalk_dic + zalk_bor + zalk_po4 + zalk_sil   &
433            &      + zalk_so4 + zalk_flu                       &
434            &      + zalk_wat - p_alktot
435
436            zalka = p_alktot - (zalk_bor + zalk_po4 + zalk_sil   &
437            &       + zalk_so4 + zalk_flu + zalk_wat)
438
439            zdeqndh = zdalk_dic + zdalk_bor + zdalk_po4 + zdalk_sil &
440            &         + zdalk_so4 + zdalk_flu + zdalk_wat
441
442            ! Adapt bracketing interval
443            IF(zeqn > 0._wp) THEN
444               zh_min(ji,jk) = zh_prev
445            ELSEIF(zeqn < 0._wp) THEN
446               zh_max(ji,jk) = zh_prev
447            ENDIF
448
449            IF(ABS(zeqn) >= 0.5_wp*zeqn_absmin(ji,jk)) THEN
450            ! if the function evaluation at the current point is
451            ! not decreasing faster than with a bisection step (at least linearly)
452            ! in absolute value take one bisection step on [ph_min, ph_max]
453            ! ph_new = (ph_min + ph_max)/2d0
454            !
455            ! In terms of [H]_new:
456            ! [H]_new = 10**(-ph_new)
457            !         = 10**(-(ph_min + ph_max)/2d0)
458            !         = SQRT(10**(-(ph_min + phmax)))
459            !         = SQRT(zh_max * zh_min)
460               zh = SQRT(zh_max(ji,jk) * zh_min(ji,jk))
461               zh_lnfactor = (zh - zh_prev)/zh_prev ! Required to test convergence below
462            ELSE
463            ! dzeqn/dpH = dzeqn/d[H] * d[H]/dpH
464            !           = -zdeqndh * LOG(10) * [H]
465            ! \Delta pH = -zeqn/(zdeqndh*d[H]/dpH) = zeqn/(zdeqndh*[H]*LOG(10))
466            !
467            ! pH_new = pH_old + \deltapH
468            !
469            ! [H]_new = 10**(-pH_new)
470            !         = 10**(-pH_old - \Delta pH)
471            !         = [H]_old * 10**(-zeqn/(zdeqndh*[H]_old*LOG(10)))
472            !         = [H]_old * EXP(-LOG(10)*zeqn/(zdeqndh*[H]_old*LOG(10)))
473            !         = [H]_old * EXP(-zeqn/(zdeqndh*[H]_old))
474
475               zh_lnfactor = -zeqn/(zdeqndh*zh_prev)
476
477               IF(ABS(zh_lnfactor) > pz_exp_threshold) THEN
478                  zh          = zh_prev*EXP(zh_lnfactor)
479               ELSE
480                  zh_delta    = zh_lnfactor*zh_prev
481                  zh          = zh_prev + zh_delta
482               ENDIF
483
484               IF( zh < zh_min(ji,jk) ) THEN
485               ! if [H]_new < [H]_min
486               ! i.e., if ph_new > ph_max then
487               ! take one bisection step on [ph_prev, ph_max]
488               ! ph_new = (ph_prev + ph_max)/2d0
489               ! In terms of [H]_new:
490               ! [H]_new = 10**(-ph_new)
491               !         = 10**(-(ph_prev + ph_max)/2d0)
492               !         = SQRT(10**(-(ph_prev + phmax)))
493               !         = SQRT([H]_old*10**(-ph_max))
494               !         = SQRT([H]_old * zh_min)
495                  zh                = SQRT(zh_prev * zh_min(ji,jk))
496                  zh_lnfactor       = (zh - zh_prev)/zh_prev ! Required to test convergence below
497               ENDIF
498
499               IF( zh > zh_max(ji,jk) ) THEN
500               ! if [H]_new > [H]_max
501               ! i.e., if ph_new < ph_min, then
502               ! take one bisection step on [ph_min, ph_prev]
503               ! ph_new = (ph_prev + ph_min)/2d0
504               ! In terms of [H]_new:
505               ! [H]_new = 10**(-ph_new)
506               !         = 10**(-(ph_prev + ph_min)/2d0)
507               !         = SQRT(10**(-(ph_prev + ph_min)))
508               !         = SQRT([H]_old*10**(-ph_min))
509               !         = SQRT([H]_old * zhmax)
510                  zh                = SQRT(zh_prev * zh_max(ji,jk))
511                  zh_lnfactor       = (zh - zh_prev)/zh_prev ! Required to test convergence below
512               ENDIF
513            ENDIF
514
515            zeqn_absmin(ji,jk) = MIN( ABS(zeqn), zeqn_absmin(ji,jk))
516
517            ! Stop iterations once |\delta{[H]}/[H]| < rdel
518            ! <=> |(zh - zh_prev)/zh_prev| = |EXP(-zeqn/(zdeqndh*zh_prev)) -1| < rdel
519            ! |EXP(-zeqn/(zdeqndh*zh_prev)) -1| ~ |zeqn/(zdeqndh*zh_prev)|
520            ! Alternatively:
521            ! |\Delta pH| = |zeqn/(zdeqndh*zh_prev*LOG(10))|
522            !             ~ 1/LOG(10) * |\Delta [H]|/[H]
523            !             < 1/LOG(10) * rdel
524
525            ! Hence |zeqn/(zdeqndh*zh)| < rdel
526
527            ! rdel <-- pp_rdel_ah_target
528            l_exitnow = (ABS(zh_lnfactor) < pp_rdel_ah_target)
529
530            IF(l_exitnow) THEN
531               rmask(ji,jk) = 0.
532            ENDIF
533
534            zhi(ji,jk) =  zh
535
536            IF(jn >= jp_maxniter_atgen) THEN
537               zhi(ji,jk) = -1._wp
538            ENDIF
539
540         ENDIF
541      END DO
542   END DO
543   END DO
544   !
545   IF( ln_timing )  CALL timing_stop('solve_at_general_sed')
546
547   END SUBROUTINE solve_at_general_sed
548
549   SUBROUTINE sed_chem_cst
550      !!---------------------------------------------------------------------
551      !!                     ***  ROUTINE sed_chem_cst  ***
552      !!
553      !! ** Purpose :   Sea water chemistry computed following MOCSY protocol
554      !!                Computation is done at the bottom of the ocean only
555      !!
556      !! ** Method  : - ...
557      !!---------------------------------------------------------------------
558      INTEGER  ::   ji
559      REAL(wp), DIMENSION(jpoce) :: saltprac, temps
560      REAL(wp) ::   ztkel, ztkel1, zt , zsal  , zsal2 , zbuf1 , zbuf2
561      REAL(wp) ::   ztgg , ztgg2, ztgg3 , ztgg4 , ztgg5
562      REAL(wp) ::   zpres, ztc  , zcl   , zcpexp, zoxy  , zcpexp2
563      REAL(wp) ::   zsqrt, ztr  , zlogt , zcek1, zc1, zplat
564      REAL(wp) ::   zis  , zis2 , zsal15, zisqrt, za1, za2
565      REAL(wp) ::   zckb , zck1 , zck2  , zckw  , zak1 , zak2  , zakb , zaksp0, zakw
566      REAL(wp) ::   zck1p, zck2p, zck3p, zcksi, zak1p, zak2p, zak3p, zaksi
567      REAL(wp) ::   zst  , zft  , zcks  , zckf  , zaksp1
568      REAL(wp) ::   total2free, free2SWS, total2SWS, SWS2total
569      !!---------------------------------------------------------------------
570      !
571      IF( ln_timing )   CALL timing_start('sed_chem_cst')
572      !
573      ! Computation of chemical constants require practical salinity
574      ! Thus, when TEOS08 is used, absolute salinity is converted to
575      ! practical salinity
576      ! -------------------------------------------------------------
577      IF (neos == -1) THEN
578         saltprac(:) = salt(:) * 35.0 / 35.16504
579      ELSE
580         saltprac(:) = temp(:)
581      ENDIF
582
583      !
584      ! Computations of chemical constants require in situ temperature
585      ! Here a quite simple formulation is used to convert
586      ! potential temperature to in situ temperature. The errors is less than
587      ! 0.04°C relative to an exact computation
588      ! ---------------------------------------------------------------------
589         DO ji = 1, jpoce
590            zpres = zkbot(ji) / 1000.
591            za1 = 0.04 * ( 1.0 + 0.185 * temp(ji) + 0.035 * (saltprac(ji) - 35.0) )
592            za2 = 0.0075 * ( 1.0 - temp(ji) / 30.0 )
593            temps(ji) = temp(ji) - za1 * zpres + za2 * zpres**2
594         END DO
595
596      ! CHEMICAL CONSTANTS - DEEP OCEAN
597      ! -------------------------------
598      DO ji = 1, jpoce
599         ! SET PRESSION ACCORDING TO SAUNDER (1980)
600         zc1 = 5.92E-3 
601         zpres = ((1-zc1)-SQRT(((1-zc1)**2)-(8.84E-6*zkbot(ji)))) / 4.42E-6
602         zpres = zpres / 10.0
603
604         ! SET ABSOLUTE TEMPERATURE
605         ztkel   = temps(ji) + 273.15
606         zsal    = saltprac(ji)
607         zsqrt  = SQRT( zsal )
608         zsal15  = zsqrt * zsal
609         zlogt  = LOG( ztkel )
610         ztr    = 1. / ztkel
611         zis    = 19.924 * zsal / ( 1000.- 1.005 * zsal )
612         zis2   = zis * zis
613         zisqrt = SQRT( zis )
614         ztc    = temps(ji)
615
616         ! CHLORINITY (WOOSTER ET AL., 1969)
617         zcl     = zsal / 1.80655
618
619         ! TOTAL SULFATE CONCENTR. [MOLES/kg soln]
620         zst     = 0.14 * zcl /96.062
621
622         ! TOTAL FLUORIDE CONCENTR. [MOLES/kg soln]
623         zft     = 0.000067 * zcl /18.9984
624
625         ! DISSOCIATION CONSTANT FOR SULFATES on free H scale (Dickson 1990)
626         zcks    = EXP(-4276.1 * ztr + 141.328 - 23.093 * zlogt         &
627         &         + (-13856. * ztr + 324.57 - 47.986 * zlogt) * zisqrt &
628         &         + (35474. * ztr - 771.54 + 114.723 * zlogt) * zis    &
629         &         - 2698. * ztr * zis**1.5 + 1776.* ztr * zis2         &
630         &         + LOG(1.0 - 0.001005 * zsal))
631
632         ! DISSOCIATION CONSTANT FOR FLUORIDES on free H scale (Dickson and Riley 79)
633         zckf    = EXP( 1590.2*ztr - 12.641 + 1.525*zisqrt   &
634         &         + LOG(1.0d0 - 0.001005d0*zsal)            &
635         &         + LOG(1.0d0 + zst/zcks))
636
637         ! DISSOCIATION CONSTANT FOR CARBONATE AND BORATE
638         zckb=  (-8966.90 - 2890.53*zsqrt - 77.942*zsal        &
639         &      + 1.728*zsal15 - 0.0996*zsal*zsal)*ztr         &
640         &      + (148.0248 + 137.1942*zsqrt + 1.62142*zsal)   &
641         &      + (-24.4344 - 25.085*zsqrt - 0.2474*zsal)      &
642         &      * zlogt + 0.053105*zsqrt*ztkel
643
644         ! DISSOCIATION COEFFICIENT FOR CARBONATE ACCORDING TO
645         ! MEHRBACH (1973) REFIT BY MILLERO (1995), seawater scale
646         zck1    = -1.0*(3633.86*ztr - 61.2172 + 9.6777*zlogt  &
647                   - 0.011555*zsal + 0.0001152*zsal*zsal)
648         zck2    = -1.0*(471.78*ztr + 25.9290 - 3.16967*zlogt      &
649                   - 0.01781*zsal + 0.0001122*zsal*zsal)
650
651         ! PKW (H2O) (MILLERO, 1995) from composite data
652         zckw    = -13847.26 * ztr + 148.9652 - 23.6521 * zlogt + ( 118.67 * ztr    &
653                   - 5.977 + 1.0495 * zlogt ) * zsqrt - 0.01615 * zsal
654
655         ! CONSTANTS FOR PHOSPHATE (MILLERO, 1995)
656         zck1p    = -4576.752*ztr + 115.540 - 18.453*zlogt   &
657         &          + (-106.736*ztr + 0.69171) * zsqrt       &
658         &          + (-0.65643*ztr - 0.01844) * zsal
659
660         zck2p    = -8814.715*ztr + 172.1033 - 27.927*zlogt  &
661         &          + (-160.340*ztr + 1.3566)*zsqrt          &
662         &          + (0.37335*ztr - 0.05778)*zsal
663
664         zck3p    = -3070.75*ztr - 18.126                    &
665         &          + (17.27039*ztr + 2.81197) * zsqrt       &
666         &          + (-44.99486*ztr - 0.09984) * zsal
667
668         ! CONSTANT FOR SILICATE, MILLERO (1995)
669         zcksi    = -8904.2*ztr  + 117.400 - 19.334*zlogt   &
670         &          + (-458.79*ztr + 3.5913) * zisqrt       &
671         &          + (188.74*ztr - 1.5998) * zis           &
672         &          + (-12.1652*ztr + 0.07871) * zis2       &
673         &          + LOG(1.0 - 0.001005*zsal)
674
675         ! APPARENT SOLUBILITY PRODUCT K'SP OF CALCITE IN SEAWATER
676         !       (S=27-43, T=2-25 DEG C) at pres =0 (atmos. pressure) (MUCCI 1983)
677         zaksp0  = -171.9065 -0.077993*ztkel + 2839.319*ztr + 71.595*LOG10( ztkel )   &
678         &         + (-0.77712 + 0.00284263*ztkel + 178.34*ztr) * zsqrt  &
679         &         - 0.07711*zsal + 0.0041249*zsal15
680
681         ! CONVERT FROM DIFFERENT PH SCALES
682         total2free  = 1.0/(1.0 + zst/zcks)
683         free2SWS    = 1. + zst/zcks + zft/(zckf*total2free)
684         total2SWS   = total2free * free2SWS
685         SWS2total   = 1.0 / total2SWS
686
687
688         ! K1, K2 OF CARBONIC ACID, KB OF BORIC ACID, KW (H2O) (LIT.?)
689         zak1    = 10**(zck1) * total2SWS
690         zak2    = 10**(zck2) * total2SWS
691         zakb    = EXP( zckb ) * total2SWS
692         zakw    = EXP( zckw )
693         zaksp1  = 10**(zaksp0)
694         zak1p   = exp( zck1p )
695         zak2p   = exp( zck2p )
696         zak3p   = exp( zck3p )
697         zaksi   = exp( zcksi )
698         zckf    = zckf * total2SWS
699
700         ! FORMULA FOR CPEXP AFTER EDMOND & GIESKES (1970)
701         !        (REFERENCE TO CULBERSON & PYTKOQICZ (1968) AS MADE
702         !        IN BROECKER ET AL. (1982) IS INCORRECT; HERE RGAS IS
703         !        TAKEN TENFOLD TO CORRECT FOR THE NOTATION OF pres  IN
704         !        DBAR INSTEAD OF BAR AND THE EXPRESSION FOR CPEXP IS
705         !        MULTIPLIED BY LN(10.) TO ALLOW USE OF EXP-FUNCTION
706         !        WITH BASIS E IN THE FORMULA FOR AKSPP (CF. EDMOND
707         !        & GIESKES (1970), P. 1285-1286 (THE SMALL
708         !        FORMULA ON P. 1286 IS RIGHT AND CONSISTENT WITH THE
709         !        SIGN IN PARTIAL MOLAR VOLUME CHANGE AS SHOWN ON P. 1285))
710         zcpexp  = zpres / (rgas*ztkel)
711         zcpexp2 = zpres * zcpexp
712
713         ! KB OF BORIC ACID, K1,K2 OF CARBONIC ACID PRESSURE
714         !        CORRECTION AFTER CULBERSON AND PYTKOWICZ (1968)
715         !        (CF. BROECKER ET AL., 1982)
716
717         zbuf1  = -     ( devk10 + devk20 * ztc + devk30 * ztc * ztc )
718         zbuf2  = 0.5 * ( devk40 + devk50 * ztc )
719         ak1s(ji) = zak1 * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
720
721         zbuf1  =     - ( devk11 + devk21 * ztc + devk31 * ztc * ztc )
722         zbuf2  = 0.5 * ( devk41 + devk51 * ztc )
723         ak2s(ji) = zak2 * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
724
725         zbuf1  =     - ( devk12 + devk22 * ztc + devk32 * ztc * ztc )
726         zbuf2  = 0.5 * ( devk42 + devk52 * ztc )
727         akbs(ji) = zakb * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
728
729         zbuf1  =     - ( devk13 + devk23 * ztc + devk33 * ztc * ztc )
730         zbuf2  = 0.5 * ( devk43 + devk53 * ztc )
731         akws(ji) = zakw * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
732
733         zbuf1  =     - ( devk14 + devk24 * ztc + devk34 * ztc * ztc )
734         zbuf2  = 0.5 * ( devk44 + devk54 * ztc )
735         aks3s(ji) = zcks * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
736
737         zbuf1  =     - ( devk15 + devk25 * ztc + devk35 * ztc * ztc )
738         zbuf2  = 0.5 * ( devk45 + devk55 * ztc )
739         akf3s(ji) = zckf * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
740
741         zbuf1  =     - ( devk17 + devk27 * ztc + devk37 * ztc * ztc )
742         zbuf2  = 0.5 * ( devk47 + devk57 * ztc )
743         ak1ps(ji) = zak1p * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
744
745         zbuf1  =     - ( devk18 + devk28 * ztc + devk38 * ztc * ztc )
746         zbuf2  = 0.5 * ( devk48 + devk58 * ztc )
747         ak2ps(ji) = zak2p * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
748
749         zbuf1  =     - ( devk110 + devk210 * ztc + devk310 * ztc * ztc )
750         zbuf2  = 0.5 * ( devk410 + devk510 * ztc )
751         aksis(ji) = zaksi * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
752
753         ! Convert to total scale
754         ak1s(ji)  = ak1s(ji)  * SWS2total
755         ak2s(ji)  = ak2s(ji)  * SWS2total
756         akbs(ji)  = akbs(ji)  * SWS2total
757         akws(ji)  = akws(ji)  * SWS2total
758         ak1ps(ji) = ak1ps(ji) * SWS2total
759         ak2ps(ji) = ak2ps(ji) * SWS2total
760         ak3ps(ji) = ak3ps(ji) * SWS2total
761         aksis(ji) = aksis(ji) * SWS2total
762         akf3s(ji) = akf3s(ji) / total2free
763
764         ! APPARENT SOLUBILITY PRODUCT K'SP OF CALCITE
765         !        AS FUNCTION OF PRESSURE FOLLOWING MILLERO
766         !        (P. 1285) AND BERNER (1976)
767         zbuf1  =     - ( devk16 + devk26 * ztc + devk36 * ztc * ztc )
768         zbuf2  = 0.5 * ( devk46 + devk56 * ztc )
769         aksps(ji) = zaksp1 * EXP( zbuf1 * zcpexp + zbuf2 * zcpexp2 )
770
771         ! TOTAL F, S, and BORATE CONCENTR. [MOLES/L]
772         borats(ji)   = 0.0002414 * zcl / 10.811
773         sulfats(ji)  = zst
774         fluorids(ji) = zft
775
776         ! Iron and SIO3 saturation concentration from ...
777         sieqs(ji) = EXP(  LOG( 10.) * ( 6.44 - 968. / ztkel )  ) * 1.e-6
778      END DO
779      !
780      IF( ln_timing )  CALL timing_stop('sed_chem_cst')
781      !
782   END SUBROUTINE sed_chem_cst
783
784
785END MODULE sedchem
Note: See TracBrowser for help on using the repository browser.