xref: /petsc/src/snes/interface/snesut.c (revision 8f1a2a5e609bf3d0ec1c7e7bf09507165b68d274)
1e7e93795SLois Curfman McInnes 
2c6db04a5SJed Brown #include <private/snesimpl.h>       /*I   "petscsnes.h"   I*/
3e7e93795SLois Curfman McInnes 
44a2ae208SSatish Balay #undef __FUNCT__
5a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorSolution"
63f1db9ecSBarry Smith /*@C
7a6570f20SBarry Smith    SNESMonitorSolution - Monitors progress of the SNES solvers by calling
836851e7fSLois Curfman McInnes    VecView() for the approximate solution at each iteration.
93f1db9ecSBarry Smith 
103f1db9ecSBarry Smith    Collective on SNES
113f1db9ecSBarry Smith 
123f1db9ecSBarry Smith    Input Parameters:
133f1db9ecSBarry Smith +  snes - the SNES context
143f1db9ecSBarry Smith .  its - iteration number
154b27c08aSLois Curfman McInnes .  fgnorm - 2-norm of residual
163f1db9ecSBarry Smith -  dummy - either a viewer or PETSC_NULL
173f1db9ecSBarry Smith 
1836851e7fSLois Curfman McInnes    Level: intermediate
193f1db9ecSBarry Smith 
2036851e7fSLois Curfman McInnes .keywords: SNES, nonlinear, vector, monitor, view
213f1db9ecSBarry Smith 
22a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorDefault(), VecView()
233f1db9ecSBarry Smith @*/
247087cfbeSBarry Smith PetscErrorCode  SNESMonitorSolution(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
253f1db9ecSBarry Smith {
26dfbe8321SBarry Smith   PetscErrorCode ierr;
273f1db9ecSBarry Smith   Vec            x;
28b0a32e0cSBarry Smith   PetscViewer    viewer = (PetscViewer) dummy;
293f1db9ecSBarry Smith 
303f1db9ecSBarry Smith   PetscFunctionBegin;
313f1db9ecSBarry Smith   ierr = SNESGetSolution(snes,&x);CHKERRQ(ierr);
323f1db9ecSBarry Smith   if (!viewer) {
333f1db9ecSBarry Smith     MPI_Comm comm;
343f1db9ecSBarry Smith     ierr   = PetscObjectGetComm((PetscObject)snes,&comm);CHKERRQ(ierr);
35b0a32e0cSBarry Smith     viewer = PETSC_VIEWER_DRAW_(comm);
363f1db9ecSBarry Smith   }
373f1db9ecSBarry Smith   ierr = VecView(x,viewer);CHKERRQ(ierr);
383f1db9ecSBarry Smith 
393f1db9ecSBarry Smith   PetscFunctionReturn(0);
403f1db9ecSBarry Smith }
413f1db9ecSBarry Smith 
424a2ae208SSatish Balay #undef __FUNCT__
43a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorResidual"
445ed2d596SBarry Smith /*@C
45a6570f20SBarry Smith    SNESMonitorResidual - Monitors progress of the SNES solvers by calling
465ed2d596SBarry Smith    VecView() for the residual at each iteration.
475ed2d596SBarry Smith 
485ed2d596SBarry Smith    Collective on SNES
495ed2d596SBarry Smith 
505ed2d596SBarry Smith    Input Parameters:
515ed2d596SBarry Smith +  snes - the SNES context
525ed2d596SBarry Smith .  its - iteration number
534b27c08aSLois Curfman McInnes .  fgnorm - 2-norm of residual
545ed2d596SBarry Smith -  dummy - either a viewer or PETSC_NULL
555ed2d596SBarry Smith 
565ed2d596SBarry Smith    Level: intermediate
575ed2d596SBarry Smith 
585ed2d596SBarry Smith .keywords: SNES, nonlinear, vector, monitor, view
595ed2d596SBarry Smith 
60a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorDefault(), VecView()
615ed2d596SBarry Smith @*/
627087cfbeSBarry Smith PetscErrorCode  SNESMonitorResidual(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
635ed2d596SBarry Smith {
64dfbe8321SBarry Smith   PetscErrorCode ierr;
655ed2d596SBarry Smith   Vec            x;
665ed2d596SBarry Smith   PetscViewer    viewer = (PetscViewer) dummy;
675ed2d596SBarry Smith 
685ed2d596SBarry Smith   PetscFunctionBegin;
695ed2d596SBarry Smith   ierr = SNESGetFunction(snes,&x,0,0);CHKERRQ(ierr);
705ed2d596SBarry Smith   if (!viewer) {
715ed2d596SBarry Smith     MPI_Comm comm;
725ed2d596SBarry Smith     ierr   = PetscObjectGetComm((PetscObject)snes,&comm);CHKERRQ(ierr);
735ed2d596SBarry Smith     viewer = PETSC_VIEWER_DRAW_(comm);
745ed2d596SBarry Smith   }
755ed2d596SBarry Smith   ierr = VecView(x,viewer);CHKERRQ(ierr);
765ed2d596SBarry Smith 
775ed2d596SBarry Smith   PetscFunctionReturn(0);
785ed2d596SBarry Smith }
795ed2d596SBarry Smith 
805ed2d596SBarry Smith #undef __FUNCT__
81a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorSolutionUpdate"
82d132466eSBarry Smith /*@C
83a6570f20SBarry Smith    SNESMonitorSolutionUpdate - Monitors progress of the SNES solvers by calling
84d132466eSBarry Smith    VecView() for the UPDATE to the solution at each iteration.
85d132466eSBarry Smith 
86d132466eSBarry Smith    Collective on SNES
87d132466eSBarry Smith 
88d132466eSBarry Smith    Input Parameters:
89d132466eSBarry Smith +  snes - the SNES context
90d132466eSBarry Smith .  its - iteration number
914b27c08aSLois Curfman McInnes .  fgnorm - 2-norm of residual
92d132466eSBarry Smith -  dummy - either a viewer or PETSC_NULL
93d132466eSBarry Smith 
94d132466eSBarry Smith    Level: intermediate
95d132466eSBarry Smith 
96d132466eSBarry Smith .keywords: SNES, nonlinear, vector, monitor, view
97d132466eSBarry Smith 
98a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorDefault(), VecView()
99d132466eSBarry Smith @*/
1007087cfbeSBarry Smith PetscErrorCode  SNESMonitorSolutionUpdate(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
101d132466eSBarry Smith {
102dfbe8321SBarry Smith   PetscErrorCode ierr;
103d132466eSBarry Smith   Vec            x;
104b0a32e0cSBarry Smith   PetscViewer    viewer = (PetscViewer) dummy;
105d132466eSBarry Smith 
106d132466eSBarry Smith   PetscFunctionBegin;
107d132466eSBarry Smith   ierr = SNESGetSolutionUpdate(snes,&x);CHKERRQ(ierr);
108d132466eSBarry Smith   if (!viewer) {
109d132466eSBarry Smith     MPI_Comm comm;
110d132466eSBarry Smith     ierr   = PetscObjectGetComm((PetscObject)snes,&comm);CHKERRQ(ierr);
111b0a32e0cSBarry Smith     viewer = PETSC_VIEWER_DRAW_(comm);
112d132466eSBarry Smith   }
113d132466eSBarry Smith   ierr = VecView(x,viewer);CHKERRQ(ierr);
114d132466eSBarry Smith 
115d132466eSBarry Smith   PetscFunctionReturn(0);
116d132466eSBarry Smith }
117d132466eSBarry Smith 
1184a2ae208SSatish Balay #undef __FUNCT__
119a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorDefault"
1204b828684SBarry Smith /*@C
121a6570f20SBarry Smith    SNESMonitorDefault - Monitors progress of the SNES solvers (default).
122e7e93795SLois Curfman McInnes 
123c7afd0dbSLois Curfman McInnes    Collective on SNES
124c7afd0dbSLois Curfman McInnes 
125e7e93795SLois Curfman McInnes    Input Parameters:
126c7afd0dbSLois Curfman McInnes +  snes - the SNES context
127e7e93795SLois Curfman McInnes .  its - iteration number
1284b27c08aSLois Curfman McInnes .  fgnorm - 2-norm of residual
129c7afd0dbSLois Curfman McInnes -  dummy - unused context
130fee21e36SBarry Smith 
131e7e93795SLois Curfman McInnes    Notes:
1324b27c08aSLois Curfman McInnes    This routine prints the residual norm at each iteration.
133e7e93795SLois Curfman McInnes 
13436851e7fSLois Curfman McInnes    Level: intermediate
13536851e7fSLois Curfman McInnes 
136e7e93795SLois Curfman McInnes .keywords: SNES, nonlinear, default, monitor, norm
137e7e93795SLois Curfman McInnes 
138a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorSolution()
139e7e93795SLois Curfman McInnes @*/
1407087cfbeSBarry Smith PetscErrorCode  SNESMonitorDefault(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
141e7e93795SLois Curfman McInnes {
142dfbe8321SBarry Smith   PetscErrorCode ierr;
143649052a6SBarry Smith   PetscViewer    viewer = dummy ? (PetscViewer) dummy : PETSC_VIEWER_STDOUT_(((PetscObject)snes)->comm);
144d132466eSBarry Smith 
1453a40ed3dSBarry Smith   PetscFunctionBegin;
146649052a6SBarry Smith   ierr = PetscViewerASCIIAddTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
147649052a6SBarry Smith   ierr = PetscViewerASCIIPrintf(viewer,"%3D SNES Function norm %14.12e \n",its,(double)fgnorm);CHKERRQ(ierr);
148649052a6SBarry Smith   ierr = PetscViewerASCIISubtractTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
1493a40ed3dSBarry Smith   PetscFunctionReturn(0);
150e7e93795SLois Curfman McInnes }
1513f1db9ecSBarry Smith 
152b271bb04SBarry Smith #undef __FUNCT__
153b271bb04SBarry Smith #define __FUNCT__ "SNESMonitorRange_Private"
1547087cfbeSBarry Smith PetscErrorCode  SNESMonitorRange_Private(SNES snes,PetscInt it,PetscReal *per)
155b271bb04SBarry Smith {
156b271bb04SBarry Smith   PetscErrorCode          ierr;
157b271bb04SBarry Smith   Vec                     resid;
158b271bb04SBarry Smith   PetscReal               rmax,pwork;
159b271bb04SBarry Smith   PetscInt                i,n,N;
160b271bb04SBarry Smith   PetscScalar             *r;
161b271bb04SBarry Smith 
162b271bb04SBarry Smith   PetscFunctionBegin;
163b271bb04SBarry Smith   ierr = SNESGetFunction(snes,&resid,0,0);CHKERRQ(ierr);
164b271bb04SBarry Smith   ierr = VecNorm(resid,NORM_INFINITY,&rmax);CHKERRQ(ierr);
165b271bb04SBarry Smith   ierr = VecGetLocalSize(resid,&n);CHKERRQ(ierr);
166b271bb04SBarry Smith   ierr = VecGetSize(resid,&N);CHKERRQ(ierr);
167b271bb04SBarry Smith   ierr = VecGetArray(resid,&r);CHKERRQ(ierr);
168b271bb04SBarry Smith   pwork = 0.0;
169b271bb04SBarry Smith   for (i=0; i<n; i++) {
170b271bb04SBarry Smith     pwork += (PetscAbsScalar(r[i]) > .20*rmax);
171b271bb04SBarry Smith   }
17206a205a8SBarry Smith   ierr = MPI_Allreduce(&pwork,per,1,MPIU_REAL,MPIU_SUM,((PetscObject)snes)->comm);CHKERRQ(ierr);
173b271bb04SBarry Smith   ierr = VecRestoreArray(resid,&r);CHKERRQ(ierr);
174b271bb04SBarry Smith   *per  = *per/N;
175b271bb04SBarry Smith   PetscFunctionReturn(0);
176b271bb04SBarry Smith }
177b271bb04SBarry Smith 
178b271bb04SBarry Smith #undef __FUNCT__
179b271bb04SBarry Smith #define __FUNCT__ "SNESMonitorRange"
180b271bb04SBarry Smith /*@C
181b271bb04SBarry Smith    SNESMonitorRange - Prints the percentage of residual elements that are more then 10 percent of the maximum value.
182b271bb04SBarry Smith 
183b271bb04SBarry Smith    Collective on SNES
184b271bb04SBarry Smith 
185b271bb04SBarry Smith    Input Parameters:
186b271bb04SBarry Smith +  snes   - iterative context
187b271bb04SBarry Smith .  it    - iteration number
188b271bb04SBarry Smith .  rnorm - 2-norm (preconditioned) residual value (may be estimated).
189b271bb04SBarry Smith -  dummy - unused monitor context
190b271bb04SBarry Smith 
191b271bb04SBarry Smith    Options Database Key:
192b271bb04SBarry Smith .  -snes_monitor_range - Activates SNESMonitorRange()
193b271bb04SBarry Smith 
194b271bb04SBarry Smith    Level: intermediate
195b271bb04SBarry Smith 
196b271bb04SBarry Smith .keywords: SNES, default, monitor, residual
197b271bb04SBarry Smith 
198b271bb04SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorDefault(), SNESMonitorLGCreate()
199b271bb04SBarry Smith @*/
2007087cfbeSBarry Smith PetscErrorCode  SNESMonitorRange(SNES snes,PetscInt it,PetscReal rnorm,void *dummy)
201b271bb04SBarry Smith {
202b271bb04SBarry Smith   PetscErrorCode   ierr;
203b271bb04SBarry Smith   PetscReal        perc,rel;
204649052a6SBarry Smith   PetscViewer      viewer = dummy ? (PetscViewer) dummy : PETSC_VIEWER_STDOUT_(((PetscObject)snes)->comm);
205b271bb04SBarry Smith   /* should be in a MonitorRangeContext */
206b271bb04SBarry Smith   static PetscReal prev;
207b271bb04SBarry Smith 
208b271bb04SBarry Smith   PetscFunctionBegin;
209b271bb04SBarry Smith   if (!it) prev = rnorm;
210b271bb04SBarry Smith   ierr = SNESMonitorRange_Private(snes,it,&perc);CHKERRQ(ierr);
211b271bb04SBarry Smith 
212b271bb04SBarry Smith   rel  = (prev - rnorm)/prev;
213b271bb04SBarry Smith   prev = rnorm;
214649052a6SBarry Smith   ierr = PetscViewerASCIIAddTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
215649052a6SBarry Smith   ierr = PetscViewerASCIIPrintf(viewer,"%3D SNES preconditioned resid norm %14.12e Percent values above 20 percent of maximum %5.2f relative decrease %5.2e ratio %5.2e \n",it,(double)rnorm,(double)100.0*perc,(double)rel,(double)rel/perc);CHKERRQ(ierr);
216649052a6SBarry Smith   ierr = PetscViewerASCIISubtractTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
217b271bb04SBarry Smith   PetscFunctionReturn(0);
218b271bb04SBarry Smith }
219b271bb04SBarry Smith 
220eabae89aSBarry Smith typedef struct {
221649052a6SBarry Smith   PetscViewer viewer;
222eabae89aSBarry Smith   PetscReal   *history;
223a6570f20SBarry Smith } SNESMonitorRatioContext;
224eabae89aSBarry Smith 
2253a7fca6bSBarry Smith #undef __FUNCT__
226a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorRatio"
2273a7fca6bSBarry Smith /*@C
228a6570f20SBarry Smith    SNESMonitorRatio - Monitors progress of the SNES solvers by printing the ratio
2294b27c08aSLois Curfman McInnes    of residual norm at each iteration to the previous.
2303a7fca6bSBarry Smith 
2313a7fca6bSBarry Smith    Collective on SNES
2323a7fca6bSBarry Smith 
2333a7fca6bSBarry Smith    Input Parameters:
2343a7fca6bSBarry Smith +  snes - the SNES context
2353a7fca6bSBarry Smith .  its - iteration number
2363a7fca6bSBarry Smith .  fgnorm - 2-norm of residual (or gradient)
237eabae89aSBarry Smith -  dummy -  context of monitor
2383a7fca6bSBarry Smith 
2393a7fca6bSBarry Smith    Level: intermediate
2403a7fca6bSBarry Smith 
2413a7fca6bSBarry Smith .keywords: SNES, nonlinear, monitor, norm
2423a7fca6bSBarry Smith 
243a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorSolution()
2443a7fca6bSBarry Smith @*/
2457087cfbeSBarry Smith PetscErrorCode  SNESMonitorRatio(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
2463a7fca6bSBarry Smith {
247dfbe8321SBarry Smith   PetscErrorCode          ierr;
24877431f27SBarry Smith   PetscInt                len;
24987828ca2SBarry Smith   PetscReal               *history;
250a6570f20SBarry Smith   SNESMonitorRatioContext *ctx = (SNESMonitorRatioContext*)dummy;
2513a7fca6bSBarry Smith 
2523a7fca6bSBarry Smith   PetscFunctionBegin;
2533a7fca6bSBarry Smith   ierr = SNESGetConvergenceHistory(snes,&history,PETSC_NULL,&len);CHKERRQ(ierr);
254649052a6SBarry Smith   ierr = PetscViewerASCIIAddTab(ctx->viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
255958c9bccSBarry Smith   if (!its || !history || its > len) {
256649052a6SBarry Smith     ierr = PetscViewerASCIIPrintf(ctx->viewer,"%3D SNES Function norm %14.12e \n",its,(double)fgnorm);CHKERRQ(ierr);
2573a7fca6bSBarry Smith   } else {
25887828ca2SBarry Smith     PetscReal ratio = fgnorm/history[its-1];
259*8f1a2a5eSBarry Smith     ierr = PetscViewerASCIIPrintf(ctx->viewer,"%3D SNES Function norm %14.12e %14.12e \n",its,(double)fgnorm,(double)ratio);CHKERRQ(ierr);
2603a7fca6bSBarry Smith   }
261649052a6SBarry Smith   ierr = PetscViewerASCIISubtractTab(ctx->viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
2623a7fca6bSBarry Smith   PetscFunctionReturn(0);
2633a7fca6bSBarry Smith }
2643a7fca6bSBarry Smith 
2653a7fca6bSBarry Smith /*
2663a7fca6bSBarry Smith    If the we set the history monitor space then we must destroy it
2673a7fca6bSBarry Smith */
2683a7fca6bSBarry Smith #undef __FUNCT__
269a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorRatioDestroy"
270c2efdce3SBarry Smith PetscErrorCode SNESMonitorRatioDestroy(void **ct)
2713a7fca6bSBarry Smith {
272dfbe8321SBarry Smith   PetscErrorCode          ierr;
273c2efdce3SBarry Smith   SNESMonitorRatioContext *ctx = *(SNESMonitorRatioContext**)ct;
2743a7fca6bSBarry Smith 
2753a7fca6bSBarry Smith   PetscFunctionBegin;
27605b42c5fSBarry Smith   ierr = PetscFree(ctx->history);CHKERRQ(ierr);
277649052a6SBarry Smith   ierr = PetscViewerDestroy(&ctx->viewer);CHKERRQ(ierr);
278eabae89aSBarry Smith   ierr = PetscFree(ctx);CHKERRQ(ierr);
2793a7fca6bSBarry Smith   PetscFunctionReturn(0);
2803a7fca6bSBarry Smith }
2813a7fca6bSBarry Smith 
2823a7fca6bSBarry Smith #undef __FUNCT__
283a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorSetRatio"
2843a7fca6bSBarry Smith /*@C
285a6570f20SBarry Smith    SNESMonitorSetRatio - Sets SNES to use a monitor that prints the
2864b27c08aSLois Curfman McInnes    ratio of the function norm at each iteration.
2873a7fca6bSBarry Smith 
2883a7fca6bSBarry Smith    Collective on SNES
2893a7fca6bSBarry Smith 
2903a7fca6bSBarry Smith    Input Parameters:
291eabae89aSBarry Smith +   snes - the SNES context
292eabae89aSBarry Smith -   viewer - ASCII viewer to print output
2933a7fca6bSBarry Smith 
2943a7fca6bSBarry Smith    Level: intermediate
2953a7fca6bSBarry Smith 
2963a7fca6bSBarry Smith .keywords: SNES, nonlinear, monitor, norm
2973a7fca6bSBarry Smith 
298a6570f20SBarry Smith .seealso: SNESMonitorSet(), SNESMonitorSolution(), SNESMonitorDefault()
2993a7fca6bSBarry Smith @*/
300649052a6SBarry Smith PetscErrorCode  SNESMonitorSetRatio(SNES snes,PetscViewer viewer)
3013a7fca6bSBarry Smith {
302dfbe8321SBarry Smith   PetscErrorCode          ierr;
303a6570f20SBarry Smith   SNESMonitorRatioContext *ctx;
30487828ca2SBarry Smith   PetscReal               *history;
3053a7fca6bSBarry Smith 
3063a7fca6bSBarry Smith   PetscFunctionBegin;
307eabae89aSBarry Smith   if (!viewer) {
308649052a6SBarry Smith     ierr = PetscViewerASCIIOpen(((PetscObject)snes)->comm,"stdout",&viewer);CHKERRQ(ierr);
309eabae89aSBarry Smith     ierr = PetscObjectReference((PetscObject)viewer);CHKERRQ(ierr);
310eabae89aSBarry Smith   }
31138f2d2fdSLisandro Dalcin   ierr = PetscNewLog(snes,SNESMonitorRatioContext,&ctx);
3123a7fca6bSBarry Smith   ierr = SNESGetConvergenceHistory(snes,&history,PETSC_NULL,PETSC_NULL);CHKERRQ(ierr);
3133a7fca6bSBarry Smith   if (!history) {
314eabae89aSBarry Smith     ierr = PetscMalloc(100*sizeof(PetscReal),&ctx->history);CHKERRQ(ierr);
315eabae89aSBarry Smith     ierr = SNESSetConvergenceHistory(snes,ctx->history,0,100,PETSC_TRUE);CHKERRQ(ierr);
3163a7fca6bSBarry Smith   }
317eabae89aSBarry Smith   ctx->viewer = viewer;
318a6570f20SBarry Smith   ierr = SNESMonitorSet(snes,SNESMonitorRatio,ctx,SNESMonitorRatioDestroy);CHKERRQ(ierr);
3193a7fca6bSBarry Smith   PetscFunctionReturn(0);
3203a7fca6bSBarry Smith }
3213a7fca6bSBarry Smith 
322e7e93795SLois Curfman McInnes /* ---------------------------------------------------------------- */
3234a2ae208SSatish Balay #undef __FUNCT__
324a6570f20SBarry Smith #define __FUNCT__ "SNESMonitorDefaultShort"
325be1f7002SBarry Smith /*
326a6570f20SBarry Smith      Default (short) SNES Monitor, same as SNESMonitorDefault() except
327be1f7002SBarry Smith   it prints fewer digits of the residual as the residual gets smaller.
328be1f7002SBarry Smith   This is because the later digits are meaningless and are often
329be1f7002SBarry Smith   different on different machines; by using this routine different
330be1f7002SBarry Smith   machines will usually generate the same output.
331be1f7002SBarry Smith */
3327087cfbeSBarry Smith PetscErrorCode  SNESMonitorDefaultShort(SNES snes,PetscInt its,PetscReal fgnorm,void *dummy)
333e7e93795SLois Curfman McInnes {
334dfbe8321SBarry Smith   PetscErrorCode ierr;
335649052a6SBarry Smith   PetscViewer    viewer = dummy ? (PetscViewer) dummy : PETSC_VIEWER_STDOUT_(((PetscObject)snes)->comm);
336d132466eSBarry Smith 
3373a40ed3dSBarry Smith   PetscFunctionBegin;
338649052a6SBarry Smith   ierr = PetscViewerASCIIAddTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
3398f240d10SBarry Smith   if (fgnorm > 1.e-9) {
340649052a6SBarry Smith     ierr = PetscViewerASCIIPrintf(viewer,"%3D SNES Function norm %G \n",its,fgnorm);CHKERRQ(ierr);
3413a40ed3dSBarry Smith   } else if (fgnorm > 1.e-11){
342649052a6SBarry Smith     ierr = PetscViewerASCIIPrintf(viewer,"%3D SNES Function norm %5.3e \n",its,fgnorm);CHKERRQ(ierr);
3433a40ed3dSBarry Smith   } else {
344649052a6SBarry Smith     ierr = PetscViewerASCIIPrintf(viewer,"%3D SNES Function norm < 1.e-11\n",its);CHKERRQ(ierr);
345a34d58ebSBarry Smith   }
346649052a6SBarry Smith   ierr = PetscViewerASCIISubtractTab(viewer,((PetscObject)snes)->tablevel);CHKERRQ(ierr);
3473a40ed3dSBarry Smith   PetscFunctionReturn(0);
348e7e93795SLois Curfman McInnes }
349e7e93795SLois Curfman McInnes /* ---------------------------------------------------------------- */
3504a2ae208SSatish Balay #undef __FUNCT__
3513f149594SLisandro Dalcin #define __FUNCT__ "SNESDefaultConverged"
3524b828684SBarry Smith /*@C
3533f149594SLisandro Dalcin    SNESDefaultConverged - Convergence test of the solvers for
354f525115eSLois Curfman McInnes    systems of nonlinear equations (default).
355e7e93795SLois Curfman McInnes 
356c7afd0dbSLois Curfman McInnes    Collective on SNES
357c7afd0dbSLois Curfman McInnes 
358e7e93795SLois Curfman McInnes    Input Parameters:
359c7afd0dbSLois Curfman McInnes +  snes - the SNES context
36006ee9f85SBarry Smith .  it - the iteration (0 indicates before any Newton steps)
361e7e93795SLois Curfman McInnes .  xnorm - 2-norm of current iterate
362e7e93795SLois Curfman McInnes .  pnorm - 2-norm of current step
3637f3332b4SBarry Smith .  fnorm - 2-norm of function at current iterate
364c7afd0dbSLois Curfman McInnes -  dummy - unused context
365e7e93795SLois Curfman McInnes 
366184914b5SBarry Smith    Output Parameter:
367184914b5SBarry Smith .   reason  - one of
36870441072SBarry Smith $  SNES_CONVERGED_FNORM_ABS       - (fnorm < abstol),
3693304466cSBarry Smith $  SNES_CONVERGED_PNORM_RELATIVE  - (pnorm < xtol*xnorm),
370184914b5SBarry Smith $  SNES_CONVERGED_FNORM_RELATIVE  - (fnorm < rtol*fnorm0),
371184914b5SBarry Smith $  SNES_DIVERGED_FUNCTION_COUNT   - (nfct > maxf),
372184914b5SBarry Smith $  SNES_DIVERGED_FNORM_NAN        - (fnorm == NaN),
373184914b5SBarry Smith $  SNES_CONVERGED_ITERATING       - (otherwise),
374e7e93795SLois Curfman McInnes 
375e7e93795SLois Curfman McInnes    where
376c7afd0dbSLois Curfman McInnes +    maxf - maximum number of function evaluations,
377c7afd0dbSLois Curfman McInnes             set with SNESSetTolerances()
378c7afd0dbSLois Curfman McInnes .    nfct - number of function evaluations,
37970441072SBarry Smith .    abstol - absolute function norm tolerance,
380c7afd0dbSLois Curfman McInnes             set with SNESSetTolerances()
381c7afd0dbSLois Curfman McInnes -    rtol - relative function norm tolerance, set with SNESSetTolerances()
382fee21e36SBarry Smith 
38336851e7fSLois Curfman McInnes    Level: intermediate
38436851e7fSLois Curfman McInnes 
385e7e93795SLois Curfman McInnes .keywords: SNES, nonlinear, default, converged, convergence
386e7e93795SLois Curfman McInnes 
38771f87433Sdalcinl .seealso: SNESSetConvergenceTest()
388e7e93795SLois Curfman McInnes @*/
3897087cfbeSBarry Smith PetscErrorCode  SNESDefaultConverged(SNES snes,PetscInt it,PetscReal xnorm,PetscReal pnorm,PetscReal fnorm,SNESConvergedReason *reason,void *dummy)
390e7e93795SLois Curfman McInnes {
39163ba0a88SBarry Smith   PetscErrorCode ierr;
39263ba0a88SBarry Smith 
3933a40ed3dSBarry Smith   PetscFunctionBegin;
3940700a824SBarry Smith   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3953f149594SLisandro Dalcin   PetscValidPointer(reason,6);
3963f149594SLisandro Dalcin 
39706ee9f85SBarry Smith   *reason = SNES_CONVERGED_ITERATING;
39806ee9f85SBarry Smith 
39906ee9f85SBarry Smith   if (!it) {
40006ee9f85SBarry Smith     /* set parameter for default relative tolerance convergence test */
40106ee9f85SBarry Smith     snes->ttol = fnorm*snes->rtol;
40206ee9f85SBarry Smith   }
403d252947aSBarry Smith   if (fnorm != fnorm) {
404ae15b995SBarry Smith     ierr = PetscInfo(snes,"Failed to converged, function norm is NaN\n");CHKERRQ(ierr);
405184914b5SBarry Smith     *reason = SNES_DIVERGED_FNORM_NAN;
40670441072SBarry Smith   } else if (fnorm < snes->abstol) {
407*8f1a2a5eSBarry Smith     ierr = PetscInfo2(snes,"Converged due to function norm %14.12e < %14.12e\n",(double)fnorm,(double)snes->abstol);CHKERRQ(ierr);
408184914b5SBarry Smith     *reason = SNES_CONVERGED_FNORM_ABS;
40943e71028SBarry Smith   } else if (snes->nfuncs >= snes->max_funcs) {
410ae15b995SBarry Smith     ierr = PetscInfo2(snes,"Exceeded maximum number of function evaluations: %D > %D\n",snes->nfuncs,snes->max_funcs);CHKERRQ(ierr);
411184914b5SBarry Smith     *reason = SNES_DIVERGED_FUNCTION_COUNT;
41206ee9f85SBarry Smith   }
41306ee9f85SBarry Smith 
41406ee9f85SBarry Smith   if (it && !*reason) {
41506ee9f85SBarry Smith     if (fnorm <= snes->ttol) {
416*8f1a2a5eSBarry Smith       ierr = PetscInfo2(snes,"Converged due to function norm %14.12e < %14.12e (relative tolerance)\n",(double)fnorm,(double)snes->ttol);CHKERRQ(ierr);
41706ee9f85SBarry Smith       *reason = SNES_CONVERGED_FNORM_RELATIVE;
41806ee9f85SBarry Smith     } else if (pnorm < snes->xtol*xnorm) {
419*8f1a2a5eSBarry Smith       ierr = PetscInfo3(snes,"Converged due to small update length: %14.12e < %14.12e * %14.12e\n",(double)pnorm,(double)snes->xtol,(double)xnorm);CHKERRQ(ierr);
42006ee9f85SBarry Smith       *reason = SNES_CONVERGED_PNORM_RELATIVE;
42106ee9f85SBarry Smith     }
422e7e93795SLois Curfman McInnes   }
4233a40ed3dSBarry Smith   PetscFunctionReturn(0);
424e7e93795SLois Curfman McInnes }
4253f149594SLisandro Dalcin 
4263f149594SLisandro Dalcin #undef __FUNCT__
4273f149594SLisandro Dalcin #define __FUNCT__ "SNESSkipConverged"
4283f149594SLisandro Dalcin /*@C
4293f149594SLisandro Dalcin    SNESSkipConverged - Convergence test for SNES that NEVER returns as
4303f149594SLisandro Dalcin    converged, UNLESS the maximum number of iteration have been reached.
4313f149594SLisandro Dalcin 
4323f9fe445SBarry Smith    Logically Collective on SNES
4333f149594SLisandro Dalcin 
4343f149594SLisandro Dalcin    Input Parameters:
4353f149594SLisandro Dalcin +  snes - the SNES context
4363f149594SLisandro Dalcin .  it - the iteration (0 indicates before any Newton steps)
4373f149594SLisandro Dalcin .  xnorm - 2-norm of current iterate
4383f149594SLisandro Dalcin .  pnorm - 2-norm of current step
4393f149594SLisandro Dalcin .  fnorm - 2-norm of function at current iterate
4403f149594SLisandro Dalcin -  dummy - unused context
4413f149594SLisandro Dalcin 
4423f149594SLisandro Dalcin    Output Parameter:
44385385478SLisandro Dalcin .   reason  - SNES_CONVERGED_ITERATING, SNES_CONVERGED_ITS, or SNES_DIVERGED_FNORM_NAN
4443f149594SLisandro Dalcin 
4453f149594SLisandro Dalcin    Notes:
4463f149594SLisandro Dalcin    Convergence is then declared after a fixed number of iterations have been used.
4473f149594SLisandro Dalcin 
4483f149594SLisandro Dalcin    Level: advanced
4493f149594SLisandro Dalcin 
4503f149594SLisandro Dalcin .keywords: SNES, nonlinear, skip, converged, convergence
4513f149594SLisandro Dalcin 
4523f149594SLisandro Dalcin .seealso: SNESSetConvergenceTest()
4533f149594SLisandro Dalcin @*/
4547087cfbeSBarry Smith PetscErrorCode  SNESSkipConverged(SNES snes,PetscInt it,PetscReal xnorm,PetscReal pnorm,PetscReal fnorm,SNESConvergedReason *reason,void *dummy)
4553f149594SLisandro Dalcin {
4563f149594SLisandro Dalcin   PetscErrorCode ierr;
4573f149594SLisandro Dalcin 
4583f149594SLisandro Dalcin   PetscFunctionBegin;
4590700a824SBarry Smith   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4603f149594SLisandro Dalcin   PetscValidPointer(reason,6);
4613f149594SLisandro Dalcin 
4623f149594SLisandro Dalcin   *reason = SNES_CONVERGED_ITERATING;
4633f149594SLisandro Dalcin 
4643f149594SLisandro Dalcin   if (fnorm != fnorm) {
4653f149594SLisandro Dalcin     ierr = PetscInfo(snes,"Failed to converged, function norm is NaN\n");CHKERRQ(ierr);
4663f149594SLisandro Dalcin     *reason = SNES_DIVERGED_FNORM_NAN;
4673f149594SLisandro Dalcin   } else if(it == snes->max_its) {
4683f149594SLisandro Dalcin     *reason = SNES_CONVERGED_ITS;
4693f149594SLisandro Dalcin   }
4703f149594SLisandro Dalcin   PetscFunctionReturn(0);
4713f149594SLisandro Dalcin }
4723f149594SLisandro Dalcin 
47358c9b817SLisandro Dalcin #undef __FUNCT__
47458c9b817SLisandro Dalcin #define __FUNCT__ "SNESDefaultGetWork"
47598acb6afSMatthew G Knepley /*@
47658c9b817SLisandro Dalcin   SNESDefaultGetWork - Gets a number of work vectors.
47758c9b817SLisandro Dalcin 
47858c9b817SLisandro Dalcin   Input Parameters:
47958c9b817SLisandro Dalcin . snes  - the SNES context
48058c9b817SLisandro Dalcin . nw - number of work vectors to allocate
48158c9b817SLisandro Dalcin 
48258c9b817SLisandro Dalcin    Level: developer
48358c9b817SLisandro Dalcin 
48458c9b817SLisandro Dalcin   Notes:
48558c9b817SLisandro Dalcin   Call this only if no work vectors have been allocated
48698acb6afSMatthew G Knepley @*/
48758c9b817SLisandro Dalcin PetscErrorCode SNESDefaultGetWork(SNES snes,PetscInt nw)
48858c9b817SLisandro Dalcin {
48958c9b817SLisandro Dalcin   PetscErrorCode ierr;
49058c9b817SLisandro Dalcin 
49158c9b817SLisandro Dalcin   PetscFunctionBegin;
49258c9b817SLisandro Dalcin   if (snes->work) {ierr = VecDestroyVecs(snes->nwork,&snes->work);CHKERRQ(ierr);}
49358c9b817SLisandro Dalcin   snes->nwork = nw;
49458c9b817SLisandro Dalcin   ierr = VecDuplicateVecs(snes->vec_sol,snes->nwork,&snes->work);CHKERRQ(ierr);
49558c9b817SLisandro Dalcin   ierr = PetscLogObjectParents(snes,nw,snes->work);CHKERRQ(ierr);
49658c9b817SLisandro Dalcin   PetscFunctionReturn(0);
49758c9b817SLisandro Dalcin }
498