source: LMDZ6/branches/Amaury_dev/libf/dyn3dmem/exner_hyb_loc_m.F90

Last change on this file was 5159, checked in by abarral, 3 months ago

Put dimensions.h and paramet.h into modules

  • Property copyright set to
    Name of program: LMDZ
    Creation date: 1984
    Version: LMDZ5
    License: CeCILL version 2
    Holder: Laboratoire de m\'et\'eorologie dynamique, CNRS, UMR 8539
    See the license file in the root directory
File size: 5.5 KB
Line 
1module exner_hyb_loc_m
2
3  IMPLICIT NONE
4
5CONTAINS
6
7  SUBROUTINE  exner_hyb_loc(ngrid, ps, p, pks, pk, pkf)
8
9    !     Auteurs :  P.Le Van  , Fr. Hourdin  .
10    !    ..........
11
12    !    ....  ngrid, ps,p             sont des argum.d'entree  au sous-prog ...
13    !    ....  pks,pk,pkf   sont des argum.de sortie au sous-prog ...
14
15    !   ************************************************************************
16    !    Calcule la fonction d'Exner pk = Cp * (p/preff) ** kappa , aux milieux des
17    !    couches .   Pk(l) sera calcule aux milieux  des couches l ,entre les
18    !    pressions p(l) et p(l+1) ,definis aux interfaces des llm couches .
19    !   ************************************************************************
20    !  .. N.B : Au sommet de l'atmosphere,  p(llm+1) = 0. , et ps et pks sont
21    !    la pression et la fonction d'Exner  au  sol  .
22
23    !                                 -------- z
24    !    A partir des relations  ( 1 ) p*dz(pk) = kappa *pk*dz(p)      et
25    !                            ( 2 ) pk(l) = alpha(l)+ beta(l)*pk(l-1)
26    !    ( voir note de Fr.Hourdin )  ,
27
28    !    on determine successivement , du haut vers le bas des couches, les
29    !    coef. alpha(llm),beta(llm) .,.,alpha(l),beta(l),,,alpha(2),beta(2),
30    !    puis pk(ij,1). Ensuite ,on calcule,du bas vers le haut des couches,
31    !     pk(ij,l)  donne  par la relation (2),  pour l = 2 a l = llm .
32
33    USE parallel_lmdz
34    USE lmdz_filtreg_p
35    USE write_field_loc
36    USE comconst_mod, ONLY: cpp, kappa, r, jmp1
37    USE comvert_mod, ONLY: preff
38    USE lmdz_cppkeys_wrapper, ONLY: CPPKEY_DEBUGIO
39    USE lmdz_comgeom
40
41USE lmdz_dimensions, ONLY: iim, jjm, llm, ndm
42  USE lmdz_paramet
43    IMPLICIT NONE
44
45
46
47
48    INTEGER  ngrid
49    REAL p(ijb_u:ije_u, llmp1), pk(ijb_u:ije_u, llm)
50    REAL, optional :: pkf(ijb_u:ije_u, llm)
51    REAL ps(ijb_u:ije_u), pks(ijb_u:ije_u)
52    REAL alpha(ijb_u:ije_u, llm), beta(ijb_u:ije_u, llm)
53
54    !    .... variables locales   ...
55
56    INTEGER l, ij
57    REAL unpl2k, dellta
58
59    INTEGER ije, ijb, jje, jjb
60    logical, save :: firstcall = .TRUE.
61    !$OMP THREADPRIVATE(firstcall)
62    CHARACTER(LEN = *), parameter :: modname = "exner_hyb_loc"
63
64    !$OMP BARRIER
65
66    ! Sanity check
67    IF (firstcall) THEN
68      ! sanity checks for Shallow Water case (1 vertical layer)
69      IF (llm==1) THEN
70        IF (kappa/=1) THEN
71          CALL abort_gcm(modname, &
72                  "kappa!=1 , but running in Shallow Water mode!!", 42)
73        endif
74        IF (cpp/=r) THEN
75          CALL abort_gcm(modname, &
76                  "cpp!=r , but running in Shallow Water mode!!", 42)
77        endif
78      endif ! of if (llm.EQ.1)
79
80      firstcall = .FALSE.
81    endif ! of if (firstcall)
82
83    !$OMP BARRIER
84
85    ! Specific behaviour for Shallow Water (1 vertical layer) case:
86    IF (llm==1) THEN
87      ! Compute pks(:),pk(:),pkf(:)
88      ijb = ij_begin
89      ije = ij_end
90      !$OMP DO SCHEDULE(STATIC)
91      DO ij = ijb, ije
92        pks(ij) = (cpp / preff) * ps(ij)
93        pk(ij, 1) = .5 * pks(ij)
94        IF (present(pkf)) pkf(ij, 1) = pk(ij, 1)
95      ENDDO
96      !$OMP ENDDO
97
98      !$OMP BARRIER
99      IF (present(pkf)) THEN
100        jjb = jj_begin
101        jje = jj_end
102        CALL filtreg_p (pkf, jjb_u, jje_u, jjb, jje, jmp1, llm, &
103                2, 1, .TRUE., 1)
104      end if
105
106      ! our work is done, exit routine
107      RETURN
108    endif ! of if (llm.EQ.1)
109
110    ! General case:
111
112    unpl2k = 1. + 2. * kappa
113
114    !     -------------
115    !     Calcul de pks
116    !     -------------
117
118    ijb = ij_begin
119    ije = ij_end
120
121    !$OMP DO SCHEDULE(STATIC)
122    DO   ij = ijb, ije
123      pks(ij) = cpp * (ps(ij) / preff) ** kappa
124    ENDDO
125    !$OMP ENDDO
126    ! Synchro OPENMP ici
127
128    !$OMP BARRIER
129
130
131    !    .... Calcul des coeff. alpha et beta  pour la couche l = llm ..
132
133    !$OMP DO SCHEDULE(STATIC)
134    DO     ij = ijb, ije
135      alpha(ij, llm) = 0.
136      beta (ij, llm) = 1. / unpl2k
137    ENDDO
138    !$OMP ENDDO NOWAIT
139
140    !     ... Calcul des coeff. alpha et beta  pour l = llm-1  a l = 2 ...
141
142    DO l = llm - 1, 2, -1
143
144      !$OMP DO SCHEDULE(STATIC)
145      DO ij = ijb, ije
146        dellta = p(ij, l) * unpl2k + p(ij, l + 1) * (beta(ij, l + 1) - unpl2k)
147        alpha(ij, l) = - p(ij, l + 1) / dellta * alpha(ij, l + 1)
148        beta (ij, l) = p(ij, l) / dellta
149      ENDDO
150      !$OMP ENDDO NOWAIT
151    ENDDO
152
153    !  ***********************************************************************
154    !     .....  Calcul de pk pour la couche 1 , pres du sol  ....
155
156    !$OMP DO SCHEDULE(STATIC)
157    DO   ij = ijb, ije
158      pk(ij, 1) = (p(ij, 1) * pks(ij) - 0.5 * alpha(ij, 2) * p(ij, 2)) / &
159              (p(ij, 1) * (1. + kappa) + 0.5 * (beta(ij, 2) - unpl2k) * p(ij, 2))
160    ENDDO
161    !$OMP ENDDO NOWAIT
162
163    !    ..... Calcul de pk(ij,l) , pour l = 2 a l = llm  ........
164
165    DO l = 2, llm
166      !$OMP DO SCHEDULE(STATIC)
167      DO   ij = ijb, ije
168        pk(ij, l) = alpha(ij, l) + beta(ij, l) * pk(ij, l - 1)
169      ENDDO
170      !$OMP ENDDO NOWAIT
171    ENDDO
172
173    IF (present(pkf)) THEN
174      !    calcul de pkf
175
176      DO l = 1, llm
177        !$OMP DO SCHEDULE(STATIC)
178        DO   ij = ijb, ije
179          pkf(ij, l) = pk(ij, l)
180        ENDDO
181        !$OMP ENDDO NOWAIT
182      ENDDO
183
184      !$OMP BARRIER
185
186      jjb = jj_begin
187      jje = jj_end
188      IF (CPPKEY_DEBUGIO) THEN
189        CALL WriteField_u('pkf', pkf)
190      END IF
191      CALL filtreg_p (pkf, jjb_u, jje_u, jjb, jje, jmp1, llm, &
192              2, 1, .TRUE., 1)
193      IF (CPPKEY_DEBUGIO) THEN
194        CALL WriteField_u('pkf', pkf)
195      END IF
196    end if
197
198  END SUBROUTINE exner_hyb_loc
199
200END MODULE exner_hyb_loc_m
Note: See TracBrowser for help on using the repository browser.