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.
trcrst.F90 in branches/CMIP5_IPSL/NEMO/TOP_SRC – NEMO

source: branches/CMIP5_IPSL/NEMO/TOP_SRC/trcrst.F90 @ 1808

Last change on this file since 1808 was 1808, checked in by cetlod, 14 years ago

update TOP_SRC component on CMIP5_IPSL branch to take into account bugfixes (ie vertical diffusion routines), re-organization of restart part, damping of passive tracers on closed seas for PISCES

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 16.0 KB
Line 
1MODULE trcrst
2   !!======================================================================
3   !!                         ***  MODULE trcrst  ***
4   !! TOP :   Manage the passive tracer restart
5   !!======================================================================
6   !! History :    -   !  1991-03  ()  original code
7   !!             1.0  !  2005-03 (O. Aumont, A. El Moussaoui) F90
8   !!              -   !  2005-10 (C. Ethe) print control
9   !!             2.0  !  2005-10 (C. Ethe, G. Madec) revised architecture
10   !!----------------------------------------------------------------------
11#if defined key_top
12   !!----------------------------------------------------------------------
13   !!   'key_top'                                                TOP models
14   !!----------------------------------------------------------------------
15   !!----------------------------------------------------------------------
16   !!   trc_rst :   Restart for passive tracer
17   !!----------------------------------------------------------------------
18   !!----------------------------------------------------------------------
19   !!   'key_top'                                                TOP models
20   !!----------------------------------------------------------------------
21   !!   trc_rst_opn    : open  restart file
22   !!   trc_rst_read   : read  restart file
23   !!   trc_rst_wri    : write restart file
24   !!----------------------------------------------------------------------
25   USE oce_trc
26   USE trc
27   USE trctrp_lec
28   USE lib_mpp
29   USE iom
30   USE trcrst_cfc      ! CFC     
31   USE trcrst_lobster  ! LOBSTER  restart
32   USE trcrst_pisces   ! PISCES   restart
33   USE trcrst_c14b     ! C14 bomb restart
34   USE trcrst_my_trc   ! MY_TRC   restart
35
36   IMPLICIT NONE
37   PRIVATE
38
39   PUBLIC   trc_rst_opn       ! called by ???
40   PUBLIC   trc_rst_read      ! called by ???
41   PUBLIC   trc_rst_wri       ! called by ???
42
43   INTEGER, PUBLIC ::   numrtr, numrtw   !: logical unit for trc restart (read and write)
44
45   !! * Substitutions
46#  include "top_substitute.h90"
47   !!----------------------------------------------------------------------
48   !! NEMO/TOP 1.0 , LOCEAN-IPSL (2005)
49   !! $Id$
50   !! Software governed by the CeCILL licence (modipsl/doc/NEMO_CeCILL.txt)
51   !!----------------------------------------------------------------------
52   
53CONTAINS
54   
55   SUBROUTINE trc_rst_opn( kt )
56      !!----------------------------------------------------------------------
57      !!                    ***  trc_rst_opn  ***
58      !!
59      !! ** purpose  :   output of sea-trc variable in a netcdf file
60      !!----------------------------------------------------------------------
61      INTEGER, INTENT(in) ::   kt       ! number of iteration
62      !
63      CHARACTER(LEN=20)   ::   clkt     ! ocean time-step define as a character
64      CHARACTER(LEN=50)   ::   clname   ! trc output restart file name
65      !!----------------------------------------------------------------------
66      !
67# if ! defined key_off_tra
68      IF( kt == nit000 ) lrst_trc = .FALSE. 
69# else
70      IF( kt == nit000 ) THEN
71        lrst_trc = .FALSE. 
72        nitrst = nitend 
73      ENDIF
74
75      IF( MOD( kt - 1, nstock ) == 0 ) THEN
76         ! we use kt - 1 and not kt - nit000 to keep the same periodicity from the beginning of the experiment
77         nitrst = kt + nstock - 1                  ! define the next value of nitrst for restart writing
78         IF( nitrst > nitend )   nitrst = nitend   ! make sure we write a restart at the end of the run
79      ENDIF
80# endif
81     ! to get better performances with NetCDF format:
82     ! we open and define the tracer restart file one tracer time step before writing the data (-> at nitrst - 2*ndttrc + 1)
83     ! except if we write tracer restart files every tracer time step or if a tracer restart file was writen at nitend - 2*ndttrc + 1
84     IF( kt == nitrst - 2*ndttrc + 1 .OR. nstock == ndttrc .OR. ( kt == nitend - ndttrc + 1 .AND. .NOT. lrst_trc ) ) THEN
85         ! beware of the format used to write kt (default is i8.8, that should be large enough)
86         IF( nitrst > 1.0e9 ) THEN   ;   WRITE(clkt,*       ) nitrst
87         ELSE                        ;   WRITE(clkt,'(i8.8)') nitrst
88         ENDIF
89         ! create the file
90         IF(lwp) WRITE(numout,*)
91         clname = TRIM(cexper)//"_"//TRIM(ADJUSTL(clkt))//"_"//TRIM(cn_trcrst_out)
92         IF(lwp) WRITE(numout,*) '             open trc restart.output NetCDF file: '//clname
93         CALL iom_open( clname, numrtw, ldwrt = .TRUE., kiolib = jprstlib )
94         lrst_trc = .TRUE.
95      ENDIF
96      !
97   END SUBROUTINE trc_rst_opn
98
99   SUBROUTINE trc_rst_read
100      !!----------------------------------------------------------------------
101      !!                    ***  trc_rst_opn  ***
102      !!
103      !! ** purpose  :   read passive tracer fields in restart files
104      !!----------------------------------------------------------------------
105      INTEGER  ::  jn     
106      INTEGER  ::  iarak0 
107      REAL(wp) ::  zarak0
108      INTEGER  ::  jlibalt = jprstlib
109      LOGICAL  ::  llok
110
111      !!----------------------------------------------------------------------
112
113      IF(lwp) WRITE(numout,*)
114      IF(lwp) WRITE(numout,*) 'trc_rst_read : read the TOP restart file'
115      IF(lwp) WRITE(numout,*) '~~~~~~~~~~~~'
116
117      IF ( jprstlib == jprstdimg ) THEN
118        ! eventually read netcdf file (monobloc)  for restarting on different number of processors
119        ! if {cn_trcrst_in}.nc exists, then set jlibalt to jpnf90
120        INQUIRE( FILE = TRIM(cn_trcrst_in)//'.nc', EXIST = llok )
121        IF ( llok ) THEN ; jlibalt = jpnf90  ; ELSE ; jlibalt = jprstlib ; ENDIF
122      ENDIF
123
124      CALL iom_open( cn_trcrst_in, numrtr, kiolib = jlibalt ) 
125
126      ! Time domain : restart
127      ! ---------------------
128      CALL trc_rst_cal( nittrc000, 'READ' )   ! calendar
129
130      IF( ln_trcadv_cen2 .OR. ln_trcadv_tvd ) THEN   ;   iarak0 = 1
131      ELSE                                           ;   iarak0 = 0
132      ENDIF
133      CALL iom_get( numrtr, 'arak0', zarak0 )
134
135      IF( iarak0 /= NINT( zarak0 ) )   &                           ! Control of the scheme
136         & CALL ctl_stop( ' ===>>>> : problem with advection scheme', &
137         & ' it must be the same type for both restart and previous run', &
138         & ' centered or euler '  )
139      IF(lwp) WRITE(numout,*)
140      IF(lwp) WRITE(numout,*) '    arakawa option      : ', NINT( zarak0 )
141
142      ! READ prognostic variables and computes diagnostic variable
143      DO jn = 1, jptra
144         CALL iom_get( numrtr, jpdom_autoglo, 'TRN'//ctrcnm(jn), trn(:,:,:,jn) )
145      END DO
146
147      DO jn = 1, jptra
148         CALL iom_get( numrtr, jpdom_autoglo, 'TRB'//ctrcnm(jn), trb(:,:,:,jn) )
149      END DO
150
151      IF( lk_lobster )   CALL trc_rst_read_lobster( numrtr )      ! LOBSTER bio-model
152      IF( lk_pisces  )   CALL trc_rst_read_pisces ( numrtr )      ! PISCES  bio-model
153      IF( lk_cfc     )   CALL trc_rst_read_cfc    ( numrtr )      ! CFC     tracers
154      IF( lk_c14b    )   CALL trc_rst_read_c14b   ( numrtr )      ! C14 bomb  tracer
155      IF( lk_my_trc  )   CALL trc_rst_read_my_trc ( numrtr )      ! MY_TRC  tracers
156
157      CALL iom_close( numrtr )
158      !
159   END SUBROUTINE trc_rst_read
160
161   SUBROUTINE trc_rst_wri( kt )
162      !!----------------------------------------------------------------------
163      !!                    ***  trc_rst_wri  ***
164      !!
165      !! ** purpose  :   write passive tracer fields in restart files
166      !!----------------------------------------------------------------------
167      INTEGER, INTENT( in ) ::   kt    ! ocean time-step index
168      !!
169      INTEGER  :: jn
170      REAL(wp) :: zarak0
171      !!----------------------------------------------------------------------
172
173
174      CALL trc_rst_cal( kt, 'WRITE' )   ! calendar
175
176      IF( ln_trcadv_cen2 .OR. ln_trcadv_tvd ) THEN   ;   zarak0 = 1.
177      ELSE                                           ;   zarak0 = 0.
178      ENDIF
179      CALL iom_rstput( kt, nitrst, numrtw, 'arak0', zarak0 )
180
181      ! prognostic variables
182      ! --------------------
183      DO jn = 1, jptra
184         CALL iom_rstput( kt, nitrst, numrtw, 'TRN'//ctrcnm(jn), trn(:,:,:,jn) )
185      END DO
186
187      DO jn = 1, jptra
188         CALL iom_rstput( kt, nitrst, numrtw, 'TRB'//ctrcnm(jn), trb(:,:,:,jn) )
189      END DO
190
191      IF( lk_lobster )   CALL trc_rst_wri_lobster( kt, nitrst, numrtw )      ! LOBSTER bio-model
192      IF( lk_pisces  )   CALL trc_rst_wri_pisces ( kt, nitrst, numrtw )      ! PISCES  bio-model
193      IF( lk_cfc     )   CALL trc_rst_wri_cfc    ( kt, nitrst, numrtw )      ! CFC     tracers
194      IF( lk_c14b    )   CALL trc_rst_wri_c14b   ( kt, nitrst, numrtw )      ! C14 bomb  tracer
195      IF( lk_my_trc  )   CALL trc_rst_wri_my_trc ( kt, nitrst, numrtw )      ! MY_TRC  tracers
196
197      IF( kt == nitrst ) THEN
198          CALL trc_rst_stat            ! statistics
199          CALL iom_close( numrtw )     ! close the restart file (only at last time step)
200#if ! defined key_trdmld_trc
201          lrst_trc = .FALSE.
202#endif
203      ENDIF
204      !
205   END SUBROUTINE trc_rst_wri 
206
207
208   SUBROUTINE trc_rst_cal( kt, cdrw )
209      !!---------------------------------------------------------------------
210      !!                   ***  ROUTINE trc_rst_cal  ***
211      !!
212      !!  ** Purpose : Read or write calendar in restart file:
213      !!
214      !!  WRITE(READ) mode:
215      !!       kt        : number of time step since the begining of the experiment at the
216      !!                   end of the current(previous) run
217      !!       adatrj(0) : number of elapsed days since the begining of the experiment at the
218      !!                   end of the current(previous) run (REAL -> keep fractions of day)
219      !!       ndastp    : date at the end of the current(previous) run (coded as yyyymmdd integer)
220      !!
221      !!   According to namelist parameter nrstdt,
222      !!       nrsttr = 0  no control on the date (nittrc000 is  arbitrary).
223      !!       nrsttr = 1  we verify that nit000 is equal to the last
224      !!                   time step of previous run + 1.
225      !!       In both those options, the  exact duration of the experiment
226      !!       since the beginning (cumulated duration of all previous restart runs)
227      !!       is not stored in the restart and is assumed to be (nit000-1)*rdt.
228      !!       This is valid is the time step has remained constant.
229      !!
230      !!       nrsttr = 2  the duration of the experiment in days (adatrj)
231      !!                    has been stored in the restart file.
232      !!----------------------------------------------------------------------
233      INTEGER         , INTENT(in) ::   kt         ! ocean time-step
234      CHARACTER(len=*), INTENT(in) ::   cdrw       ! "READ"/"WRITE" flag
235      !
236      REAL(wp) ::  zkt
237#if defined key_off_tra
238      REAL(wp) ::  zndastp
239#endif
240
241      ! Time domain : restart
242      ! ---------------------
243
244      IF( TRIM(cdrw) == 'READ' ) THEN
245         CALL iom_get ( numrtr, 'kt', zkt )   ! last time-step of previous run
246         IF(lwp) THEN
247            WRITE(numout,*) ' *** Info read in restart : '
248            WRITE(numout,*) '   previous time-step                               : ', NINT( zkt )
249            WRITE(numout,*) ' *** restart option'
250            SELECT CASE ( nrsttr )
251            CASE ( 0 )   ;   WRITE(numout,*) ' nrsttr = 0 : no control of nittrc000'
252            CASE ( 1 )   ;   WRITE(numout,*) ' nrsttr = 1 : no control the date at nit000 (use ndate0 read in the namelist)'
253            CASE ( 2 )   ;   WRITE(numout,*) ' nrsttr = 2 : calendar parameters read in restart'
254            END SELECT
255            WRITE(numout,*)
256         ENDIF
257         ! Control of date
258         IF( nittrc000  - NINT( zkt ) /= 1 .AND.  nrsttr /= 0 )                                  &
259            &   CALL ctl_stop( ' ===>>>> : problem with nit000 for the restart',                 &
260            &                  ' verify the restart file or rerun with nrsttr = 0 (namelist)' )
261#if defined key_off_tra
262         ! define ndastp and adatrj
263         IF ( nrsttr == 2 ) THEN
264            CALL iom_get( numrtr, 'ndastp', zndastp ) 
265            ndastp = NINT( zndastp )
266            CALL iom_get( numrtr, 'adatrj', adatrj  )
267         ELSE
268            ndastp = ndate0 - 1     ! ndate0 read in the namelist in dom_nam
269            adatrj = ( REAL( nittrc000-1, wp ) * rdttra(1) ) / rday
270            ! note this is wrong if time step has changed during run
271         ENDIF
272         !
273         IF(lwp) THEN
274           WRITE(numout,*) ' *** Info used values : '
275           WRITE(numout,*) '   date ndastp                                      : ', ndastp
276           WRITE(numout,*) '   number of elapsed days since the begining of run : ', adatrj
277           WRITE(numout,*)
278         ENDIF
279#endif
280
281      ELSEIF( TRIM(cdrw) == 'WRITE' ) THEN
282         !
283         IF(  kt == nitrst ) THEN
284            IF(lwp) WRITE(numout,*)
285            IF(lwp) WRITE(numout,*) 'trc_wri : write the TOP restart file (NetCDF) at it= ', kt, ' date= ', ndastp
286            IF(lwp) WRITE(numout,*) '~~~~~~~'
287         ENDIF
288         ! calendar control
289         CALL iom_rstput( kt, nitrst, numrtw, 'kt'     , REAL( kt    , wp) )   ! time-step
290         CALL iom_rstput( kt, nitrst, numrtw, 'ndastp' , REAL( ndastp, wp) )   ! date
291         CALL iom_rstput( kt, nitrst, numrtw, 'adatrj' , adatrj            )   ! number of elapsed days since
292         !                                                                     ! the begining of the run [s]
293      ENDIF
294
295   END SUBROUTINE trc_rst_cal
296
297
298   SUBROUTINE trc_rst_stat
299      !!----------------------------------------------------------------------
300      !!                    ***  trc_rst_stat  ***
301      !!
302      !! ** purpose  :   Compute tracers statistics
303      !!----------------------------------------------------------------------
304
305      INTEGER  :: ji, jj, jk, jn
306      REAL(wp) :: zdiag_var, zdiag_varmin, zdiag_varmax, zdiag_tot
307      REAL(wp) :: zder, zvol
308      !!----------------------------------------------------------------------
309
310
311      IF( lwp ) THEN
312         WRITE(numout,*) 
313         WRITE(numout,*) '           ----TRACER STAT----             '
314         WRITE(numout,*) 
315      ENDIF
316     
317      zdiag_tot = 0.e0
318      DO jn = 1, jptra
319         zdiag_var    = 0.e0
320         zdiag_varmin = 0.e0
321         zdiag_varmax = 0.e0
322         DO jk = 1, jpk
323            DO jj = 1, jpj
324               DO ji = 1, jpi
325                  zvol = cvol(ji,jj,jk)
326#  if defined key_off_degrad
327                  zvol = zvol * facvol(ji,jj,jk)
328#  endif
329                  zdiag_var = zdiag_var + trn(ji,jj,jk,jn) * zvol
330               END DO
331            END DO
332         END DO
333         
334         zdiag_varmin = MINVAL( trn(:,:,:,jn), mask= ((tmask*SPREAD(tmask_i,DIM=3,NCOPIES=jpk).NE.0.)) )
335         zdiag_varmax = MAXVAL( trn(:,:,:,jn), mask= ((tmask*SPREAD(tmask_i,DIM=3,NCOPIES=jpk).NE.0.)) )
336         IF( lk_mpp ) THEN
337            CALL mpp_min( zdiag_varmin )      ! min over the global domain
338            CALL mpp_max( zdiag_varmax )      ! max over the global domain
339            CALL mpp_sum( zdiag_var    )      ! sum over the global domain
340         END IF
341         zdiag_tot = zdiag_tot + zdiag_var
342         zdiag_var = zdiag_var / areatot
343         IF(lwp) WRITE(numout,*) '   MEAN NO ', jn, ctrcnm(jn), ' = ', zdiag_var,   &
344            &                    ' MIN = ', zdiag_varmin, ' MAX = ', zdiag_varmax
345      END DO
346     
347      zder = ( ( zdiag_tot - trai ) / ( trai + 1.e-12 )  ) * 100._wp
348      IF(lwp) WRITE(numout,*) '   Integral of all tracers over the full domain  = ', zdiag_tot
349      IF(lwp) WRITE(numout,*) '   Drift of the sum of all tracers =', zder, ' %'
350     
351   END SUBROUTINE trc_rst_stat
352
353#else
354   !!----------------------------------------------------------------------
355   !!  Dummy module :                                     No passive tracer
356   !!----------------------------------------------------------------------
357CONTAINS
358   SUBROUTINE trc_rst_read                      ! Empty routines
359   END SUBROUTINE trc_rst_read
360   SUBROUTINE trc_rst_wri( kt )
361      INTEGER, INTENT ( in ) :: kt
362      WRITE(*,*) 'trc_rst_wri: You should not have seen this print! error?', kt
363   END SUBROUTINE trc_rst_wri   
364#endif
365
366   !!======================================================================
367END MODULE trcrst
Note: See TracBrowser for help on using the repository browser.