/[MITgcm]/MITgcm/pkg/grdchk/grdchk_main.F
ViewVC logotype

Contents of /MITgcm/pkg/grdchk/grdchk_main.F

Parent Directory Parent Directory | Revision Log Revision Log | View Revision Graph Revision Graph


Revision 1.18 - (show annotations) (download)
Fri Nov 10 04:57:10 2006 UTC (17 years, 6 months ago) by heimbach
Branch: MAIN
CVS Tags: checkpoint58r_post
Changes since 1.17: +17 -13 lines
o Correct some location calculations for obcs gradient checks
o Improve output for obcs gradient checks and include iobcs index

1 C
2 C $Header: /u/gcmpack/MITgcm/pkg/grdchk/grdchk_main.F,v 1.17 2006/05/12 02:17:03 heimbach Exp $
3 C $Name: $
4
5 #include "AD_CONFIG.h"
6 #include "CPP_OPTIONS.h"
7
8 CBOI
9 C
10 C !TITLE: GRADIENT CHECK
11 C !AUTHORS: mitgcm developers ( support@mitgcm.org )
12 C !AFFILIATION: Massachussetts Institute of Technology
13 C !DATE:
14 C !INTRODUCTION: gradient check package
15 c \bv
16 c Compare the gradients calculated by the adjoint model with
17 c finite difference approximations.
18 c
19 C !CALLING SEQUENCE:
20 c
21 c the_model_main
22 c |
23 c |-- ctrl_unpack
24 c |-- adthe_main_loop - unperturbed cost function and
25 c |-- ctrl_pack adjoint gradient are computed here
26 c |
27 c |-- grdchk_main
28 c |
29 c |-- grdchk_init
30 c |-- do icomp=... - loop over control vector elements
31 c |
32 c |-- grdchk_loc - determine location of icomp on grid
33 c |
34 c |-- grdchk_getxx - get control vector component from file
35 c | perturb it and write back to file
36 c |-- grdchk_getadxx - get gradient component calculated
37 c | via adjoint
38 c |-- the_main_loop - forward run and cost evaluation
39 c | with perturbed control vector element
40 c |-- calculate ratio of adj. vs. finite difference gradient
41 c |
42 c |-- grdchk_setxx - Reset control vector element
43 c |
44 c |-- grdchk_print - print results
45 c \ev
46 CEOI
47
48 CBOP
49 C !ROUTINE: grdchk_main
50 C !INTERFACE:
51 subroutine grdchk_main( mythid )
52
53 C !DESCRIPTION: \bv
54 c ==================================================================
55 c SUBROUTINE grdchk_main
56 c ==================================================================
57 c o Compare the gradients calculated by the adjoint model with
58 c finite difference approximations.
59 c started: Christian Eckert eckert@mit.edu 24-Feb-2000
60 c continued&finished: heimbach@mit.edu: 13-Jun-2001
61 c changed: mlosch@ocean.mit.edu: 09-May-2002
62 c - added centered difference vs. 1-sided difference option
63 c - improved output format for readability
64 c - added control variable hFacC
65 c heimbach@mit.edu 24-Feb-2003
66 c - added tangent linear gradient checks
67 c - fixes for multiproc. gradient checks
68 c - added more control variables
69 c
70 c ==================================================================
71 c SUBROUTINE grdchk_main
72 c ==================================================================
73 C \ev
74
75 C !USES:
76 implicit none
77
78 c == global variables ==
79 #include "SIZE.h"
80 #include "EEPARAMS.h"
81 #include "PARAMS.h"
82 #include "grdchk.h"
83 #include "cost.h"
84 #ifdef ALLOW_TANGENTLINEAR_RUN
85 #include "g_cost.h"
86 #endif
87
88 C !INPUT/OUTPUT PARAMETERS:
89 c == routine arguments ==
90 integer mythid
91
92 #ifdef ALLOW_GRDCHK
93 C !LOCAL VARIABLES:
94 c == local variables ==
95 integer myiter
96 _RL mytime
97 integer bi, itlo, ithi
98 integer bj, jtlo, jthi
99 integer i, imin, imax
100 integer j, jmin, jmax
101 integer k
102
103 integer icomp
104 integer ichknum
105 integer icvrec
106 integer jtile
107 integer itile
108 integer layer
109 integer obcspos
110 integer itilepos
111 integer jtilepos
112 integer itest
113 integer ierr
114 integer ierr_grdchk
115 _RL gfd
116 _RL fcref
117 _RL fcpertplus, fcpertminus
118 _RL ratio_ad
119 _RL ratio_ftl
120 _RL xxmemo_ref
121 _RL xxmemo_pert
122 _RL adxxmemo
123 _RL ftlxxmemo
124 _RL localEps
125 _RL grdchk_epsfac
126
127 _RL tmpplot1(1-olx:snx+olx,1-oly:sny+oly,nr,nsx,nsy)
128 _RL tmpplot2(1-olx:snx+olx,1-oly:sny+oly,nr,nsx,nsy)
129 _RL tmpplot3(1-olx:snx+olx,1-oly:sny+oly,nr,nsx,nsy)
130
131 CHARACTER*(MAX_LEN_MBUF) msgBuf
132
133 c == end of interface ==
134 CEOP
135
136 c-- Set the loop ranges.
137 jtlo = mybylo(mythid)
138 jthi = mybyhi(mythid)
139 itlo = mybxlo(mythid)
140 ithi = mybxhi(mythid)
141 jmin = 1
142 jmax = sny
143 imin = 1
144 imax = snx
145
146 print *, 'ph-check entering grdchk_main '
147
148 c-- initialise variables
149 call grdchk_init( mythid )
150
151 c-- Compute the adjoint models' gradients.
152 c-- Compute the unperturbed cost function.
153 cph Gradient via adjoint has already been computed,
154 cph and so has unperturbed cost function,
155 cph assuming all xx_ fields are initialised to zero.
156
157 ierr_grdchk = 0
158 cphadmtlm(
159 fcref = fc
160 cphadmtlm fcref = objf_state_final(45,4,1,1,1)
161 cphadmtlm)
162
163 print *, 'ph-check fcref = ', fcref
164
165 do bj = jtlo, jthi
166 do bi = itlo, ithi
167 do k = 1, nr
168 do j = jmin, jmax
169 do i = imin, imax
170 tmpplot1(i,j,k,bi,bj) = 0. _d 0
171 tmpplot2(i,j,k,bi,bj) = 0. _d 0
172 tmpplot3(i,j,k,bi,bj) = 0. _d 0
173 end do
174 end do
175 end do
176 end do
177 end do
178
179 if ( useCentralDiff ) then
180 grdchk_epsfac = 2. _d 0
181 else
182 grdchk_epsfac = 1. _d 0
183 end if
184
185 print *, 'grad-res -------------------------------'
186 print ('(2a)'),
187 & ' grad-res proc # i j k iobc',
188 & ' fc ref fc + eps fc - eps'
189 #ifdef ALLOW_TANGENTLINEAR_RUN
190 print ('(2a)'),
191 & ' grad-res proc # i j k iobc',
192 & ' tlm grad fd grad 1 - fd/tlm'
193 #else
194 print ('(2a)'),
195 & ' grad-res proc # i j k iobc',
196 & ' adj grad fd grad 1 - fd/adj'
197 #endif
198
199 c-- Compute the finite difference approximations.
200 c-- Cycle through all processes doing NINT(nend-nbeg+1)/nstep
201 c-- gradient checks.
202
203 if ( nbeg .EQ. 0 )
204 & call grdchk_get_position( mythid )
205
206 do icomp = nbeg, nend, nstep
207
208 ichknum = (icomp - nbeg)/nstep + 1
209
210 if (ichknum .le. maxgrdchecks ) then
211
212 c-- Determine the location of icomp on the grid.
213 if ( myProcId .EQ. grdchkwhichproc ) then
214 call grdchk_loc( icomp, ichknum,
215 & icvrec, itile, jtile, layer, obcspos,
216 & itilepos, jtilepos, itest, ierr,
217 & mythid )
218 cph(
219 print *, 'ph-grd ----- back from loc -----',
220 & icvrec, itilepos, jtilepos, layer, obcspos
221 cph)
222 endif
223 _BARRIER
224
225 c******************************************************
226 c-- (A): get gradient component calculated via adjoint
227 c******************************************************
228
229 c-- get gradient component calculated via adjoint
230 if ( myProcId .EQ. grdchkwhichproc .AND.
231 & ierr .EQ. 0 ) then
232 call grdchk_getadxx( icvrec,
233 & itile, jtile, layer,
234 & itilepos, jtilepos,
235 & adxxmemo, mythid )
236 endif
237 _BARRIER
238
239 #ifdef ALLOW_TANGENTLINEAR_RUN
240 c******************************************************
241 c-- (B): Get gradient component g_fc from tangent linear run:
242 c******************************************************
243 c--
244 c-- 1. perturb control vector component: xx(i)=1.
245
246 if ( myProcId .EQ. grdchkwhichproc .AND.
247 & ierr .EQ. 0 ) then
248 localEps = 1. _d 0
249 call grdchk_getxx( icvrec, TANGENT_SIMULATION,
250 & itile, jtile, layer,
251 & itilepos, jtilepos,
252 & xxmemo_ref, xxmemo_pert, localEps,
253 & mythid )
254 endif
255 _BARRIER
256
257 c--
258 c-- 2. perform tangent linear run
259 mytime = starttime
260 myiter = niter0
261 cphadmtlm(
262 g_fc = 0.
263 cphadmtlm do j=1,sny
264 cphadmtlm do i=1,snx
265 cphadmtlm g_objf_state_final(i,j,1,1,1) = 0.
266 cphadmtlm g_objf_state_final(i,j,1,1,2) = 0.
267 cphadmtlm enddo
268 cphadmtlm enddo
269 cphadmtlm)
270 call g_the_main_loop( mytime, myiter, mythid )
271 cphadmtlm(
272 ftlxxmemo = g_fc
273 cphadmtlm ftlxxmemo = g_objf_state_final(45,4,1,1,1)
274 cphadmtlm)
275 _BARRIER
276 c--
277 c-- 3. reset control vector
278 if ( myProcId .EQ. grdchkwhichproc .AND.
279 & ierr .EQ. 0 ) then
280 call grdchk_setxx( icvrec, TANGENT_SIMULATION,
281 & itile, jtile, layer,
282 & itilepos, jtilepos,
283 & xxmemo_ref, mythid )
284 endif
285 _BARRIER
286
287 #endif /* ALLOW_TANGENTLINEAR_RUN */
288
289
290 c******************************************************
291 c-- (C): Get gradient via finite difference perturbation
292 c******************************************************
293
294 c-- get control vector component from file
295 c-- perturb it and write back to file
296 c-- positive perturbation
297 localEps = abs(grdchk_eps)
298 if ( myProcId .EQ. grdchkwhichproc .AND.
299 & ierr .EQ. 0 ) then
300 call grdchk_getxx( icvrec, FORWARD_SIMULATION,
301 & itile, jtile, layer,
302 & itilepos, jtilepos,
303 & xxmemo_ref, xxmemo_pert, localEps,
304 & mythid )
305 endif
306 _BARRIER
307
308 c-- forward run with perturbed control vector
309 mytime = starttime
310 myiter = niter0
311 call the_main_loop( mytime, myiter, mythid )
312 cphadmtlm(
313 fcpertplus = fc
314 cphadmtlm fcpertplus = objf_state_final(45,4,1,1,1)
315 cphadmtlm)
316 print *, 'ph-check fcpertplus = ', fcpertplus
317 _BARRIER
318
319 c-- Reset control vector.
320 if ( myProcId .EQ. grdchkwhichproc .AND.
321 & ierr .EQ. 0 ) then
322 call grdchk_setxx( icvrec, FORWARD_SIMULATION,
323 & itile, jtile, layer,
324 & itilepos, jtilepos,
325 & xxmemo_ref, mythid )
326 endif
327 _BARRIER
328
329 fcpertminus = fcref
330 print *, 'ph-check fcpertminus = ', fcpertminus
331
332 if ( useCentralDiff ) then
333
334 c-- get control vector component from file
335 c-- perturb it and write back to file
336 c-- repeat the proceedure for a negative perturbation
337 if ( myProcId .EQ. grdchkwhichproc .AND.
338 & ierr .EQ. 0 ) then
339 localEps = - abs(grdchk_eps)
340 call grdchk_getxx( icvrec, FORWARD_SIMULATION,
341 & itile, jtile, layer,
342 & itilepos, jtilepos,
343 & xxmemo_ref, xxmemo_pert, localEps,
344 & mythid )
345 endif
346 _BARRIER
347
348 c-- forward run with perturbed control vector
349 mytime = starttime
350 myiter = niter0
351 call the_main_loop( mytime, myiter, mythid )
352 _BARRIER
353 fcpertminus = fc
354
355 c-- Reset control vector.
356 if ( myProcId .EQ. grdchkwhichproc .AND.
357 & ierr .EQ. 0 ) then
358 call grdchk_setxx( icvrec, FORWARD_SIMULATION,
359 & itile, jtile, layer,
360 & itilepos, jtilepos,
361 & xxmemo_ref, mythid )
362 endif
363 _BARRIER
364
365 c-- end of if useCentralDiff ...
366 end if
367
368 c******************************************************
369 c-- (D): calculate relative differences between gradients
370 c******************************************************
371
372 if ( myProcId .EQ. grdchkwhichproc .AND.
373 & ierr .EQ. 0 ) then
374
375 if ( grdchk_eps .eq. 0. ) then
376 gfd = (fcpertplus-fcpertminus)
377 else
378 gfd = (fcpertplus-fcpertminus)
379 & /(grdchk_epsfac*grdchk_eps)
380 endif
381
382 if ( adxxmemo .eq. 0. ) then
383 ratio_ad = abs( adxxmemo - gfd )
384 else
385 ratio_ad = 1. - gfd/adxxmemo
386 endif
387
388 if ( ftlxxmemo .eq. 0. ) then
389 ratio_ftl = abs( ftlxxmemo - gfd )
390 else
391 ratio_ftl = 1. - gfd/ftlxxmemo
392 endif
393
394 tmpplot1(itilepos,jtilepos,layer,itile,jtile)
395 & = gfd
396 tmpplot2(itilepos,jtilepos,layer,itile,jtile)
397 & = ratio_ad
398 tmpplot3(itilepos,jtilepos,layer,itile,jtile)
399 & = ratio_ftl
400
401 fcrmem ( ichknum ) = fcref
402 fcppmem ( ichknum ) = fcpertplus
403 fcpmmem ( ichknum ) = fcpertminus
404 xxmemref ( ichknum ) = xxmemo_ref
405 xxmempert ( ichknum ) = xxmemo_pert
406 gfdmem ( ichknum ) = gfd
407 adxxmem ( ichknum ) = adxxmemo
408 ftlxxmem ( ichknum ) = ftlxxmemo
409 ratioadmem ( ichknum ) = ratio_ad
410 ratioftlmem ( ichknum ) = ratio_ftl
411
412 irecmem ( ichknum ) = icvrec
413 bimem ( ichknum ) = itile
414 bjmem ( ichknum ) = jtile
415 ilocmem ( ichknum ) = itilepos
416 jlocmem ( ichknum ) = jtilepos
417 klocmem ( ichknum ) = layer
418 iobcsmem ( ichknum ) = obcspos
419 icompmem ( ichknum ) = icomp
420 ichkmem ( ichknum ) = ichknum
421 itestmem ( ichknum ) = itest
422 ierrmem ( ichknum ) = ierr
423
424 print *, 'grad-res -------------------------------'
425 print '(a,6I5,2x,3(1x,E18.12))', ' grad-res ',
426 & myprocid,ichknum,itilepos,jtilepos,layer,obcspos,
427 & fcref, fcpertplus, fcpertminus
428 #ifdef ALLOW_TANGENTLINEAR_RUN
429 print '(a,6I5,2x,3(1x,E18.12))', ' grad-res ',
430 & myprocid,ichknum,ichkmem(ichknum),
431 & icompmem(ichknum),itestmem(ichknum),obcspos,
432 & ftlxxmemo, gfd, ratio_ftl
433 WRITE(msgBuf,'(A34,2(1PE24.14,X))')
434 & 'precision_grdchk_result TLM ', fcref, ftlxxmemo
435 CALL PRINT_MESSAGE
436 & (msgBuf,standardMessageUnit,SQUEEZE_RIGHT,1)
437 #else
438 print '(a,6I5,2x,3(1x,E18.12))', ' grad-res ',
439 & myprocid,ichknum,ichkmem(ichknum),
440 & icompmem(ichknum),itestmem(ichknum),obcspos,
441 & adxxmemo, gfd, ratio_ad
442 WRITE(msgBuf,'(A34,2(1PE24.14,X))')
443 & 'precision_grdchk_result ADM ', fcref, adxxmemo
444 CALL PRINT_MESSAGE
445 & (msgBuf,standardMessageUnit,SQUEEZE_RIGHT,1)
446 #endif
447
448 endif
449
450 print *, 'ph-grd ierr ---------------------------'
451 print *, 'ph-grd ierr = ', ierr, ', icomp = ', icomp,
452 & ', ichknum = ', ichknum
453
454 _BARRIER
455
456 c-- else of if ( ichknum ...
457 else
458 ierr_grdchk = -1
459
460 c-- end of if ( ichknum ...
461 endif
462
463 c-- end of do icomp = ...
464 enddo
465
466 if ( myProcId .EQ. grdchkwhichproc ) then
467 CALL WRITE_REC_XYZ_RL(
468 & 'grd_findiff' , tmpplot1, 1, 0, myThid)
469 CALL WRITE_REC_XYZ_RL(
470 & 'grd_ratio_ad' , tmpplot2, 1, 0, myThid)
471 CALL WRITE_REC_XYZ_RL(
472 & 'grd_ratio_ftl' , tmpplot3, 1, 0, myThid)
473 endif
474
475 c-- Everyone has to wait for the component to be reset.
476 _BARRIER
477
478 c-- Print the results of the gradient check.
479 call grdchk_print( ichknum, ierr_grdchk, mythid )
480
481 #endif /* ALLOW_GRDCHK */
482
483 end

  ViewVC Help
Powered by ViewVC 1.1.22