xref: /petsc/src/snes/interface/snes.c (revision f97672e55eacc8688507b9471cd7ec2664d7f203)
1 #include <petsc/private/snesimpl.h>      /*I "petscsnes.h"  I*/
2 #include <petscdmshell.h>
3 #include <petscdraw.h>
4 #include <petscds.h>
5 #include <petscdmadaptor.h>
6 #include <petscconvest.h>
7 
8 PetscBool         SNESRegisterAllCalled = PETSC_FALSE;
9 PetscFunctionList SNESList              = NULL;
10 
11 /* Logging support */
12 PetscClassId  SNES_CLASSID, DMSNES_CLASSID;
13 PetscLogEvent SNES_Solve, SNES_Setup, SNES_FunctionEval, SNES_JacobianEval, SNES_NGSEval, SNES_NGSFuncEval, SNES_NPCSolve, SNES_ObjectiveEval;
14 
15 /*@
16    SNESSetErrorIfNotConverged - Causes SNESSolve() to generate an error if the solver has not converged.
17 
18    Logically Collective on SNES
19 
20    Input Parameters:
21 +  snes - iterative context obtained from SNESCreate()
22 -  flg - PETSC_TRUE indicates you want the error generated
23 
24    Options database keys:
25 .  -snes_error_if_not_converged <true,false> - cause an immediate error condition and stop the program if the solver does not converge
26 
27    Level: intermediate
28 
29    Notes:
30     Normally PETSc continues if a linear solver fails to converge, you can call SNESGetConvergedReason() after a SNESSolve()
31     to determine if it has converged.
32 
33 .seealso: `SNESGetErrorIfNotConverged()`, `KSPGetErrorIfNotConverged()`, `KSPSetErrorIfNotConverged()`
34 @*/
35 PetscErrorCode  SNESSetErrorIfNotConverged(SNES snes,PetscBool flg)
36 {
37   PetscFunctionBegin;
38   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
39   PetscValidLogicalCollectiveBool(snes,flg,2);
40   snes->errorifnotconverged = flg;
41   PetscFunctionReturn(0);
42 }
43 
44 /*@
45    SNESGetErrorIfNotConverged - Will SNESSolve() generate an error if the solver does not converge?
46 
47    Not Collective
48 
49    Input Parameter:
50 .  snes - iterative context obtained from SNESCreate()
51 
52    Output Parameter:
53 .  flag - PETSC_TRUE if it will generate an error, else PETSC_FALSE
54 
55    Level: intermediate
56 
57 .seealso: `SNESSetErrorIfNotConverged()`, `KSPGetErrorIfNotConverged()`, `KSPSetErrorIfNotConverged()`
58 @*/
59 PetscErrorCode  SNESGetErrorIfNotConverged(SNES snes,PetscBool  *flag)
60 {
61   PetscFunctionBegin;
62   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
63   PetscValidBoolPointer(flag,2);
64   *flag = snes->errorifnotconverged;
65   PetscFunctionReturn(0);
66 }
67 
68 /*@
69     SNESSetAlwaysComputesFinalResidual - does the SNES always compute the residual at the final solution?
70 
71    Logically Collective on SNES
72 
73     Input Parameters:
74 +   snes - the shell SNES
75 -   flg - is the residual computed?
76 
77    Level: advanced
78 
79 .seealso: `SNESGetAlwaysComputesFinalResidual()`
80 @*/
81 PetscErrorCode  SNESSetAlwaysComputesFinalResidual(SNES snes, PetscBool flg)
82 {
83   PetscFunctionBegin;
84   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
85   snes->alwayscomputesfinalresidual = flg;
86   PetscFunctionReturn(0);
87 }
88 
89 /*@
90     SNESGetAlwaysComputesFinalResidual - does the SNES always compute the residual at the final solution?
91 
92    Logically Collective on SNES
93 
94     Input Parameter:
95 .   snes - the shell SNES
96 
97     Output Parameter:
98 .   flg - is the residual computed?
99 
100    Level: advanced
101 
102 .seealso: `SNESSetAlwaysComputesFinalResidual()`
103 @*/
104 PetscErrorCode  SNESGetAlwaysComputesFinalResidual(SNES snes, PetscBool *flg)
105 {
106   PetscFunctionBegin;
107   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
108   *flg = snes->alwayscomputesfinalresidual;
109   PetscFunctionReturn(0);
110 }
111 
112 /*@
113    SNESSetFunctionDomainError - tells SNES that the input vector to your SNESFunction is not
114      in the functions domain. For example, negative pressure.
115 
116    Logically Collective on SNES
117 
118    Input Parameters:
119 .  snes - the SNES context
120 
121    Level: advanced
122 
123 .seealso: `SNESCreate()`, `SNESSetFunction()`, `SNESFunction`
124 @*/
125 PetscErrorCode  SNESSetFunctionDomainError(SNES snes)
126 {
127   PetscFunctionBegin;
128   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
129   PetscCheck(!snes->errorifnotconverged,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"User code indicates input vector is not in the function domain");
130   snes->domainerror = PETSC_TRUE;
131   PetscFunctionReturn(0);
132 }
133 
134 /*@
135    SNESSetJacobianDomainError - tells SNES that computeJacobian does not make sense any more. For example there is a negative element transformation.
136 
137    Logically Collective on SNES
138 
139    Input Parameters:
140 .  snes - the SNES context
141 
142    Level: advanced
143 
144 .seealso: `SNESCreate()`, `SNESSetFunction()`, `SNESFunction()`, `SNESSetFunctionDomainError()`
145 @*/
146 PetscErrorCode SNESSetJacobianDomainError(SNES snes)
147 {
148   PetscFunctionBegin;
149   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
150   PetscCheck(!snes->errorifnotconverged,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"User code indicates computeJacobian does not make sense");
151   snes->jacobiandomainerror = PETSC_TRUE;
152   PetscFunctionReturn(0);
153 }
154 
155 /*@
156    SNESSetCheckJacobianDomainError - if or not to check jacobian domain error after each Jacobian evaluation. By default, we check Jacobian domain error
157    in the debug mode, and do not check it in the optimized mode.
158 
159    Logically Collective on SNES
160 
161    Input Parameters:
162 +  snes - the SNES context
163 -  flg  - indicates if or not to check jacobian domain error after each Jacobian evaluation
164 
165    Level: advanced
166 
167 .seealso: `SNESCreate()`, `SNESSetFunction()`, `SNESFunction()`, `SNESSetFunctionDomainError()`, `SNESGetCheckJacobianDomainError()`
168 @*/
169 PetscErrorCode SNESSetCheckJacobianDomainError(SNES snes, PetscBool flg)
170 {
171   PetscFunctionBegin;
172   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
173   snes->checkjacdomainerror = flg;
174   PetscFunctionReturn(0);
175 }
176 
177 /*@
178    SNESGetCheckJacobianDomainError - Get an indicator whether or not we are checking Jacobian domain errors after each Jacobian evaluation.
179 
180    Logically Collective on SNES
181 
182    Input Parameters:
183 .  snes - the SNES context
184 
185    Output Parameters:
186 .  flg  - PETSC_FALSE indicates that we don't check jacobian domain errors after each Jacobian evaluation
187 
188    Level: advanced
189 
190 .seealso: `SNESCreate()`, `SNESSetFunction()`, `SNESFunction()`, `SNESSetFunctionDomainError()`, `SNESSetCheckJacobianDomainError()`
191 @*/
192 PetscErrorCode SNESGetCheckJacobianDomainError(SNES snes, PetscBool *flg)
193 {
194   PetscFunctionBegin;
195   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
196   PetscValidBoolPointer(flg,2);
197   *flg = snes->checkjacdomainerror;
198   PetscFunctionReturn(0);
199 }
200 
201 /*@
202    SNESGetFunctionDomainError - Gets the status of the domain error after a call to SNESComputeFunction;
203 
204    Logically Collective on SNES
205 
206    Input Parameters:
207 .  snes - the SNES context
208 
209    Output Parameters:
210 .  domainerror - Set to PETSC_TRUE if there's a domain error; PETSC_FALSE otherwise.
211 
212    Level: advanced
213 
214 .seealso: `SNESSetFunctionDomainError()`, `SNESComputeFunction()`
215 @*/
216 PetscErrorCode  SNESGetFunctionDomainError(SNES snes, PetscBool *domainerror)
217 {
218   PetscFunctionBegin;
219   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
220   PetscValidBoolPointer(domainerror,2);
221   *domainerror = snes->domainerror;
222   PetscFunctionReturn(0);
223 }
224 
225 /*@
226    SNESGetJacobianDomainError - Gets the status of the Jacobian domain error after a call to SNESComputeJacobian;
227 
228    Logically Collective on SNES
229 
230    Input Parameters:
231 .  snes - the SNES context
232 
233    Output Parameters:
234 .  domainerror - Set to PETSC_TRUE if there's a jacobian domain error; PETSC_FALSE otherwise.
235 
236    Level: advanced
237 
238 .seealso: `SNESSetFunctionDomainError()`, `SNESComputeFunction(),SNESGetFunctionDomainError()`
239 @*/
240 PetscErrorCode SNESGetJacobianDomainError(SNES snes, PetscBool *domainerror)
241 {
242   PetscFunctionBegin;
243   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
244   PetscValidBoolPointer(domainerror,2);
245   *domainerror = snes->jacobiandomainerror;
246   PetscFunctionReturn(0);
247 }
248 
249 /*@C
250   SNESLoad - Loads a SNES that has been stored in binary  with SNESView().
251 
252   Collective on PetscViewer
253 
254   Input Parameters:
255 + newdm - the newly loaded SNES, this needs to have been created with SNESCreate() or
256            some related function before a call to SNESLoad().
257 - viewer - binary file viewer, obtained from PetscViewerBinaryOpen()
258 
259    Level: intermediate
260 
261   Notes:
262    The type is determined by the data in the file, any type set into the SNES before this call is ignored.
263 
264   Notes for advanced users:
265   Most users should not need to know the details of the binary storage
266   format, since SNESLoad() and TSView() completely hide these details.
267   But for anyone who's interested, the standard binary matrix storage
268   format is
269 .vb
270      has not yet been determined
271 .ve
272 
273 .seealso: `PetscViewerBinaryOpen()`, `SNESView()`, `MatLoad()`, `VecLoad()`
274 @*/
275 PetscErrorCode  SNESLoad(SNES snes, PetscViewer viewer)
276 {
277   PetscBool      isbinary;
278   PetscInt       classid;
279   char           type[256];
280   KSP            ksp;
281   DM             dm;
282   DMSNES         dmsnes;
283 
284   PetscFunctionBegin;
285   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
286   PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2);
287   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERBINARY,&isbinary));
288   PetscCheck(isbinary,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Invalid viewer; open viewer with PetscViewerBinaryOpen()");
289 
290   PetscCall(PetscViewerBinaryRead(viewer,&classid,1,NULL,PETSC_INT));
291   PetscCheck(classid == SNES_FILE_CLASSID,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_WRONG,"Not SNES next in file");
292   PetscCall(PetscViewerBinaryRead(viewer,type,256,NULL,PETSC_CHAR));
293   PetscCall(SNESSetType(snes, type));
294   if (snes->ops->load) {
295     PetscCall((*snes->ops->load)(snes,viewer));
296   }
297   PetscCall(SNESGetDM(snes,&dm));
298   PetscCall(DMGetDMSNES(dm,&dmsnes));
299   PetscCall(DMSNESLoad(dmsnes,viewer));
300   PetscCall(SNESGetKSP(snes,&ksp));
301   PetscCall(KSPLoad(ksp,viewer));
302   PetscFunctionReturn(0);
303 }
304 
305 #include <petscdraw.h>
306 #if defined(PETSC_HAVE_SAWS)
307 #include <petscviewersaws.h>
308 #endif
309 
310 /*@C
311    SNESViewFromOptions - View from Options
312 
313    Collective on SNES
314 
315    Input Parameters:
316 +  A - the application ordering context
317 .  obj - Optional object
318 -  name - command line option
319 
320    Level: intermediate
321 .seealso: `SNES`, `SNESView`, `PetscObjectViewFromOptions()`, `SNESCreate()`
322 @*/
323 PetscErrorCode  SNESViewFromOptions(SNES A,PetscObject obj,const char name[])
324 {
325   PetscFunctionBegin;
326   PetscValidHeaderSpecific(A,SNES_CLASSID,1);
327   PetscCall(PetscObjectViewFromOptions((PetscObject)A,obj,name));
328   PetscFunctionReturn(0);
329 }
330 
331 PETSC_EXTERN PetscErrorCode SNESComputeJacobian_DMDA(SNES,Vec,Mat,Mat,void*);
332 
333 /*@C
334    SNESView - Prints the SNES data structure.
335 
336    Collective on SNES
337 
338    Input Parameters:
339 +  SNES - the SNES context
340 -  viewer - visualization context
341 
342    Options Database Key:
343 .  -snes_view - Calls SNESView() at end of SNESSolve()
344 
345    Notes:
346    The available visualization contexts include
347 +     PETSC_VIEWER_STDOUT_SELF - standard output (default)
348 -     PETSC_VIEWER_STDOUT_WORLD - synchronized standard
349          output where only the first processor opens
350          the file.  All other processors send their
351          data to the first processor to print.
352 
353    The available formats include
354 +     PETSC_VIEWER_DEFAULT - standard output (default)
355 -     PETSC_VIEWER_ASCII_INFO_DETAIL - more verbose output for SNESNASM
356 
357    The user can open an alternative visualization context with
358    PetscViewerASCIIOpen() - output to a specified file.
359 
360   In the debugger you can do "call SNESView(snes,0)" to display the SNES solver. (The same holds for any PETSc object viewer).
361 
362    Level: beginner
363 
364 .seealso: `PetscViewerASCIIOpen()`
365 @*/
366 PetscErrorCode  SNESView(SNES snes,PetscViewer viewer)
367 {
368   SNESKSPEW      *kctx;
369   KSP            ksp;
370   SNESLineSearch linesearch;
371   PetscBool      iascii,isstring,isbinary,isdraw;
372   DMSNES         dmsnes;
373 #if defined(PETSC_HAVE_SAWS)
374   PetscBool      issaws;
375 #endif
376 
377   PetscFunctionBegin;
378   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
379   if (!viewer) {
380     PetscCall(PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)snes),&viewer));
381   }
382   PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2);
383   PetscCheckSameComm(snes,1,viewer,2);
384 
385   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii));
386   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring));
387   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERBINARY,&isbinary));
388   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERDRAW,&isdraw));
389 #if defined(PETSC_HAVE_SAWS)
390   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSAWS,&issaws));
391 #endif
392   if (iascii) {
393     SNESNormSchedule normschedule;
394     DM               dm;
395     PetscErrorCode   (*cJ)(SNES,Vec,Mat,Mat,void*);
396     void             *ctx;
397     const char       *pre = "";
398 
399     PetscCall(PetscObjectPrintClassNamePrefixType((PetscObject)snes,viewer));
400     if (!snes->setupcalled) {
401       PetscCall(PetscViewerASCIIPrintf(viewer,"  SNES has not been set up so information may be incomplete\n"));
402     }
403     if (snes->ops->view) {
404       PetscCall(PetscViewerASCIIPushTab(viewer));
405       PetscCall((*snes->ops->view)(snes,viewer));
406       PetscCall(PetscViewerASCIIPopTab(viewer));
407     }
408     PetscCall(PetscViewerASCIIPrintf(viewer,"  maximum iterations=%" PetscInt_FMT ", maximum function evaluations=%" PetscInt_FMT "\n",snes->max_its,snes->max_funcs));
409     PetscCall(PetscViewerASCIIPrintf(viewer,"  tolerances: relative=%g, absolute=%g, solution=%g\n",(double)snes->rtol,(double)snes->abstol,(double)snes->stol));
410     if (snes->usesksp) {
411       PetscCall(PetscViewerASCIIPrintf(viewer,"  total number of linear solver iterations=%" PetscInt_FMT "\n",snes->linear_its));
412     }
413     PetscCall(PetscViewerASCIIPrintf(viewer,"  total number of function evaluations=%" PetscInt_FMT "\n",snes->nfuncs));
414     PetscCall(SNESGetNormSchedule(snes, &normschedule));
415     if (normschedule > 0) PetscCall(PetscViewerASCIIPrintf(viewer,"  norm schedule %s\n",SNESNormSchedules[normschedule]));
416     if (snes->gridsequence) {
417       PetscCall(PetscViewerASCIIPrintf(viewer,"  total number of grid sequence refinements=%" PetscInt_FMT "\n",snes->gridsequence));
418     }
419     if (snes->ksp_ewconv) {
420       kctx = (SNESKSPEW*)snes->kspconvctx;
421       if (kctx) {
422         PetscCall(PetscViewerASCIIPrintf(viewer,"  Eisenstat-Walker computation of KSP relative tolerance (version %" PetscInt_FMT ")\n",kctx->version));
423         PetscCall(PetscViewerASCIIPrintf(viewer,"    rtol_0=%g, rtol_max=%g, threshold=%g\n",(double)kctx->rtol_0,(double)kctx->rtol_max,(double)kctx->threshold));
424         PetscCall(PetscViewerASCIIPrintf(viewer,"    gamma=%g, alpha=%g, alpha2=%g\n",(double)kctx->gamma,(double)kctx->alpha,(double)kctx->alpha2));
425       }
426     }
427     if (snes->lagpreconditioner == -1) {
428       PetscCall(PetscViewerASCIIPrintf(viewer,"  Preconditioned is never rebuilt\n"));
429     } else if (snes->lagpreconditioner > 1) {
430       PetscCall(PetscViewerASCIIPrintf(viewer,"  Preconditioned is rebuilt every %" PetscInt_FMT " new Jacobians\n",snes->lagpreconditioner));
431     }
432     if (snes->lagjacobian == -1) {
433       PetscCall(PetscViewerASCIIPrintf(viewer,"  Jacobian is never rebuilt\n"));
434     } else if (snes->lagjacobian > 1) {
435       PetscCall(PetscViewerASCIIPrintf(viewer,"  Jacobian is rebuilt every %" PetscInt_FMT " SNES iterations\n",snes->lagjacobian));
436     }
437     PetscCall(SNESGetDM(snes,&dm));
438     PetscCall(DMSNESGetJacobian(dm,&cJ,&ctx));
439     if (snes->mf_operator) {
440       PetscCall(PetscViewerASCIIPrintf(viewer,"  Jacobian is applied matrix-free with differencing\n"));
441       pre  = "Preconditioning ";
442     }
443     if (cJ == SNESComputeJacobianDefault) {
444       PetscCall(PetscViewerASCIIPrintf(viewer,"  %sJacobian is built using finite differences one column at a time\n",pre));
445     } else if (cJ == SNESComputeJacobianDefaultColor) {
446       PetscCall(PetscViewerASCIIPrintf(viewer,"  %sJacobian is built using finite differences with coloring\n",pre));
447     /* it slightly breaks data encapsulation for access the DMDA information directly */
448     } else if (cJ == SNESComputeJacobian_DMDA) {
449       MatFDColoring fdcoloring;
450       PetscCall(PetscObjectQuery((PetscObject)dm,"DMDASNES_FDCOLORING",(PetscObject*)&fdcoloring));
451       if (fdcoloring) {
452         PetscCall(PetscViewerASCIIPrintf(viewer,"  %sJacobian is built using colored finite differences on a DMDA\n",pre));
453       } else {
454         PetscCall(PetscViewerASCIIPrintf(viewer,"  %sJacobian is built using a DMDA local Jacobian\n",pre));
455       }
456     } else if (snes->mf) {
457       PetscCall(PetscViewerASCIIPrintf(viewer,"  Jacobian is applied matrix-free with differencing, no explicit Jacobian\n"));
458     }
459   } else if (isstring) {
460     const char *type;
461     PetscCall(SNESGetType(snes,&type));
462     PetscCall(PetscViewerStringSPrintf(viewer," SNESType: %-7.7s",type));
463     if (snes->ops->view) PetscCall((*snes->ops->view)(snes,viewer));
464   } else if (isbinary) {
465     PetscInt    classid = SNES_FILE_CLASSID;
466     MPI_Comm    comm;
467     PetscMPIInt rank;
468     char        type[256];
469 
470     PetscCall(PetscObjectGetComm((PetscObject)snes,&comm));
471     PetscCallMPI(MPI_Comm_rank(comm,&rank));
472     if (rank == 0) {
473       PetscCall(PetscViewerBinaryWrite(viewer,&classid,1,PETSC_INT));
474       PetscCall(PetscStrncpy(type,((PetscObject)snes)->type_name,sizeof(type)));
475       PetscCall(PetscViewerBinaryWrite(viewer,type,sizeof(type),PETSC_CHAR));
476     }
477     if (snes->ops->view) {
478       PetscCall((*snes->ops->view)(snes,viewer));
479     }
480   } else if (isdraw) {
481     PetscDraw draw;
482     char      str[36];
483     PetscReal x,y,bottom,h;
484 
485     PetscCall(PetscViewerDrawGetDraw(viewer,0,&draw));
486     PetscCall(PetscDrawGetCurrentPoint(draw,&x,&y));
487     PetscCall(PetscStrncpy(str,"SNES: ",sizeof(str)));
488     PetscCall(PetscStrlcat(str,((PetscObject)snes)->type_name,sizeof(str)));
489     PetscCall(PetscDrawStringBoxed(draw,x,y,PETSC_DRAW_BLUE,PETSC_DRAW_BLACK,str,NULL,&h));
490     bottom = y - h;
491     PetscCall(PetscDrawPushCurrentPoint(draw,x,bottom));
492     if (snes->ops->view) {
493       PetscCall((*snes->ops->view)(snes,viewer));
494     }
495 #if defined(PETSC_HAVE_SAWS)
496   } else if (issaws) {
497     PetscMPIInt rank;
498     const char *name;
499 
500     PetscCall(PetscObjectGetName((PetscObject)snes,&name));
501     PetscCallMPI(MPI_Comm_rank(PETSC_COMM_WORLD,&rank));
502     if (!((PetscObject)snes)->amsmem && rank == 0) {
503       char       dir[1024];
504 
505       PetscCall(PetscObjectViewSAWs((PetscObject)snes,viewer));
506       PetscCall(PetscSNPrintf(dir,1024,"/PETSc/Objects/%s/its",name));
507       PetscStackCallSAWs(SAWs_Register,(dir,&snes->iter,1,SAWs_READ,SAWs_INT));
508       if (!snes->conv_hist) {
509         PetscCall(SNESSetConvergenceHistory(snes,NULL,NULL,PETSC_DECIDE,PETSC_TRUE));
510       }
511       PetscCall(PetscSNPrintf(dir,1024,"/PETSc/Objects/%s/conv_hist",name));
512       PetscStackCallSAWs(SAWs_Register,(dir,snes->conv_hist,10,SAWs_READ,SAWs_DOUBLE));
513     }
514 #endif
515   }
516   if (snes->linesearch) {
517     PetscCall(SNESGetLineSearch(snes, &linesearch));
518     PetscCall(PetscViewerASCIIPushTab(viewer));
519     PetscCall(SNESLineSearchView(linesearch, viewer));
520     PetscCall(PetscViewerASCIIPopTab(viewer));
521   }
522   if (snes->npc && snes->usesnpc) {
523     PetscCall(PetscViewerASCIIPushTab(viewer));
524     PetscCall(SNESView(snes->npc, viewer));
525     PetscCall(PetscViewerASCIIPopTab(viewer));
526   }
527   PetscCall(PetscViewerASCIIPushTab(viewer));
528   PetscCall(DMGetDMSNES(snes->dm,&dmsnes));
529   PetscCall(DMSNESView(dmsnes, viewer));
530   PetscCall(PetscViewerASCIIPopTab(viewer));
531   if (snes->usesksp) {
532     PetscCall(SNESGetKSP(snes,&ksp));
533     PetscCall(PetscViewerASCIIPushTab(viewer));
534     PetscCall(KSPView(ksp,viewer));
535     PetscCall(PetscViewerASCIIPopTab(viewer));
536   }
537   if (isdraw) {
538     PetscDraw draw;
539     PetscCall(PetscViewerDrawGetDraw(viewer,0,&draw));
540     PetscCall(PetscDrawPopCurrentPoint(draw));
541   }
542   PetscFunctionReturn(0);
543 }
544 
545 /*
546   We retain a list of functions that also take SNES command
547   line options. These are called at the end SNESSetFromOptions()
548 */
549 #define MAXSETFROMOPTIONS 5
550 static PetscInt numberofsetfromoptions;
551 static PetscErrorCode (*othersetfromoptions[MAXSETFROMOPTIONS])(SNES);
552 
553 /*@C
554   SNESAddOptionsChecker - Adds an additional function to check for SNES options.
555 
556   Not Collective
557 
558   Input Parameter:
559 . snescheck - function that checks for options
560 
561   Level: developer
562 
563 .seealso: `SNESSetFromOptions()`
564 @*/
565 PetscErrorCode  SNESAddOptionsChecker(PetscErrorCode (*snescheck)(SNES))
566 {
567   PetscFunctionBegin;
568   PetscCheck(numberofsetfromoptions < MAXSETFROMOPTIONS,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE, "Too many options checkers, only %d allowed", MAXSETFROMOPTIONS);
569   othersetfromoptions[numberofsetfromoptions++] = snescheck;
570   PetscFunctionReturn(0);
571 }
572 
573 PETSC_INTERN PetscErrorCode SNESDefaultMatrixFreeCreate2(SNES,Vec,Mat*);
574 
575 static PetscErrorCode SNESSetUpMatrixFree_Private(SNES snes, PetscBool hasOperator, PetscInt version)
576 {
577   Mat            J;
578   MatNullSpace   nullsp;
579 
580   PetscFunctionBegin;
581   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
582 
583   if (!snes->vec_func && (snes->jacobian || snes->jacobian_pre)) {
584     Mat A = snes->jacobian, B = snes->jacobian_pre;
585     PetscCall(MatCreateVecs(A ? A : B, NULL,&snes->vec_func));
586   }
587 
588   if (version == 1) {
589     PetscCall(MatCreateSNESMF(snes,&J));
590     PetscCall(MatMFFDSetOptionsPrefix(J,((PetscObject)snes)->prefix));
591     PetscCall(MatSetFromOptions(J));
592     /* TODO: the version 2 code should be merged into the MatCreateSNESMF() and MatCreateMFFD() infrastructure and then removed */
593   } else if (version == 2) {
594     PetscCheck(snes->vec_func,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"SNESSetFunction() must be called first");
595 #if !defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_REAL_SINGLE) && !defined(PETSC_USE_REAL___FLOAT128) && !defined(PETSC_USE_REAL___FP16)
596     PetscCall(SNESDefaultMatrixFreeCreate2(snes,snes->vec_func,&J));
597 #else
598     SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP, "matrix-free operator routines (version 2)");
599 #endif
600   } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE, "matrix-free operator routines, only version 1 and 2");
601 
602   /* attach any user provided null space that was on Amat to the newly created matrix free matrix */
603   if (snes->jacobian) {
604     PetscCall(MatGetNullSpace(snes->jacobian,&nullsp));
605     if (nullsp) {
606       PetscCall(MatSetNullSpace(J,nullsp));
607     }
608   }
609 
610   PetscCall(PetscInfo(snes,"Setting default matrix-free operator routines (version %" PetscInt_FMT ")\n", version));
611   if (hasOperator) {
612 
613     /* This version replaces the user provided Jacobian matrix with a
614        matrix-free version but still employs the user-provided preconditioner matrix. */
615     PetscCall(SNESSetJacobian(snes,J,NULL,NULL,NULL));
616   } else {
617     /* This version replaces both the user-provided Jacobian and the user-
618      provided preconditioner Jacobian with the default matrix free version. */
619     if (snes->npcside == PC_LEFT && snes->npc) {
620       if (!snes->jacobian) PetscCall(SNESSetJacobian(snes,J,NULL,NULL,NULL));
621     } else {
622       KSP       ksp;
623       PC        pc;
624       PetscBool match;
625 
626       PetscCall(SNESSetJacobian(snes,J,J,MatMFFDComputeJacobian,NULL));
627       /* Force no preconditioner */
628       PetscCall(SNESGetKSP(snes,&ksp));
629       PetscCall(KSPGetPC(ksp,&pc));
630       PetscCall(PetscObjectTypeCompare((PetscObject)pc,PCSHELL,&match));
631       if (!match) {
632         PetscCall(PetscInfo(snes,"Setting default matrix-free preconditioner routines\nThat is no preconditioner is being used\n"));
633         PetscCall(PCSetType(pc,PCNONE));
634       }
635     }
636   }
637   PetscCall(MatDestroy(&J));
638   PetscFunctionReturn(0);
639 }
640 
641 static PetscErrorCode DMRestrictHook_SNESVecSol(DM dmfine,Mat Restrict,Vec Rscale,Mat Inject,DM dmcoarse,void *ctx)
642 {
643   SNES           snes = (SNES)ctx;
644   Vec            Xfine,Xfine_named = NULL,Xcoarse;
645 
646   PetscFunctionBegin;
647   if (PetscLogPrintInfo) {
648     PetscInt finelevel,coarselevel,fineclevel,coarseclevel;
649     PetscCall(DMGetRefineLevel(dmfine,&finelevel));
650     PetscCall(DMGetCoarsenLevel(dmfine,&fineclevel));
651     PetscCall(DMGetRefineLevel(dmcoarse,&coarselevel));
652     PetscCall(DMGetCoarsenLevel(dmcoarse,&coarseclevel));
653     PetscCall(PetscInfo(dmfine,"Restricting SNES solution vector from level %" PetscInt_FMT "-%" PetscInt_FMT " to level %" PetscInt_FMT "-%" PetscInt_FMT "\n",finelevel,fineclevel,coarselevel,coarseclevel));
654   }
655   if (dmfine == snes->dm) Xfine = snes->vec_sol;
656   else {
657     PetscCall(DMGetNamedGlobalVector(dmfine,"SNESVecSol",&Xfine_named));
658     Xfine = Xfine_named;
659   }
660   PetscCall(DMGetNamedGlobalVector(dmcoarse,"SNESVecSol",&Xcoarse));
661   if (Inject) {
662     PetscCall(MatRestrict(Inject,Xfine,Xcoarse));
663   } else {
664     PetscCall(MatRestrict(Restrict,Xfine,Xcoarse));
665     PetscCall(VecPointwiseMult(Xcoarse,Xcoarse,Rscale));
666   }
667   PetscCall(DMRestoreNamedGlobalVector(dmcoarse,"SNESVecSol",&Xcoarse));
668   if (Xfine_named) PetscCall(DMRestoreNamedGlobalVector(dmfine,"SNESVecSol",&Xfine_named));
669   PetscFunctionReturn(0);
670 }
671 
672 static PetscErrorCode DMCoarsenHook_SNESVecSol(DM dm,DM dmc,void *ctx)
673 {
674   PetscFunctionBegin;
675   PetscCall(DMCoarsenHookAdd(dmc,DMCoarsenHook_SNESVecSol,DMRestrictHook_SNESVecSol,ctx));
676   PetscFunctionReturn(0);
677 }
678 
679 /* This may be called to rediscretize the operator on levels of linear multigrid. The DM shuffle is so the user can
680  * safely call SNESGetDM() in their residual evaluation routine. */
681 static PetscErrorCode KSPComputeOperators_SNES(KSP ksp,Mat A,Mat B,void *ctx)
682 {
683   SNES           snes = (SNES)ctx;
684   Vec            X,Xnamed = NULL;
685   DM             dmsave;
686   void           *ctxsave;
687   PetscErrorCode (*jac)(SNES,Vec,Mat,Mat,void*) = NULL;
688 
689   PetscFunctionBegin;
690   dmsave = snes->dm;
691   PetscCall(KSPGetDM(ksp,&snes->dm));
692   if (dmsave == snes->dm) X = snes->vec_sol; /* We are on the finest level */
693   else {                                     /* We are on a coarser level, this vec was initialized using a DM restrict hook */
694     PetscCall(DMGetNamedGlobalVector(snes->dm,"SNESVecSol",&Xnamed));
695     X    = Xnamed;
696     PetscCall(SNESGetJacobian(snes,NULL,NULL,&jac,&ctxsave));
697     /* If the DM's don't match up, the MatFDColoring context needed for the jacobian won't match up either -- fixit. */
698     if (jac == SNESComputeJacobianDefaultColor) {
699       PetscCall(SNESSetJacobian(snes,NULL,NULL,SNESComputeJacobianDefaultColor,NULL));
700     }
701   }
702   /* Make sure KSP DM has the Jacobian computation routine */
703   {
704     DMSNES sdm;
705 
706     PetscCall(DMGetDMSNES(snes->dm, &sdm));
707     if (!sdm->ops->computejacobian) {
708       PetscCall(DMCopyDMSNES(dmsave, snes->dm));
709     }
710   }
711   /* Compute the operators */
712   PetscCall(SNESComputeJacobian(snes,X,A,B));
713   /* Put the previous context back */
714   if (snes->dm != dmsave && jac == SNESComputeJacobianDefaultColor) {
715     PetscCall(SNESSetJacobian(snes,NULL,NULL,jac,ctxsave));
716   }
717 
718   if (Xnamed) PetscCall(DMRestoreNamedGlobalVector(snes->dm,"SNESVecSol",&Xnamed));
719   snes->dm = dmsave;
720   PetscFunctionReturn(0);
721 }
722 
723 /*@
724    SNESSetUpMatrices - ensures that matrices are available for SNES, to be called by SNESSetUp_XXX()
725 
726    Collective
727 
728    Input Parameter:
729 .  snes - snes to configure
730 
731    Level: developer
732 
733 .seealso: `SNESSetUp()`
734 @*/
735 PetscErrorCode SNESSetUpMatrices(SNES snes)
736 {
737   DM             dm;
738   DMSNES         sdm;
739 
740   PetscFunctionBegin;
741   PetscCall(SNESGetDM(snes,&dm));
742   PetscCall(DMGetDMSNES(dm,&sdm));
743   if (!snes->jacobian && snes->mf) {
744     Mat  J;
745     void *functx;
746     PetscCall(MatCreateSNESMF(snes,&J));
747     PetscCall(MatMFFDSetOptionsPrefix(J,((PetscObject)snes)->prefix));
748     PetscCall(MatSetFromOptions(J));
749     PetscCall(SNESGetFunction(snes,NULL,NULL,&functx));
750     PetscCall(SNESSetJacobian(snes,J,J,NULL,NULL));
751     PetscCall(MatDestroy(&J));
752   } else if (snes->mf_operator && !snes->jacobian_pre && !snes->jacobian) {
753     Mat J,B;
754     PetscCall(MatCreateSNESMF(snes,&J));
755     PetscCall(MatMFFDSetOptionsPrefix(J,((PetscObject)snes)->prefix));
756     PetscCall(MatSetFromOptions(J));
757     PetscCall(DMCreateMatrix(snes->dm,&B));
758     /* sdm->computejacobian was already set to reach here */
759     PetscCall(SNESSetJacobian(snes,J,B,NULL,NULL));
760     PetscCall(MatDestroy(&J));
761     PetscCall(MatDestroy(&B));
762   } else if (!snes->jacobian_pre) {
763     PetscDS   prob;
764     Mat       J, B;
765     PetscBool hasPrec   = PETSC_FALSE;
766 
767     J    = snes->jacobian;
768     PetscCall(DMGetDS(dm, &prob));
769     if (prob) PetscCall(PetscDSHasJacobianPreconditioner(prob, &hasPrec));
770     if (J)            PetscCall(PetscObjectReference((PetscObject) J));
771     else if (hasPrec) PetscCall(DMCreateMatrix(snes->dm, &J));
772     PetscCall(DMCreateMatrix(snes->dm, &B));
773     PetscCall(SNESSetJacobian(snes, J ? J : B, B, NULL, NULL));
774     PetscCall(MatDestroy(&J));
775     PetscCall(MatDestroy(&B));
776   }
777   {
778     KSP ksp;
779     PetscCall(SNESGetKSP(snes,&ksp));
780     PetscCall(KSPSetComputeOperators(ksp,KSPComputeOperators_SNES,snes));
781     PetscCall(DMCoarsenHookAdd(snes->dm,DMCoarsenHook_SNESVecSol,DMRestrictHook_SNESVecSol,snes));
782   }
783   PetscFunctionReturn(0);
784 }
785 
786 static PetscErrorCode SNESMonitorPauseFinal_Internal(SNES snes)
787 {
788   PetscInt       i;
789 
790   PetscFunctionBegin;
791   if (!snes->pauseFinal) PetscFunctionReturn(0);
792   for (i = 0; i < snes->numbermonitors; ++i) {
793     PetscViewerAndFormat *vf = (PetscViewerAndFormat *) snes->monitorcontext[i];
794     PetscDraw             draw;
795     PetscReal             lpause;
796 
797     if (!vf) continue;
798     if (vf->lg) {
799       if (!PetscCheckPointer(vf->lg, PETSC_OBJECT)) continue;
800       if (((PetscObject) vf->lg)->classid != PETSC_DRAWLG_CLASSID) continue;
801       PetscCall(PetscDrawLGGetDraw(vf->lg, &draw));
802       PetscCall(PetscDrawGetPause(draw, &lpause));
803       PetscCall(PetscDrawSetPause(draw, -1.0));
804       PetscCall(PetscDrawPause(draw));
805       PetscCall(PetscDrawSetPause(draw, lpause));
806     } else {
807       PetscBool isdraw;
808 
809       if (!PetscCheckPointer(vf->viewer, PETSC_OBJECT)) continue;
810       if (((PetscObject) vf->viewer)->classid != PETSC_VIEWER_CLASSID) continue;
811       PetscCall(PetscObjectTypeCompare((PetscObject) vf->viewer, PETSCVIEWERDRAW, &isdraw));
812       if (!isdraw) continue;
813       PetscCall(PetscViewerDrawGetDraw(vf->viewer, 0, &draw));
814       PetscCall(PetscDrawGetPause(draw, &lpause));
815       PetscCall(PetscDrawSetPause(draw, -1.0));
816       PetscCall(PetscDrawPause(draw));
817       PetscCall(PetscDrawSetPause(draw, lpause));
818     }
819   }
820   PetscFunctionReturn(0);
821 }
822 
823 /*@C
824    SNESMonitorSetFromOptions - Sets a monitor function and viewer appropriate for the type indicated by the user
825 
826    Collective on SNES
827 
828    Input Parameters:
829 +  snes - SNES object you wish to monitor
830 .  name - the monitor type one is seeking
831 .  help - message indicating what monitoring is done
832 .  manual - manual page for the monitor
833 .  monitor - the monitor function
834 -  monitorsetup - a function that is called once ONLY if the user selected this monitor that may set additional features of the SNES or PetscViewer objects
835 
836    Level: developer
837 
838 .seealso: `PetscOptionsGetViewer()`, `PetscOptionsGetReal()`, `PetscOptionsHasName()`, `PetscOptionsGetString()`,
839           `PetscOptionsGetIntArray()`, `PetscOptionsGetRealArray()`, `PetscOptionsBool()`
840           `PetscOptionsInt()`, `PetscOptionsString()`, `PetscOptionsReal()`, `PetscOptionsBool()`,
841           `PetscOptionsName()`, `PetscOptionsBegin()`, `PetscOptionsEnd()`, `PetscOptionsHeadBegin()`,
842           `PetscOptionsStringArray(),PetscOptionsRealArray()`, `PetscOptionsScalar()`,
843           `PetscOptionsBoolGroupBegin()`, `PetscOptionsBoolGroup()`, `PetscOptionsBoolGroupEnd()`,
844           `PetscOptionsFList()`, `PetscOptionsEList()`
845 @*/
846 PetscErrorCode  SNESMonitorSetFromOptions(SNES snes,const char name[],const char help[], const char manual[],PetscErrorCode (*monitor)(SNES,PetscInt,PetscReal,PetscViewerAndFormat*),PetscErrorCode (*monitorsetup)(SNES,PetscViewerAndFormat*))
847 {
848   PetscViewer       viewer;
849   PetscViewerFormat format;
850   PetscBool         flg;
851 
852   PetscFunctionBegin;
853   PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject) snes)->options,((PetscObject)snes)->prefix,name,&viewer,&format,&flg));
854   if (flg) {
855     PetscViewerAndFormat *vf;
856     PetscCall(PetscViewerAndFormatCreate(viewer,format,&vf));
857     PetscCall(PetscObjectDereference((PetscObject)viewer));
858     if (monitorsetup) {
859       PetscCall((*monitorsetup)(snes,vf));
860     }
861     PetscCall(SNESMonitorSet(snes,(PetscErrorCode (*)(SNES,PetscInt,PetscReal,void*))monitor,vf,(PetscErrorCode (*)(void**))PetscViewerAndFormatDestroy));
862   }
863   PetscFunctionReturn(0);
864 }
865 
866 /*@
867    SNESSetFromOptions - Sets various SNES and KSP parameters from user options.
868 
869    Collective on SNES
870 
871    Input Parameter:
872 .  snes - the SNES context
873 
874    Options Database Keys:
875 +  -snes_type <type> - newtonls, newtontr, ngmres, ncg, nrichardson, qn, vi, fas, SNESType for complete list
876 .  -snes_stol - convergence tolerance in terms of the norm
877                 of the change in the solution between steps
878 .  -snes_atol <abstol> - absolute tolerance of residual norm
879 .  -snes_rtol <rtol> - relative decrease in tolerance norm from initial
880 .  -snes_divergence_tolerance <divtol> - if the residual goes above divtol*rnorm0, exit with divergence
881 .  -snes_force_iteration <force> - force SNESSolve() to take at least one iteration
882 .  -snes_max_it <max_it> - maximum number of iterations
883 .  -snes_max_funcs <max_funcs> - maximum number of function evaluations
884 .  -snes_max_fail <max_fail> - maximum number of line search failures allowed before stopping, default is none
885 .  -snes_max_linear_solve_fail - number of linear solver failures before SNESSolve() stops
886 .  -snes_lag_preconditioner <lag> - how often preconditioner is rebuilt (use -1 to never rebuild)
887 .  -snes_lag_preconditioner_persists <true,false> - retains the -snes_lag_preconditioner information across multiple SNESSolve()
888 .  -snes_lag_jacobian <lag> - how often Jacobian is rebuilt (use -1 to never rebuild)
889 .  -snes_lag_jacobian_persists <true,false> - retains the -snes_lag_jacobian information across multiple SNESSolve()
890 .  -snes_trtol <trtol> - trust region tolerance
891 .  -snes_convergence_test - <default,skip,correct_pressure> convergence test in nonlinear solver.
892                                default SNESConvergedDefault(). skip SNESConvergedSkip() means continue iterating until max_it or some other criterion is reached, saving expense
893                                of convergence test. correct_pressure SNESConvergedCorrectPressure() has special handling of a pressure null space.
894 .  -snes_monitor [ascii][:filename][:viewer format] - prints residual norm at each iteration. if no filename given prints to stdout
895 .  -snes_monitor_solution [ascii binary draw][:filename][:viewer format] - plots solution at each iteration
896 .  -snes_monitor_residual [ascii binary draw][:filename][:viewer format] - plots residual (not its norm) at each iteration
897 .  -snes_monitor_solution_update [ascii binary draw][:filename][:viewer format] - plots update to solution at each iteration
898 .  -snes_monitor_lg_residualnorm - plots residual norm at each iteration
899 .  -snes_monitor_lg_range - plots residual norm at each iteration
900 .  -snes_monitor_pause_final - Pauses all monitor drawing after the solver ends
901 .  -snes_fd - use finite differences to compute Jacobian; very slow, only for testing
902 .  -snes_fd_color - use finite differences with coloring to compute Jacobian
903 .  -snes_mf_ksp_monitor - if using matrix-free multiply then print h at each KSP iteration
904 .  -snes_converged_reason - print the reason for convergence/divergence after each solve
905 .  -npc_snes_type <type> - the SNES type to use as a nonlinear preconditioner
906 .   -snes_test_jacobian <optional threshold> - compare the user provided Jacobian with one computed via finite differences to check for errors.  If a threshold is given, display only those entries whose difference is greater than the threshold.
907 -   -snes_test_jacobian_view - display the user provided Jacobian, the finite difference Jacobian and the difference between them to help users detect the location of errors in the user provided Jacobian.
908 
909     Options Database for Eisenstat-Walker method:
910 +  -snes_ksp_ew - use Eisenstat-Walker method for determining linear system convergence
911 .  -snes_ksp_ew_version ver - version of  Eisenstat-Walker method
912 .  -snes_ksp_ew_rtol0 <rtol0> - Sets rtol0
913 .  -snes_ksp_ew_rtolmax <rtolmax> - Sets rtolmax
914 .  -snes_ksp_ew_gamma <gamma> - Sets gamma
915 .  -snes_ksp_ew_alpha <alpha> - Sets alpha
916 .  -snes_ksp_ew_alpha2 <alpha2> - Sets alpha2
917 -  -snes_ksp_ew_threshold <threshold> - Sets threshold
918 
919    Notes:
920    To see all options, run your program with the -help option or consult the users manual
921 
922    Notes:
923       SNES supports three approaches for computing (approximate) Jacobians: user provided via SNESSetJacobian(), matrix free, and computing explicitly with
924       finite differences and coloring using MatFDColoring. It is also possible to use automatic differentiation and the MatFDColoring object.
925 
926    Level: beginner
927 
928 .seealso: `SNESSetOptionsPrefix()`, `SNESResetFromOptions()`, `SNES`, `SNESCreate()`
929 @*/
930 PetscErrorCode  SNESSetFromOptions(SNES snes)
931 {
932   PetscBool      flg,pcset,persist,set;
933   PetscInt       i,indx,lag,grids;
934   const char     *deft        = SNESNEWTONLS;
935   const char     *convtests[] = {"default","skip","correct_pressure"};
936   SNESKSPEW      *kctx        = NULL;
937   char           type[256], monfilename[PETSC_MAX_PATH_LEN];
938   PCSide         pcside;
939   const char     *optionsprefix;
940 
941   PetscFunctionBegin;
942   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
943   PetscCall(SNESRegisterAll());
944   PetscObjectOptionsBegin((PetscObject)snes);
945   if (((PetscObject)snes)->type_name) deft = ((PetscObject)snes)->type_name;
946   PetscCall(PetscOptionsFList("-snes_type","Nonlinear solver method","SNESSetType",SNESList,deft,type,256,&flg));
947   if (flg) {
948     PetscCall(SNESSetType(snes,type));
949   } else if (!((PetscObject)snes)->type_name) {
950     PetscCall(SNESSetType(snes,deft));
951   }
952   PetscCall(PetscOptionsReal("-snes_stol","Stop if step length less than","SNESSetTolerances",snes->stol,&snes->stol,NULL));
953   PetscCall(PetscOptionsReal("-snes_atol","Stop if function norm less than","SNESSetTolerances",snes->abstol,&snes->abstol,NULL));
954 
955   PetscCall(PetscOptionsReal("-snes_rtol","Stop if decrease in function norm less than","SNESSetTolerances",snes->rtol,&snes->rtol,NULL));
956   PetscCall(PetscOptionsReal("-snes_divergence_tolerance","Stop if residual norm increases by this factor","SNESSetDivergenceTolerance",snes->divtol,&snes->divtol,NULL));
957   PetscCall(PetscOptionsInt("-snes_max_it","Maximum iterations","SNESSetTolerances",snes->max_its,&snes->max_its,NULL));
958   PetscCall(PetscOptionsInt("-snes_max_funcs","Maximum function evaluations","SNESSetTolerances",snes->max_funcs,&snes->max_funcs,NULL));
959   PetscCall(PetscOptionsInt("-snes_max_fail","Maximum nonlinear step failures","SNESSetMaxNonlinearStepFailures",snes->maxFailures,&snes->maxFailures,NULL));
960   PetscCall(PetscOptionsInt("-snes_max_linear_solve_fail","Maximum failures in linear solves allowed","SNESSetMaxLinearSolveFailures",snes->maxLinearSolveFailures,&snes->maxLinearSolveFailures,NULL));
961   PetscCall(PetscOptionsBool("-snes_error_if_not_converged","Generate error if solver does not converge","SNESSetErrorIfNotConverged",snes->errorifnotconverged,&snes->errorifnotconverged,NULL));
962   PetscCall(PetscOptionsBool("-snes_force_iteration","Force SNESSolve() to take at least one iteration","SNESSetForceIteration",snes->forceiteration,&snes->forceiteration,NULL));
963   PetscCall(PetscOptionsBool("-snes_check_jacobian_domain_error","Check Jacobian domain error after Jacobian evaluation","SNESCheckJacobianDomainError",snes->checkjacdomainerror,&snes->checkjacdomainerror,NULL));
964 
965   PetscCall(PetscOptionsInt("-snes_lag_preconditioner","How often to rebuild preconditioner","SNESSetLagPreconditioner",snes->lagpreconditioner,&lag,&flg));
966   if (flg) {
967     PetscCheck(lag != -1,PetscObjectComm((PetscObject)snes),PETSC_ERR_USER,"Cannot set the lag to -1 from the command line since the preconditioner must be built as least once, perhaps you mean -2");
968     PetscCall(SNESSetLagPreconditioner(snes,lag));
969   }
970   PetscCall(PetscOptionsBool("-snes_lag_preconditioner_persists","Preconditioner lagging through multiple SNES solves","SNESSetLagPreconditionerPersists",snes->lagjac_persist,&persist,&flg));
971   if (flg) {
972     PetscCall(SNESSetLagPreconditionerPersists(snes,persist));
973   }
974   PetscCall(PetscOptionsInt("-snes_lag_jacobian","How often to rebuild Jacobian","SNESSetLagJacobian",snes->lagjacobian,&lag,&flg));
975   if (flg) {
976     PetscCheck(lag != -1,PetscObjectComm((PetscObject)snes),PETSC_ERR_USER,"Cannot set the lag to -1 from the command line since the Jacobian must be built as least once, perhaps you mean -2");
977     PetscCall(SNESSetLagJacobian(snes,lag));
978   }
979   PetscCall(PetscOptionsBool("-snes_lag_jacobian_persists","Jacobian lagging through multiple SNES solves","SNESSetLagJacobianPersists",snes->lagjac_persist,&persist,&flg));
980   if (flg) {
981     PetscCall(SNESSetLagJacobianPersists(snes,persist));
982   }
983 
984   PetscCall(PetscOptionsInt("-snes_grid_sequence","Use grid sequencing to generate initial guess","SNESSetGridSequence",snes->gridsequence,&grids,&flg));
985   if (flg) {
986     PetscCall(SNESSetGridSequence(snes,grids));
987   }
988 
989   PetscCall(PetscOptionsEList("-snes_convergence_test","Convergence test","SNESSetConvergenceTest",convtests,sizeof(convtests)/sizeof(char*),"default",&indx,&flg));
990   if (flg) {
991     switch (indx) {
992     case 0: PetscCall(SNESSetConvergenceTest(snes,SNESConvergedDefault,NULL,NULL)); break;
993     case 1: PetscCall(SNESSetConvergenceTest(snes,SNESConvergedSkip,NULL,NULL)); break;
994     case 2: PetscCall(SNESSetConvergenceTest(snes,SNESConvergedCorrectPressure,NULL,NULL)); break;
995     }
996   }
997 
998   PetscCall(PetscOptionsEList("-snes_norm_schedule","SNES Norm schedule","SNESSetNormSchedule",SNESNormSchedules,5,"function",&indx,&flg));
999   if (flg) PetscCall(SNESSetNormSchedule(snes,(SNESNormSchedule)indx));
1000 
1001   PetscCall(PetscOptionsEList("-snes_function_type","SNES Norm schedule","SNESSetFunctionType",SNESFunctionTypes,2,"unpreconditioned",&indx,&flg));
1002   if (flg) PetscCall(SNESSetFunctionType(snes,(SNESFunctionType)indx));
1003 
1004   kctx = (SNESKSPEW*)snes->kspconvctx;
1005 
1006   PetscCall(PetscOptionsBool("-snes_ksp_ew","Use Eisentat-Walker linear system convergence test","SNESKSPSetUseEW",snes->ksp_ewconv,&snes->ksp_ewconv,NULL));
1007 
1008   PetscCall(PetscOptionsInt("-snes_ksp_ew_version","Version 1, 2 or 3","SNESKSPSetParametersEW",kctx->version,&kctx->version,NULL));
1009   PetscCall(PetscOptionsReal("-snes_ksp_ew_rtol0","0 <= rtol0 < 1","SNESKSPSetParametersEW",kctx->rtol_0,&kctx->rtol_0,NULL));
1010   PetscCall(PetscOptionsReal("-snes_ksp_ew_rtolmax","0 <= rtolmax < 1","SNESKSPSetParametersEW",kctx->rtol_max,&kctx->rtol_max,NULL));
1011   PetscCall(PetscOptionsReal("-snes_ksp_ew_gamma","0 <= gamma <= 1","SNESKSPSetParametersEW",kctx->gamma,&kctx->gamma,NULL));
1012   PetscCall(PetscOptionsReal("-snes_ksp_ew_alpha","1 < alpha <= 2","SNESKSPSetParametersEW",kctx->alpha,&kctx->alpha,NULL));
1013   PetscCall(PetscOptionsReal("-snes_ksp_ew_alpha2","alpha2","SNESKSPSetParametersEW",kctx->alpha2,&kctx->alpha2,NULL));
1014   PetscCall(PetscOptionsReal("-snes_ksp_ew_threshold","0 < threshold < 1","SNESKSPSetParametersEW",kctx->threshold,&kctx->threshold,NULL));
1015 
1016   flg  = PETSC_FALSE;
1017   PetscCall(PetscOptionsBool("-snes_monitor_cancel","Remove all monitors","SNESMonitorCancel",flg,&flg,&set));
1018   if (set && flg) PetscCall(SNESMonitorCancel(snes));
1019 
1020   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor","Monitor norm of function","SNESMonitorDefault",SNESMonitorDefault,SNESMonitorDefaultSetUp));
1021   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_short","Monitor norm of function with fewer digits","SNESMonitorDefaultShort",SNESMonitorDefaultShort,NULL));
1022   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_range","Monitor range of elements of function","SNESMonitorRange",SNESMonitorRange,NULL));
1023 
1024   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_ratio","Monitor ratios of the norm of function for consecutive steps","SNESMonitorRatio",SNESMonitorRatio,SNESMonitorRatioSetUp));
1025   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_field","Monitor norm of function (split into fields)","SNESMonitorDefaultField",SNESMonitorDefaultField,NULL));
1026   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_solution","View solution at each iteration","SNESMonitorSolution",SNESMonitorSolution,NULL));
1027   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_solution_update","View correction at each iteration","SNESMonitorSolutionUpdate",SNESMonitorSolutionUpdate,NULL));
1028   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_residual","View residual at each iteration","SNESMonitorResidual",SNESMonitorResidual,NULL));
1029   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_jacupdate_spectrum","Print the change in the spectrum of the Jacobian","SNESMonitorJacUpdateSpectrum",SNESMonitorJacUpdateSpectrum,NULL));
1030   PetscCall(SNESMonitorSetFromOptions(snes,"-snes_monitor_fields","Monitor norm of function per field","SNESMonitorSet",SNESMonitorFields,NULL));
1031   PetscCall(PetscOptionsBool("-snes_monitor_pause_final", "Pauses all draw monitors at the final iterate", "SNESMonitorPauseFinal_Internal", PETSC_FALSE, &snes->pauseFinal, NULL));
1032 
1033   PetscCall(PetscOptionsString("-snes_monitor_python","Use Python function","SNESMonitorSet",NULL,monfilename,sizeof(monfilename),&flg));
1034   if (flg) PetscCall(PetscPythonMonitorSet((PetscObject)snes,monfilename));
1035 
1036   flg  = PETSC_FALSE;
1037   PetscCall(PetscOptionsBool("-snes_monitor_lg_range","Plot function range at each iteration","SNESMonitorLGRange",flg,&flg,NULL));
1038   if (flg) {
1039     PetscViewer ctx;
1040 
1041     PetscCall(PetscViewerDrawOpen(PetscObjectComm((PetscObject)snes),NULL,NULL,PETSC_DECIDE,PETSC_DECIDE,400,300,&ctx));
1042     PetscCall(SNESMonitorSet(snes,SNESMonitorLGRange,ctx,(PetscErrorCode (*)(void**))PetscViewerDestroy));
1043   }
1044 
1045   flg  = PETSC_FALSE;
1046   PetscCall(PetscOptionsBool("-snes_converged_reason_view_cancel","Remove all converged reason viewers","SNESConvergedReasonViewCancel",flg,&flg,&set));
1047   if (set && flg) PetscCall(SNESConvergedReasonViewCancel(snes));
1048 
1049   flg  = PETSC_FALSE;
1050   PetscCall(PetscOptionsBool("-snes_fd","Use finite differences (slow) to compute Jacobian","SNESComputeJacobianDefault",flg,&flg,NULL));
1051   if (flg) {
1052     void    *functx;
1053     DM      dm;
1054     DMSNES  sdm;
1055     PetscCall(SNESGetDM(snes,&dm));
1056     PetscCall(DMGetDMSNES(dm,&sdm));
1057     sdm->jacobianctx = NULL;
1058     PetscCall(SNESGetFunction(snes,NULL,NULL,&functx));
1059     PetscCall(SNESSetJacobian(snes,snes->jacobian,snes->jacobian_pre,SNESComputeJacobianDefault,functx));
1060     PetscCall(PetscInfo(snes,"Setting default finite difference Jacobian matrix\n"));
1061   }
1062 
1063   flg  = PETSC_FALSE;
1064   PetscCall(PetscOptionsBool("-snes_fd_function","Use finite differences (slow) to compute function from user objective","SNESObjectiveComputeFunctionDefaultFD",flg,&flg,NULL));
1065   if (flg) {
1066     PetscCall(SNESSetFunction(snes,NULL,SNESObjectiveComputeFunctionDefaultFD,NULL));
1067   }
1068 
1069   flg  = PETSC_FALSE;
1070   PetscCall(PetscOptionsBool("-snes_fd_color","Use finite differences with coloring to compute Jacobian","SNESComputeJacobianDefaultColor",flg,&flg,NULL));
1071   if (flg) {
1072     DM             dm;
1073     DMSNES         sdm;
1074     PetscCall(SNESGetDM(snes,&dm));
1075     PetscCall(DMGetDMSNES(dm,&sdm));
1076     sdm->jacobianctx = NULL;
1077     PetscCall(SNESSetJacobian(snes,snes->jacobian,snes->jacobian_pre,SNESComputeJacobianDefaultColor,NULL));
1078     PetscCall(PetscInfo(snes,"Setting default finite difference coloring Jacobian matrix\n"));
1079   }
1080 
1081   flg  = PETSC_FALSE;
1082   PetscCall(PetscOptionsBool("-snes_mf_operator","Use a Matrix-Free Jacobian with user-provided preconditioner matrix","SNESSetUseMatrixFree",PETSC_FALSE,&snes->mf_operator,&flg));
1083   if (flg && snes->mf_operator) {
1084     snes->mf_operator = PETSC_TRUE;
1085     snes->mf          = PETSC_TRUE;
1086   }
1087   flg  = PETSC_FALSE;
1088   PetscCall(PetscOptionsBool("-snes_mf","Use a Matrix-Free Jacobian with no preconditioner matrix","SNESSetUseMatrixFree",PETSC_FALSE,&snes->mf,&flg));
1089   if (!flg && snes->mf_operator) snes->mf = PETSC_TRUE;
1090   PetscCall(PetscOptionsInt("-snes_mf_version","Matrix-Free routines version 1 or 2","None",snes->mf_version,&snes->mf_version,NULL));
1091 
1092   flg  = PETSC_FALSE;
1093   PetscCall(SNESGetNPCSide(snes,&pcside));
1094   PetscCall(PetscOptionsEnum("-snes_npc_side","SNES nonlinear preconditioner side","SNESSetNPCSide",PCSides,(PetscEnum)pcside,(PetscEnum*)&pcside,&flg));
1095   if (flg) PetscCall(SNESSetNPCSide(snes,pcside));
1096 
1097 #if defined(PETSC_HAVE_SAWS)
1098   /*
1099     Publish convergence information using SAWs
1100   */
1101   flg  = PETSC_FALSE;
1102   PetscCall(PetscOptionsBool("-snes_monitor_saws","Publish SNES progress using SAWs","SNESMonitorSet",flg,&flg,NULL));
1103   if (flg) {
1104     void *ctx;
1105     PetscCall(SNESMonitorSAWsCreate(snes,&ctx));
1106     PetscCall(SNESMonitorSet(snes,SNESMonitorSAWs,ctx,SNESMonitorSAWsDestroy));
1107   }
1108 #endif
1109 #if defined(PETSC_HAVE_SAWS)
1110   {
1111   PetscBool set;
1112   flg  = PETSC_FALSE;
1113   PetscCall(PetscOptionsBool("-snes_saws_block","Block for SAWs at end of SNESSolve","PetscObjectSAWsBlock",((PetscObject)snes)->amspublishblock,&flg,&set));
1114   if (set) {
1115     PetscCall(PetscObjectSAWsSetBlock((PetscObject)snes,flg));
1116   }
1117   }
1118 #endif
1119 
1120   for (i = 0; i < numberofsetfromoptions; i++) {
1121     PetscCall((*othersetfromoptions[i])(snes));
1122   }
1123 
1124   if (snes->ops->setfromoptions) {
1125     PetscCall((*snes->ops->setfromoptions)(PetscOptionsObject,snes));
1126   }
1127 
1128   /* process any options handlers added with PetscObjectAddOptionsHandler() */
1129   PetscCall(PetscObjectProcessOptionsHandlers(PetscOptionsObject,(PetscObject)snes));
1130   PetscOptionsEnd();
1131 
1132   if (snes->linesearch) {
1133     PetscCall(SNESGetLineSearch(snes, &snes->linesearch));
1134     PetscCall(SNESLineSearchSetFromOptions(snes->linesearch));
1135   }
1136 
1137   if (snes->usesksp) {
1138     if (!snes->ksp) PetscCall(SNESGetKSP(snes,&snes->ksp));
1139     PetscCall(KSPSetOperators(snes->ksp,snes->jacobian,snes->jacobian_pre));
1140     PetscCall(KSPSetFromOptions(snes->ksp));
1141   }
1142 
1143   /* if user has set the SNES NPC type via options database, create it. */
1144   PetscCall(SNESGetOptionsPrefix(snes, &optionsprefix));
1145   PetscCall(PetscOptionsHasName(((PetscObject)snes)->options,optionsprefix, "-npc_snes_type", &pcset));
1146   if (pcset && (!snes->npc)) {
1147     PetscCall(SNESGetNPC(snes, &snes->npc));
1148   }
1149   if (snes->npc) {
1150     PetscCall(SNESSetFromOptions(snes->npc));
1151   }
1152   snes->setfromoptionscalled++;
1153   PetscFunctionReturn(0);
1154 }
1155 
1156 /*@
1157    SNESResetFromOptions - Sets various SNES and KSP parameters from user options ONLY if the SNES was previously set from options
1158 
1159    Collective on SNES
1160 
1161    Input Parameter:
1162 .  snes - the SNES context
1163 
1164    Level: beginner
1165 
1166 .seealso: `SNESSetFromOptions()`, `SNESSetOptionsPrefix()`
1167 @*/
1168 PetscErrorCode SNESResetFromOptions(SNES snes)
1169 {
1170   PetscFunctionBegin;
1171   if (snes->setfromoptionscalled) PetscCall(SNESSetFromOptions(snes));
1172   PetscFunctionReturn(0);
1173 }
1174 
1175 /*@C
1176    SNESSetComputeApplicationContext - Sets an optional function to compute a user-defined context for
1177    the nonlinear solvers.
1178 
1179    Logically Collective on SNES
1180 
1181    Input Parameters:
1182 +  snes - the SNES context
1183 .  compute - function to compute the context
1184 -  destroy - function to destroy the context
1185 
1186    Level: intermediate
1187 
1188    Notes:
1189    This function is currently not available from Fortran.
1190 
1191 .seealso: `SNESGetApplicationContext()`, `SNESSetComputeApplicationContext()`, `SNESGetApplicationContext()`
1192 @*/
1193 PetscErrorCode  SNESSetComputeApplicationContext(SNES snes,PetscErrorCode (*compute)(SNES,void**),PetscErrorCode (*destroy)(void**))
1194 {
1195   PetscFunctionBegin;
1196   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1197   snes->ops->usercompute = compute;
1198   snes->ops->userdestroy = destroy;
1199   PetscFunctionReturn(0);
1200 }
1201 
1202 /*@
1203    SNESSetApplicationContext - Sets the optional user-defined context for
1204    the nonlinear solvers.
1205 
1206    Logically Collective on SNES
1207 
1208    Input Parameters:
1209 +  snes - the SNES context
1210 -  usrP - optional user context
1211 
1212    Level: intermediate
1213 
1214    Fortran Notes:
1215     To use this from Fortran you must write a Fortran interface definition for this
1216     function that tells Fortran the Fortran derived data type that you are passing in as the ctx argument.
1217 
1218 .seealso: `SNESGetApplicationContext()`
1219 @*/
1220 PetscErrorCode  SNESSetApplicationContext(SNES snes,void *usrP)
1221 {
1222   KSP            ksp;
1223 
1224   PetscFunctionBegin;
1225   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1226   PetscCall(SNESGetKSP(snes,&ksp));
1227   PetscCall(KSPSetApplicationContext(ksp,usrP));
1228   snes->user = usrP;
1229   PetscFunctionReturn(0);
1230 }
1231 
1232 /*@
1233    SNESGetApplicationContext - Gets the user-defined context for the
1234    nonlinear solvers.
1235 
1236    Not Collective
1237 
1238    Input Parameter:
1239 .  snes - SNES context
1240 
1241    Output Parameter:
1242 .  usrP - user context
1243 
1244    Fortran Notes:
1245     To use this from Fortran you must write a Fortran interface definition for this
1246     function that tells Fortran the Fortran derived data type that you are passing in as the ctx argument.
1247 
1248    Level: intermediate
1249 
1250 .seealso: `SNESSetApplicationContext()`
1251 @*/
1252 PetscErrorCode  SNESGetApplicationContext(SNES snes,void *usrP)
1253 {
1254   PetscFunctionBegin;
1255   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1256   *(void**)usrP = snes->user;
1257   PetscFunctionReturn(0);
1258 }
1259 
1260 /*@
1261    SNESSetUseMatrixFree - indicates that SNES should use matrix free finite difference matrix vector products internally to apply the Jacobian.
1262 
1263    Collective on SNES
1264 
1265    Input Parameters:
1266 +  snes - SNES context
1267 .  mf_operator - use matrix-free only for the Amat used by SNESSetJacobian(), this means the user provided Pmat will continue to be used
1268 -  mf - use matrix-free for both the Amat and Pmat used by SNESSetJacobian(), both the Amat and Pmat set in SNESSetJacobian() will be ignored
1269 
1270    Options Database:
1271 + -snes_mf - use matrix free for both the mat and pmat operator
1272 . -snes_mf_operator - use matrix free only for the mat operator
1273 . -snes_fd_color - compute the Jacobian via coloring and finite differences.
1274 - -snes_fd - compute the Jacobian via finite differences (slow)
1275 
1276    Level: intermediate
1277 
1278    Notes:
1279       SNES supports three approaches for computing (approximate) Jacobians: user provided via SNESSetJacobian(), matrix free, and computing explicitly with
1280       finite differences and coloring using MatFDColoring. It is also possible to use automatic differentiation and the MatFDColoring object.
1281 
1282 .seealso: `SNESGetUseMatrixFree()`, `MatCreateSNESMF()`, `SNESComputeJacobianDefaultColor()`
1283 @*/
1284 PetscErrorCode  SNESSetUseMatrixFree(SNES snes,PetscBool mf_operator,PetscBool mf)
1285 {
1286   PetscFunctionBegin;
1287   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1288   PetscValidLogicalCollectiveBool(snes,mf_operator,2);
1289   PetscValidLogicalCollectiveBool(snes,mf,3);
1290   snes->mf          = mf_operator ? PETSC_TRUE : mf;
1291   snes->mf_operator = mf_operator;
1292   PetscFunctionReturn(0);
1293 }
1294 
1295 /*@
1296    SNESGetUseMatrixFree - indicates if the SNES uses matrix free finite difference matrix vector products to apply the Jacobian.
1297 
1298    Collective on SNES
1299 
1300    Input Parameter:
1301 .  snes - SNES context
1302 
1303    Output Parameters:
1304 +  mf_operator - use matrix-free only for the Amat used by SNESSetJacobian(), this means the user provided Pmat will continue to be used
1305 -  mf - use matrix-free for both the Amat and Pmat used by SNESSetJacobian(), both the Amat and Pmat set in SNESSetJacobian() will be ignored
1306 
1307    Options Database:
1308 + -snes_mf - use matrix free for both the mat and pmat operator
1309 - -snes_mf_operator - use matrix free only for the mat operator
1310 
1311    Level: intermediate
1312 
1313 .seealso: `SNESSetUseMatrixFree()`, `MatCreateSNESMF()`
1314 @*/
1315 PetscErrorCode  SNESGetUseMatrixFree(SNES snes,PetscBool *mf_operator,PetscBool *mf)
1316 {
1317   PetscFunctionBegin;
1318   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1319   if (mf)          *mf          = snes->mf;
1320   if (mf_operator) *mf_operator = snes->mf_operator;
1321   PetscFunctionReturn(0);
1322 }
1323 
1324 /*@
1325    SNESGetIterationNumber - Gets the number of nonlinear iterations completed
1326    at this time.
1327 
1328    Not Collective
1329 
1330    Input Parameter:
1331 .  snes - SNES context
1332 
1333    Output Parameter:
1334 .  iter - iteration number
1335 
1336    Notes:
1337    For example, during the computation of iteration 2 this would return 1.
1338 
1339    This is useful for using lagged Jacobians (where one does not recompute the
1340    Jacobian at each SNES iteration). For example, the code
1341 .vb
1342       ierr = SNESGetIterationNumber(snes,&it);
1343       if (!(it % 2)) {
1344         [compute Jacobian here]
1345       }
1346 .ve
1347    can be used in your ComputeJacobian() function to cause the Jacobian to be
1348    recomputed every second SNES iteration.
1349 
1350    After the SNES solve is complete this will return the number of nonlinear iterations used.
1351 
1352    Level: intermediate
1353 
1354 .seealso: `SNESGetLinearSolveIterations()`
1355 @*/
1356 PetscErrorCode  SNESGetIterationNumber(SNES snes,PetscInt *iter)
1357 {
1358   PetscFunctionBegin;
1359   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1360   PetscValidIntPointer(iter,2);
1361   *iter = snes->iter;
1362   PetscFunctionReturn(0);
1363 }
1364 
1365 /*@
1366    SNESSetIterationNumber - Sets the current iteration number.
1367 
1368    Not Collective
1369 
1370    Input Parameters:
1371 +  snes - SNES context
1372 -  iter - iteration number
1373 
1374    Level: developer
1375 
1376 .seealso: `SNESGetLinearSolveIterations()`
1377 @*/
1378 PetscErrorCode  SNESSetIterationNumber(SNES snes,PetscInt iter)
1379 {
1380   PetscFunctionBegin;
1381   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1382   PetscCall(PetscObjectSAWsTakeAccess((PetscObject)snes));
1383   snes->iter = iter;
1384   PetscCall(PetscObjectSAWsGrantAccess((PetscObject)snes));
1385   PetscFunctionReturn(0);
1386 }
1387 
1388 /*@
1389    SNESGetNonlinearStepFailures - Gets the number of unsuccessful steps
1390    attempted by the nonlinear solver.
1391 
1392    Not Collective
1393 
1394    Input Parameter:
1395 .  snes - SNES context
1396 
1397    Output Parameter:
1398 .  nfails - number of unsuccessful steps attempted
1399 
1400    Notes:
1401    This counter is reset to zero for each successive call to SNESSolve().
1402 
1403    Level: intermediate
1404 
1405 .seealso: `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`, `SNESGetLinearSolveFailures()`,
1406           `SNESSetMaxNonlinearStepFailures()`, `SNESGetMaxNonlinearStepFailures()`
1407 @*/
1408 PetscErrorCode  SNESGetNonlinearStepFailures(SNES snes,PetscInt *nfails)
1409 {
1410   PetscFunctionBegin;
1411   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1412   PetscValidIntPointer(nfails,2);
1413   *nfails = snes->numFailures;
1414   PetscFunctionReturn(0);
1415 }
1416 
1417 /*@
1418    SNESSetMaxNonlinearStepFailures - Sets the maximum number of unsuccessful steps
1419    attempted by the nonlinear solver before it gives up.
1420 
1421    Not Collective
1422 
1423    Input Parameters:
1424 +  snes     - SNES context
1425 -  maxFails - maximum of unsuccessful steps
1426 
1427    Level: intermediate
1428 
1429 .seealso: `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`, `SNESGetLinearSolveFailures()`,
1430           `SNESGetMaxNonlinearStepFailures()`, `SNESGetNonlinearStepFailures()`
1431 @*/
1432 PetscErrorCode  SNESSetMaxNonlinearStepFailures(SNES snes, PetscInt maxFails)
1433 {
1434   PetscFunctionBegin;
1435   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1436   snes->maxFailures = maxFails;
1437   PetscFunctionReturn(0);
1438 }
1439 
1440 /*@
1441    SNESGetMaxNonlinearStepFailures - Gets the maximum number of unsuccessful steps
1442    attempted by the nonlinear solver before it gives up.
1443 
1444    Not Collective
1445 
1446    Input Parameter:
1447 .  snes     - SNES context
1448 
1449    Output Parameter:
1450 .  maxFails - maximum of unsuccessful steps
1451 
1452    Level: intermediate
1453 
1454 .seealso: `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`, `SNESGetLinearSolveFailures()`,
1455           `SNESSetMaxNonlinearStepFailures()`, `SNESGetNonlinearStepFailures()`
1456 
1457 @*/
1458 PetscErrorCode  SNESGetMaxNonlinearStepFailures(SNES snes, PetscInt *maxFails)
1459 {
1460   PetscFunctionBegin;
1461   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1462   PetscValidIntPointer(maxFails,2);
1463   *maxFails = snes->maxFailures;
1464   PetscFunctionReturn(0);
1465 }
1466 
1467 /*@
1468    SNESGetNumberFunctionEvals - Gets the number of user provided function evaluations
1469      done by SNES.
1470 
1471    Not Collective
1472 
1473    Input Parameter:
1474 .  snes     - SNES context
1475 
1476    Output Parameter:
1477 .  nfuncs - number of evaluations
1478 
1479    Level: intermediate
1480 
1481    Notes:
1482     Reset every time SNESSolve is called unless SNESSetCountersReset() is used.
1483 
1484 .seealso: `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`, `SNESGetLinearSolveFailures()`, `SNESSetCountersReset()`
1485 @*/
1486 PetscErrorCode  SNESGetNumberFunctionEvals(SNES snes, PetscInt *nfuncs)
1487 {
1488   PetscFunctionBegin;
1489   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1490   PetscValidIntPointer(nfuncs,2);
1491   *nfuncs = snes->nfuncs;
1492   PetscFunctionReturn(0);
1493 }
1494 
1495 /*@
1496    SNESGetLinearSolveFailures - Gets the number of failed (non-converged)
1497    linear solvers.
1498 
1499    Not Collective
1500 
1501    Input Parameter:
1502 .  snes - SNES context
1503 
1504    Output Parameter:
1505 .  nfails - number of failed solves
1506 
1507    Level: intermediate
1508 
1509    Options Database Keys:
1510 . -snes_max_linear_solve_fail <num> - The number of failures before the solve is terminated
1511 
1512    Notes:
1513    This counter is reset to zero for each successive call to SNESSolve().
1514 
1515 .seealso: `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`
1516 @*/
1517 PetscErrorCode  SNESGetLinearSolveFailures(SNES snes,PetscInt *nfails)
1518 {
1519   PetscFunctionBegin;
1520   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1521   PetscValidIntPointer(nfails,2);
1522   *nfails = snes->numLinearSolveFailures;
1523   PetscFunctionReturn(0);
1524 }
1525 
1526 /*@
1527    SNESSetMaxLinearSolveFailures - the number of failed linear solve attempts
1528    allowed before SNES returns with a diverged reason of SNES_DIVERGED_LINEAR_SOLVE
1529 
1530    Logically Collective on SNES
1531 
1532    Input Parameters:
1533 +  snes     - SNES context
1534 -  maxFails - maximum allowed linear solve failures
1535 
1536    Level: intermediate
1537 
1538    Options Database Keys:
1539 . -snes_max_linear_solve_fail <num> - The number of failures before the solve is terminated
1540 
1541    Notes:
1542     By default this is 0; that is SNES returns on the first failed linear solve
1543 
1544 .seealso: `SNESGetLinearSolveFailures()`, `SNESGetMaxLinearSolveFailures()`, `SNESGetLinearSolveIterations()`
1545 @*/
1546 PetscErrorCode  SNESSetMaxLinearSolveFailures(SNES snes, PetscInt maxFails)
1547 {
1548   PetscFunctionBegin;
1549   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1550   PetscValidLogicalCollectiveInt(snes,maxFails,2);
1551   snes->maxLinearSolveFailures = maxFails;
1552   PetscFunctionReturn(0);
1553 }
1554 
1555 /*@
1556    SNESGetMaxLinearSolveFailures - gets the maximum number of linear solve failures that
1557      are allowed before SNES terminates
1558 
1559    Not Collective
1560 
1561    Input Parameter:
1562 .  snes     - SNES context
1563 
1564    Output Parameter:
1565 .  maxFails - maximum of unsuccessful solves allowed
1566 
1567    Level: intermediate
1568 
1569    Notes:
1570     By default this is 1; that is SNES returns on the first failed linear solve
1571 
1572 .seealso: `SNESGetLinearSolveFailures()`, `SNESGetLinearSolveIterations()`, `SNESSetMaxLinearSolveFailures()`,
1573 @*/
1574 PetscErrorCode  SNESGetMaxLinearSolveFailures(SNES snes, PetscInt *maxFails)
1575 {
1576   PetscFunctionBegin;
1577   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1578   PetscValidIntPointer(maxFails,2);
1579   *maxFails = snes->maxLinearSolveFailures;
1580   PetscFunctionReturn(0);
1581 }
1582 
1583 /*@
1584    SNESGetLinearSolveIterations - Gets the total number of linear iterations
1585    used by the nonlinear solver.
1586 
1587    Not Collective
1588 
1589    Input Parameter:
1590 .  snes - SNES context
1591 
1592    Output Parameter:
1593 .  lits - number of linear iterations
1594 
1595    Notes:
1596    This counter is reset to zero for each successive call to SNESSolve() unless SNESSetCountersReset() is used.
1597 
1598    If the linear solver fails inside the SNESSolve() the iterations for that call to the linear solver are not included. If you wish to count them
1599    then call KSPGetIterationNumber() after the failed solve.
1600 
1601    Level: intermediate
1602 
1603 .seealso: `SNESGetIterationNumber()`, `SNESGetLinearSolveFailures()`, `SNESGetMaxLinearSolveFailures()`, `SNESSetCountersReset()`
1604 @*/
1605 PetscErrorCode  SNESGetLinearSolveIterations(SNES snes,PetscInt *lits)
1606 {
1607   PetscFunctionBegin;
1608   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1609   PetscValidIntPointer(lits,2);
1610   *lits = snes->linear_its;
1611   PetscFunctionReturn(0);
1612 }
1613 
1614 /*@
1615    SNESSetCountersReset - Sets whether or not the counters for linear iterations and function evaluations
1616    are reset every time SNESSolve() is called.
1617 
1618    Logically Collective on SNES
1619 
1620    Input Parameters:
1621 +  snes - SNES context
1622 -  reset - whether to reset the counters or not
1623 
1624    Notes:
1625    This defaults to PETSC_TRUE
1626 
1627    Level: developer
1628 
1629 .seealso: `SNESGetNumberFunctionEvals()`, `SNESGetLinearSolveIterations()`, `SNESGetNPC()`
1630 @*/
1631 PetscErrorCode  SNESSetCountersReset(SNES snes,PetscBool reset)
1632 {
1633   PetscFunctionBegin;
1634   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1635   PetscValidLogicalCollectiveBool(snes,reset,2);
1636   snes->counters_reset = reset;
1637   PetscFunctionReturn(0);
1638 }
1639 
1640 /*@
1641    SNESSetKSP - Sets a KSP context for the SNES object to use
1642 
1643    Not Collective, but the SNES and KSP objects must live on the same MPI_Comm
1644 
1645    Input Parameters:
1646 +  snes - the SNES context
1647 -  ksp - the KSP context
1648 
1649    Notes:
1650    The SNES object already has its KSP object, you can obtain with SNESGetKSP()
1651    so this routine is rarely needed.
1652 
1653    The KSP object that is already in the SNES object has its reference count
1654    decreased by one.
1655 
1656    Level: developer
1657 
1658 .seealso: `KSPGetPC()`, `SNESCreate()`, `KSPCreate()`, `SNESSetKSP()`
1659 @*/
1660 PetscErrorCode  SNESSetKSP(SNES snes,KSP ksp)
1661 {
1662   PetscFunctionBegin;
1663   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1664   PetscValidHeaderSpecific(ksp,KSP_CLASSID,2);
1665   PetscCheckSameComm(snes,1,ksp,2);
1666   PetscCall(PetscObjectReference((PetscObject)ksp));
1667   if (snes->ksp) PetscCall(PetscObjectDereference((PetscObject)snes->ksp));
1668   snes->ksp = ksp;
1669   PetscFunctionReturn(0);
1670 }
1671 
1672 /* -----------------------------------------------------------*/
1673 /*@
1674    SNESCreate - Creates a nonlinear solver context.
1675 
1676    Collective
1677 
1678    Input Parameters:
1679 .  comm - MPI communicator
1680 
1681    Output Parameter:
1682 .  outsnes - the new SNES context
1683 
1684    Options Database Keys:
1685 +   -snes_mf - Activates default matrix-free Jacobian-vector products,
1686                and no preconditioning matrix
1687 .   -snes_mf_operator - Activates default matrix-free Jacobian-vector
1688                products, and a user-provided preconditioning matrix
1689                as set by SNESSetJacobian()
1690 -   -snes_fd - Uses (slow!) finite differences to compute Jacobian
1691 
1692    Level: beginner
1693 
1694    Developer Notes:
1695     SNES always creates a KSP object even though many SNES methods do not use it. This is
1696                     unfortunate and should be fixed at some point. The flag snes->usesksp indicates if the
1697                     particular method does use KSP and regulates if the information about the KSP is printed
1698                     in SNESView(). TSSetFromOptions() does call SNESSetFromOptions() which can lead to users being confused
1699                     by help messages about meaningless SNES options.
1700 
1701                     SNES always creates the snes->kspconvctx even though it is used by only one type. This should
1702                     be fixed.
1703 
1704 .seealso: `SNESSolve()`, `SNESDestroy()`, `SNES`, `SNESSetLagPreconditioner()`, `SNESSetLagJacobian()`
1705 
1706 @*/
1707 PetscErrorCode  SNESCreate(MPI_Comm comm,SNES *outsnes)
1708 {
1709   SNES           snes;
1710   SNESKSPEW      *kctx;
1711 
1712   PetscFunctionBegin;
1713   PetscValidPointer(outsnes,2);
1714   *outsnes = NULL;
1715   PetscCall(SNESInitializePackage());
1716 
1717   PetscCall(PetscHeaderCreate(snes,SNES_CLASSID,"SNES","Nonlinear solver","SNES",comm,SNESDestroy,SNESView));
1718 
1719   snes->ops->converged    = SNESConvergedDefault;
1720   snes->usesksp           = PETSC_TRUE;
1721   snes->tolerancesset     = PETSC_FALSE;
1722   snes->max_its           = 50;
1723   snes->max_funcs         = 10000;
1724   snes->norm              = 0.0;
1725   snes->xnorm             = 0.0;
1726   snes->ynorm             = 0.0;
1727   snes->normschedule      = SNES_NORM_ALWAYS;
1728   snes->functype          = SNES_FUNCTION_DEFAULT;
1729 #if defined(PETSC_USE_REAL_SINGLE)
1730   snes->rtol              = 1.e-5;
1731 #else
1732   snes->rtol              = 1.e-8;
1733 #endif
1734   snes->ttol              = 0.0;
1735 #if defined(PETSC_USE_REAL_SINGLE)
1736   snes->abstol            = 1.e-25;
1737 #else
1738   snes->abstol            = 1.e-50;
1739 #endif
1740 #if defined(PETSC_USE_REAL_SINGLE)
1741   snes->stol              = 1.e-5;
1742 #else
1743   snes->stol              = 1.e-8;
1744 #endif
1745 #if defined(PETSC_USE_REAL_SINGLE)
1746   snes->deltatol          = 1.e-6;
1747 #else
1748   snes->deltatol          = 1.e-12;
1749 #endif
1750   snes->divtol            = 1.e4;
1751   snes->rnorm0            = 0;
1752   snes->nfuncs            = 0;
1753   snes->numFailures       = 0;
1754   snes->maxFailures       = 1;
1755   snes->linear_its        = 0;
1756   snes->lagjacobian       = 1;
1757   snes->jac_iter          = 0;
1758   snes->lagjac_persist    = PETSC_FALSE;
1759   snes->lagpreconditioner = 1;
1760   snes->pre_iter          = 0;
1761   snes->lagpre_persist    = PETSC_FALSE;
1762   snes->numbermonitors    = 0;
1763   snes->numberreasonviews = 0;
1764   snes->data              = NULL;
1765   snes->setupcalled       = PETSC_FALSE;
1766   snes->ksp_ewconv        = PETSC_FALSE;
1767   snes->nwork             = 0;
1768   snes->work              = NULL;
1769   snes->nvwork            = 0;
1770   snes->vwork             = NULL;
1771   snes->conv_hist_len     = 0;
1772   snes->conv_hist_max     = 0;
1773   snes->conv_hist         = NULL;
1774   snes->conv_hist_its     = NULL;
1775   snes->conv_hist_reset   = PETSC_TRUE;
1776   snes->counters_reset    = PETSC_TRUE;
1777   snes->vec_func_init_set = PETSC_FALSE;
1778   snes->reason            = SNES_CONVERGED_ITERATING;
1779   snes->npcside           = PC_RIGHT;
1780   snes->setfromoptionscalled = 0;
1781 
1782   snes->mf          = PETSC_FALSE;
1783   snes->mf_operator = PETSC_FALSE;
1784   snes->mf_version  = 1;
1785 
1786   snes->numLinearSolveFailures = 0;
1787   snes->maxLinearSolveFailures = 1;
1788 
1789   snes->vizerotolerance = 1.e-8;
1790   snes->checkjacdomainerror = PetscDefined(USE_DEBUG) ? PETSC_TRUE : PETSC_FALSE;
1791 
1792   /* Set this to true if the implementation of SNESSolve_XXX does compute the residual at the final solution. */
1793   snes->alwayscomputesfinalresidual = PETSC_FALSE;
1794 
1795   /* Create context to compute Eisenstat-Walker relative tolerance for KSP */
1796   PetscCall(PetscNewLog(snes,&kctx));
1797 
1798   snes->kspconvctx  = (void*)kctx;
1799   kctx->version     = 2;
1800   kctx->rtol_0      = .3; /* Eisenstat and Walker suggest rtol_0=.5, but
1801                              this was too large for some test cases */
1802   kctx->rtol_last   = 0.0;
1803   kctx->rtol_max    = .9;
1804   kctx->gamma       = 1.0;
1805   kctx->alpha       = .5*(1.0 + PetscSqrtReal(5.0));
1806   kctx->alpha2      = kctx->alpha;
1807   kctx->threshold   = .1;
1808   kctx->lresid_last = 0.0;
1809   kctx->norm_last   = 0.0;
1810 
1811   *outsnes = snes;
1812   PetscFunctionReturn(0);
1813 }
1814 
1815 /*MC
1816     SNESFunction - Functional form used to convey the nonlinear function to be solved by SNES
1817 
1818      Synopsis:
1819      #include "petscsnes.h"
1820      PetscErrorCode SNESFunction(SNES snes,Vec x,Vec f,void *ctx);
1821 
1822      Collective on snes
1823 
1824      Input Parameters:
1825 +     snes - the SNES context
1826 .     x    - state at which to evaluate residual
1827 -     ctx     - optional user-defined function context, passed in with SNESSetFunction()
1828 
1829      Output Parameter:
1830 .     f  - vector to put residual (function value)
1831 
1832    Level: intermediate
1833 
1834 .seealso: `SNESSetFunction()`, `SNESGetFunction()`
1835 M*/
1836 
1837 /*@C
1838    SNESSetFunction - Sets the function evaluation routine and function
1839    vector for use by the SNES routines in solving systems of nonlinear
1840    equations.
1841 
1842    Logically Collective on SNES
1843 
1844    Input Parameters:
1845 +  snes - the SNES context
1846 .  r - vector to store function values, may be NULL
1847 .  f - function evaluation routine; see SNESFunction for calling sequence details
1848 -  ctx - [optional] user-defined context for private data for the
1849          function evaluation routine (may be NULL)
1850 
1851    Notes:
1852    The Newton-like methods typically solve linear systems of the form
1853 $      f'(x) x = -f(x),
1854    where f'(x) denotes the Jacobian matrix and f(x) is the function.
1855 
1856    Level: beginner
1857 
1858 .seealso: `SNESGetFunction()`, `SNESComputeFunction()`, `SNESSetJacobian()`, `SNESSetPicard()`, `SNESFunction`
1859 @*/
1860 PetscErrorCode  SNESSetFunction(SNES snes,Vec r,PetscErrorCode (*f)(SNES,Vec,Vec,void*),void *ctx)
1861 {
1862   DM             dm;
1863 
1864   PetscFunctionBegin;
1865   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1866   if (r) {
1867     PetscValidHeaderSpecific(r,VEC_CLASSID,2);
1868     PetscCheckSameComm(snes,1,r,2);
1869     PetscCall(PetscObjectReference((PetscObject)r));
1870     PetscCall(VecDestroy(&snes->vec_func));
1871     snes->vec_func = r;
1872   }
1873   PetscCall(SNESGetDM(snes,&dm));
1874   PetscCall(DMSNESSetFunction(dm,f,ctx));
1875   if (f == SNESPicardComputeFunction) {
1876     PetscCall(DMSNESSetMFFunction(dm,SNESPicardComputeMFFunction,ctx));
1877   }
1878   PetscFunctionReturn(0);
1879 }
1880 
1881 /*@C
1882    SNESSetInitialFunction - Sets the function vector to be used as the
1883    function norm at the initialization of the method.  In some
1884    instances, the user has precomputed the function before calling
1885    SNESSolve.  This function allows one to avoid a redundant call
1886    to SNESComputeFunction in that case.
1887 
1888    Logically Collective on SNES
1889 
1890    Input Parameters:
1891 +  snes - the SNES context
1892 -  f - vector to store function value
1893 
1894    Notes:
1895    This should not be modified during the solution procedure.
1896 
1897    This is used extensively in the SNESFAS hierarchy and in nonlinear preconditioning.
1898 
1899    Level: developer
1900 
1901 .seealso: `SNESSetFunction()`, `SNESComputeFunction()`, `SNESSetInitialFunctionNorm()`
1902 @*/
1903 PetscErrorCode  SNESSetInitialFunction(SNES snes, Vec f)
1904 {
1905   Vec            vec_func;
1906 
1907   PetscFunctionBegin;
1908   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1909   PetscValidHeaderSpecific(f,VEC_CLASSID,2);
1910   PetscCheckSameComm(snes,1,f,2);
1911   if (snes->npcside == PC_LEFT && snes->functype == SNES_FUNCTION_PRECONDITIONED) {
1912     snes->vec_func_init_set = PETSC_FALSE;
1913     PetscFunctionReturn(0);
1914   }
1915   PetscCall(SNESGetFunction(snes,&vec_func,NULL,NULL));
1916   PetscCall(VecCopy(f,vec_func));
1917 
1918   snes->vec_func_init_set = PETSC_TRUE;
1919   PetscFunctionReturn(0);
1920 }
1921 
1922 /*@
1923    SNESSetNormSchedule - Sets the SNESNormSchedule used in convergence and monitoring
1924    of the SNES method.
1925 
1926    Logically Collective on SNES
1927 
1928    Input Parameters:
1929 +  snes - the SNES context
1930 -  normschedule - the frequency of norm computation
1931 
1932    Options Database Key:
1933 .  -snes_norm_schedule <none, always, initialonly, finalonly, initialfinalonly> - set the schedule
1934 
1935    Notes:
1936    Only certain SNES methods support certain SNESNormSchedules.  Most require evaluation
1937    of the nonlinear function and the taking of its norm at every iteration to
1938    even ensure convergence at all.  However, methods such as custom Gauss-Seidel methods
1939    (SNESNGS) and the like do not require the norm of the function to be computed, and therefore
1940    may either be monitored for convergence or not.  As these are often used as nonlinear
1941    preconditioners, monitoring the norm of their error is not a useful enterprise within
1942    their solution.
1943 
1944    Level: developer
1945 
1946 .seealso: `SNESGetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
1947 @*/
1948 PetscErrorCode  SNESSetNormSchedule(SNES snes, SNESNormSchedule normschedule)
1949 {
1950   PetscFunctionBegin;
1951   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1952   snes->normschedule = normschedule;
1953   PetscFunctionReturn(0);
1954 }
1955 
1956 /*@
1957    SNESGetNormSchedule - Gets the SNESNormSchedule used in convergence and monitoring
1958    of the SNES method.
1959 
1960    Logically Collective on SNES
1961 
1962    Input Parameters:
1963 +  snes - the SNES context
1964 -  normschedule - the type of the norm used
1965 
1966    Level: advanced
1967 
1968 .seealso: `SNESSetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
1969 @*/
1970 PetscErrorCode  SNESGetNormSchedule(SNES snes, SNESNormSchedule *normschedule)
1971 {
1972   PetscFunctionBegin;
1973   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1974   *normschedule = snes->normschedule;
1975   PetscFunctionReturn(0);
1976 }
1977 
1978 /*@
1979   SNESSetFunctionNorm - Sets the last computed residual norm.
1980 
1981   Logically Collective on SNES
1982 
1983   Input Parameters:
1984 + snes - the SNES context
1985 
1986 - normschedule - the frequency of norm computation
1987 
1988   Level: developer
1989 
1990 .seealso: `SNESGetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
1991 @*/
1992 PetscErrorCode SNESSetFunctionNorm(SNES snes, PetscReal norm)
1993 {
1994   PetscFunctionBegin;
1995   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
1996   snes->norm = norm;
1997   PetscFunctionReturn(0);
1998 }
1999 
2000 /*@
2001   SNESGetFunctionNorm - Gets the last computed norm of the residual
2002 
2003   Not Collective
2004 
2005   Input Parameter:
2006 . snes - the SNES context
2007 
2008   Output Parameter:
2009 . norm - the last computed residual norm
2010 
2011   Level: developer
2012 
2013 .seealso: `SNESSetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
2014 @*/
2015 PetscErrorCode SNESGetFunctionNorm(SNES snes, PetscReal *norm)
2016 {
2017   PetscFunctionBegin;
2018   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2019   PetscValidRealPointer(norm, 2);
2020   *norm = snes->norm;
2021   PetscFunctionReturn(0);
2022 }
2023 
2024 /*@
2025   SNESGetUpdateNorm - Gets the last computed norm of the Newton update
2026 
2027   Not Collective
2028 
2029   Input Parameter:
2030 . snes - the SNES context
2031 
2032   Output Parameter:
2033 . ynorm - the last computed update norm
2034 
2035   Level: developer
2036 
2037 .seealso: `SNESSetNormSchedule()`, `SNESComputeFunction()`, `SNESGetFunctionNorm()`
2038 @*/
2039 PetscErrorCode SNESGetUpdateNorm(SNES snes, PetscReal *ynorm)
2040 {
2041   PetscFunctionBegin;
2042   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2043   PetscValidRealPointer(ynorm, 2);
2044   *ynorm = snes->ynorm;
2045   PetscFunctionReturn(0);
2046 }
2047 
2048 /*@
2049   SNESGetSolutionNorm - Gets the last computed norm of the solution
2050 
2051   Not Collective
2052 
2053   Input Parameter:
2054 . snes - the SNES context
2055 
2056   Output Parameter:
2057 . xnorm - the last computed solution norm
2058 
2059   Level: developer
2060 
2061 .seealso: `SNESSetNormSchedule()`, `SNESComputeFunction()`, `SNESGetFunctionNorm()`, `SNESGetUpdateNorm()`
2062 @*/
2063 PetscErrorCode SNESGetSolutionNorm(SNES snes, PetscReal *xnorm)
2064 {
2065   PetscFunctionBegin;
2066   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2067   PetscValidRealPointer(xnorm, 2);
2068   *xnorm = snes->xnorm;
2069   PetscFunctionReturn(0);
2070 }
2071 
2072 /*@C
2073    SNESSetFunctionType - Sets the SNESNormSchedule used in convergence and monitoring
2074    of the SNES method.
2075 
2076    Logically Collective on SNES
2077 
2078    Input Parameters:
2079 +  snes - the SNES context
2080 -  normschedule - the frequency of norm computation
2081 
2082    Notes:
2083    Only certain SNES methods support certain SNESNormSchedules.  Most require evaluation
2084    of the nonlinear function and the taking of its norm at every iteration to
2085    even ensure convergence at all.  However, methods such as custom Gauss-Seidel methods
2086    (SNESNGS) and the like do not require the norm of the function to be computed, and therefore
2087    may either be monitored for convergence or not.  As these are often used as nonlinear
2088    preconditioners, monitoring the norm of their error is not a useful enterprise within
2089    their solution.
2090 
2091    Level: developer
2092 
2093 .seealso: `SNESGetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
2094 @*/
2095 PetscErrorCode  SNESSetFunctionType(SNES snes, SNESFunctionType type)
2096 {
2097   PetscFunctionBegin;
2098   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2099   snes->functype = type;
2100   PetscFunctionReturn(0);
2101 }
2102 
2103 /*@C
2104    SNESGetFunctionType - Gets the SNESNormSchedule used in convergence and monitoring
2105    of the SNES method.
2106 
2107    Logically Collective on SNES
2108 
2109    Input Parameters:
2110 +  snes - the SNES context
2111 -  normschedule - the type of the norm used
2112 
2113    Level: advanced
2114 
2115 .seealso: `SNESSetNormSchedule()`, `SNESComputeFunction()`, `VecNorm()`, `SNESSetFunction()`, `SNESSetInitialFunction()`, `SNESNormSchedule`
2116 @*/
2117 PetscErrorCode  SNESGetFunctionType(SNES snes, SNESFunctionType *type)
2118 {
2119   PetscFunctionBegin;
2120   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2121   *type = snes->functype;
2122   PetscFunctionReturn(0);
2123 }
2124 
2125 /*MC
2126     SNESNGSFunction - function used to convey a Gauss-Seidel sweep on the nonlinear function
2127 
2128      Synopsis:
2129      #include <petscsnes.h>
2130 $    SNESNGSFunction(SNES snes,Vec x,Vec b,void *ctx);
2131 
2132      Collective on snes
2133 
2134      Input Parameters:
2135 +  X   - solution vector
2136 .  B   - RHS vector
2137 -  ctx - optional user-defined Gauss-Seidel context
2138 
2139      Output Parameter:
2140 .  X   - solution vector
2141 
2142    Level: intermediate
2143 
2144 .seealso: `SNESSetNGS()`, `SNESGetNGS()`
2145 M*/
2146 
2147 /*@C
2148    SNESSetNGS - Sets the user nonlinear Gauss-Seidel routine for
2149    use with composed nonlinear solvers.
2150 
2151    Input Parameters:
2152 +  snes   - the SNES context
2153 .  f - function evaluation routine to apply Gauss-Seidel see SNESNGSFunction
2154 -  ctx    - [optional] user-defined context for private data for the
2155             smoother evaluation routine (may be NULL)
2156 
2157    Notes:
2158    The NGS routines are used by the composed nonlinear solver to generate
2159     a problem appropriate update to the solution, particularly FAS.
2160 
2161    Level: intermediate
2162 
2163 .seealso: `SNESGetFunction()`, `SNESComputeNGS()`
2164 @*/
2165 PetscErrorCode SNESSetNGS(SNES snes,PetscErrorCode (*f)(SNES,Vec,Vec,void*),void *ctx)
2166 {
2167   DM             dm;
2168 
2169   PetscFunctionBegin;
2170   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2171   PetscCall(SNESGetDM(snes,&dm));
2172   PetscCall(DMSNESSetNGS(dm,f,ctx));
2173   PetscFunctionReturn(0);
2174 }
2175 
2176 /*
2177      This is used for -snes_mf_operator; it uses a duplicate of snes->jacobian_pre because snes->jacobian_pre cannot be
2178    changed during the KSPSolve()
2179 */
2180 PetscErrorCode SNESPicardComputeMFFunction(SNES snes,Vec x,Vec f,void *ctx)
2181 {
2182   DM             dm;
2183   DMSNES         sdm;
2184 
2185   PetscFunctionBegin;
2186   PetscCall(SNESGetDM(snes,&dm));
2187   PetscCall(DMGetDMSNES(dm,&sdm));
2188   PetscCheck(sdm->ops->computepjacobian,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetPicard() to provide Picard Jacobian.");
2189   /*  A(x)*x - b(x) */
2190   if (sdm->ops->computepfunction) {
2191     PetscStackPush("SNES Picard user function");
2192     PetscCall((*sdm->ops->computepfunction)(snes,x,f,sdm->pctx));
2193     PetscStackPop;
2194     PetscCall(VecScale(f,-1.0));
2195     if (!snes->picard) {
2196       /* Cannot share nonzero pattern because of the possible use of SNESComputeJacobianDefault() */
2197       PetscCall(MatDuplicate(snes->jacobian_pre,MAT_DO_NOT_COPY_VALUES,&snes->picard));
2198     }
2199     PetscStackPush("SNES Picard user Jacobian");
2200     PetscCall((*sdm->ops->computepjacobian)(snes,x,snes->picard,snes->picard,sdm->pctx));
2201     PetscStackPop;
2202     PetscCall(MatMultAdd(snes->picard,x,f,f));
2203   } else {
2204     PetscStackPush("SNES Picard user Jacobian");
2205     PetscCall((*sdm->ops->computepjacobian)(snes,x,snes->picard,snes->picard,sdm->pctx));
2206     PetscStackPop;
2207     PetscCall(MatMult(snes->picard,x,f));
2208   }
2209   PetscFunctionReturn(0);
2210 }
2211 
2212 PetscErrorCode SNESPicardComputeFunction(SNES snes,Vec x,Vec f,void *ctx)
2213 {
2214   DM             dm;
2215   DMSNES         sdm;
2216 
2217   PetscFunctionBegin;
2218   PetscCall(SNESGetDM(snes,&dm));
2219   PetscCall(DMGetDMSNES(dm,&sdm));
2220   PetscCheck(sdm->ops->computepjacobian,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetPicard() to provide Picard Jacobian.");
2221   /*  A(x)*x - b(x) */
2222   if (sdm->ops->computepfunction) {
2223     PetscStackPush("SNES Picard user function");
2224     PetscCall((*sdm->ops->computepfunction)(snes,x,f,sdm->pctx));
2225     PetscStackPop;
2226     PetscCall(VecScale(f,-1.0));
2227     PetscStackPush("SNES Picard user Jacobian");
2228     PetscCall((*sdm->ops->computepjacobian)(snes,x,snes->jacobian,snes->jacobian_pre,sdm->pctx));
2229     PetscStackPop;
2230     PetscCall(MatMultAdd(snes->jacobian_pre,x,f,f));
2231   } else {
2232     PetscStackPush("SNES Picard user Jacobian");
2233     PetscCall((*sdm->ops->computepjacobian)(snes,x,snes->jacobian,snes->jacobian_pre,sdm->pctx));
2234     PetscStackPop;
2235     PetscCall(MatMult(snes->jacobian_pre,x,f));
2236   }
2237   PetscFunctionReturn(0);
2238 }
2239 
2240 PetscErrorCode SNESPicardComputeJacobian(SNES snes,Vec x1,Mat J,Mat B,void *ctx)
2241 {
2242   PetscFunctionBegin;
2243   /* the jacobian matrix should be pre-filled in SNESPicardComputeFunction */
2244   /* must assembly if matrix-free to get the last SNES solution */
2245   PetscCall(MatAssemblyBegin(J,MAT_FINAL_ASSEMBLY));
2246   PetscCall(MatAssemblyEnd(J,MAT_FINAL_ASSEMBLY));
2247   PetscFunctionReturn(0);
2248 }
2249 
2250 /*@C
2251    SNESSetPicard - Use SNES to solve the system A(x) x = bp(x) + b via a Picard type iteration (Picard linearization)
2252 
2253    Logically Collective on SNES
2254 
2255    Input Parameters:
2256 +  snes - the SNES context
2257 .  r - vector to store function values, may be NULL
2258 .  bp - function evaluation routine, may be NULL
2259 .  Amat - matrix with which A(x) x - bp(x) - b is to be computed
2260 .  Pmat - matrix from which preconditioner is computed (usually the same as Amat)
2261 .  J  - function to compute matrix values, see SNESJacobianFunction() for details on its calling sequence
2262 -  ctx - [optional] user-defined context for private data for the function evaluation routine (may be NULL)
2263 
2264    Notes:
2265     It is often better to provide the nonlinear function F() and some approximation to its Jacobian directly and use
2266     an approximate Newton solver. This interface is provided to allow porting/testing a previous Picard based code in PETSc before converting it to approximate Newton.
2267 
2268     One can call SNESSetPicard() or SNESSetFunction() (and possibly SNESSetJacobian()) but cannot call both
2269 
2270 $     Solves the equation A(x) x = bp(x) - b via the defect correction algorithm A(x^{n}) (x^{n+1} - x^{n}) = bp(x^{n}) + b - A(x^{n})x^{n}
2271 $     Note that when an exact solver is used this corresponds to the "classic" Picard A(x^{n}) x^{n+1} = bp(x^{n}) + b iteration.
2272 
2273      Run with -snes_mf_operator to solve the system with Newton's method using A(x^{n}) to construct the preconditioner.
2274 
2275    We implement the defect correction form of the Picard iteration because it converges much more generally when inexact linear solvers are used then
2276    the direct Picard iteration A(x^n) x^{n+1} = bp(x^n) + b
2277 
2278    There is some controversity over the definition of a Picard iteration for nonlinear systems but almost everyone agrees that it involves a linear solve and some
2279    believe it is the iteration  A(x^{n}) x^{n+1} = b(x^{n}) hence we use the name Picard. If anyone has an authoritative  reference that defines the Picard iteration
2280    different please contact us at petsc-dev@mcs.anl.gov and we'll have an entirely new argument :-).
2281 
2282    When used with -snes_mf_operator this will run matrix-free Newton's method where the matrix-vector product is of the true Jacobian of A(x)x - bp(x) -b.
2283 
2284    When used with -snes_fd this will compute the true Jacobian (very slowly one column at at time) and thus represent Newton's method.
2285 
2286    When used with -snes_fd_coloring this will compute the Jacobian via coloring and thus represent a faster implementation of Newton's method. But the
2287    the nonzero structure of the Jacobian is, in general larger than that of the Picard matrix A so you must provide in A the needed nonzero structure for the correct
2288    coloring. When using DMDA this may mean creating the matrix A with DMCreateMatrix() using a wider stencil than strictly needed for A or with a DMDA_STENCIL_BOX.
2289    See the commment in src/snes/tutorials/ex15.c.
2290 
2291    Level: intermediate
2292 
2293 .seealso: `SNESGetFunction()`, `SNESSetFunction()`, `SNESComputeFunction()`, `SNESSetJacobian()`, `SNESGetPicard()`, `SNESLineSearchPreCheckPicard()`, `SNESJacobianFunction`
2294 @*/
2295 PetscErrorCode  SNESSetPicard(SNES snes,Vec r,PetscErrorCode (*bp)(SNES,Vec,Vec,void*),Mat Amat, Mat Pmat, PetscErrorCode (*J)(SNES,Vec,Mat,Mat,void*),void *ctx)
2296 {
2297   DM             dm;
2298 
2299   PetscFunctionBegin;
2300   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2301   PetscCall(SNESGetDM(snes, &dm));
2302   PetscCall(DMSNESSetPicard(dm,bp,J,ctx));
2303   PetscCall(DMSNESSetMFFunction(dm,SNESPicardComputeMFFunction,ctx));
2304   PetscCall(SNESSetFunction(snes,r,SNESPicardComputeFunction,ctx));
2305   PetscCall(SNESSetJacobian(snes,Amat,Pmat,SNESPicardComputeJacobian,ctx));
2306   PetscFunctionReturn(0);
2307 }
2308 
2309 /*@C
2310    SNESGetPicard - Returns the context for the Picard iteration
2311 
2312    Not Collective, but Vec is parallel if SNES is parallel. Collective if Vec is requested, but has not been created yet.
2313 
2314    Input Parameter:
2315 .  snes - the SNES context
2316 
2317    Output Parameters:
2318 +  r - the function (or NULL)
2319 .  f - the function (or NULL); see SNESFunction for calling sequence details
2320 .  Amat - the matrix used to defined the operation A(x) x - b(x) (or NULL)
2321 .  Pmat  - the matrix from which the preconditioner will be constructed (or NULL)
2322 .  J - the function for matrix evaluation (or NULL); see SNESJacobianFunction for calling sequence details
2323 -  ctx - the function context (or NULL)
2324 
2325    Level: advanced
2326 
2327 .seealso: `SNESSetPicard()`, `SNESGetFunction()`, `SNESGetJacobian()`, `SNESGetDM()`, `SNESFunction`, `SNESJacobianFunction`
2328 @*/
2329 PetscErrorCode  SNESGetPicard(SNES snes,Vec *r,PetscErrorCode (**f)(SNES,Vec,Vec,void*),Mat *Amat, Mat *Pmat, PetscErrorCode (**J)(SNES,Vec,Mat,Mat,void*),void **ctx)
2330 {
2331   DM             dm;
2332 
2333   PetscFunctionBegin;
2334   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2335   PetscCall(SNESGetFunction(snes,r,NULL,NULL));
2336   PetscCall(SNESGetJacobian(snes,Amat,Pmat,NULL,NULL));
2337   PetscCall(SNESGetDM(snes,&dm));
2338   PetscCall(DMSNESGetPicard(dm,f,J,ctx));
2339   PetscFunctionReturn(0);
2340 }
2341 
2342 /*@C
2343    SNESSetComputeInitialGuess - Sets a routine used to compute an initial guess for the problem
2344 
2345    Logically Collective on SNES
2346 
2347    Input Parameters:
2348 +  snes - the SNES context
2349 .  func - function evaluation routine
2350 -  ctx - [optional] user-defined context for private data for the
2351          function evaluation routine (may be NULL)
2352 
2353    Calling sequence of func:
2354 $    func (SNES snes,Vec x,void *ctx);
2355 
2356 .  f - function vector
2357 -  ctx - optional user-defined function context
2358 
2359    Level: intermediate
2360 
2361 .seealso: `SNESGetFunction()`, `SNESComputeFunction()`, `SNESSetJacobian()`
2362 @*/
2363 PetscErrorCode  SNESSetComputeInitialGuess(SNES snes,PetscErrorCode (*func)(SNES,Vec,void*),void *ctx)
2364 {
2365   PetscFunctionBegin;
2366   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2367   if (func) snes->ops->computeinitialguess = func;
2368   if (ctx)  snes->initialguessP            = ctx;
2369   PetscFunctionReturn(0);
2370 }
2371 
2372 /* --------------------------------------------------------------- */
2373 /*@C
2374    SNESGetRhs - Gets the vector for solving F(x) = rhs. If rhs is not set
2375    it assumes a zero right hand side.
2376 
2377    Logically Collective on SNES
2378 
2379    Input Parameter:
2380 .  snes - the SNES context
2381 
2382    Output Parameter:
2383 .  rhs - the right hand side vector or NULL if the right hand side vector is null
2384 
2385    Level: intermediate
2386 
2387 .seealso: `SNESGetSolution()`, `SNESGetFunction()`, `SNESComputeFunction()`, `SNESSetJacobian()`, `SNESSetFunction()`
2388 @*/
2389 PetscErrorCode  SNESGetRhs(SNES snes,Vec *rhs)
2390 {
2391   PetscFunctionBegin;
2392   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2393   PetscValidPointer(rhs,2);
2394   *rhs = snes->vec_rhs;
2395   PetscFunctionReturn(0);
2396 }
2397 
2398 /*@
2399    SNESComputeFunction - Calls the function that has been set with SNESSetFunction().
2400 
2401    Collective on SNES
2402 
2403    Input Parameters:
2404 +  snes - the SNES context
2405 -  x - input vector
2406 
2407    Output Parameter:
2408 .  y - function vector, as set by SNESSetFunction()
2409 
2410    Notes:
2411    SNESComputeFunction() is typically used within nonlinear solvers
2412    implementations, so users would not generally call this routine themselves.
2413 
2414    Level: developer
2415 
2416 .seealso: `SNESSetFunction()`, `SNESGetFunction()`, `SNESComputeMFFunction()`
2417 @*/
2418 PetscErrorCode  SNESComputeFunction(SNES snes,Vec x,Vec y)
2419 {
2420   DM             dm;
2421   DMSNES         sdm;
2422 
2423   PetscFunctionBegin;
2424   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2425   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
2426   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
2427   PetscCheckSameComm(snes,1,x,2);
2428   PetscCheckSameComm(snes,1,y,3);
2429   PetscCall(VecValidValues(x,2,PETSC_TRUE));
2430 
2431   PetscCall(SNESGetDM(snes,&dm));
2432   PetscCall(DMGetDMSNES(dm,&sdm));
2433   if (sdm->ops->computefunction) {
2434     if (sdm->ops->computefunction != SNESObjectiveComputeFunctionDefaultFD) {
2435       PetscCall(PetscLogEventBegin(SNES_FunctionEval,snes,x,y,0));
2436     }
2437     PetscCall(VecLockReadPush(x));
2438     PetscStackPush("SNES user function");
2439     /* ensure domainerror is false prior to computefunction evaluation (may not have been reset) */
2440     snes->domainerror = PETSC_FALSE;
2441     PetscCall((*sdm->ops->computefunction)(snes,x,y,sdm->functionctx));
2442     PetscStackPop;
2443     PetscCall(VecLockReadPop(x));
2444     if (sdm->ops->computefunction != SNESObjectiveComputeFunctionDefaultFD) {
2445       PetscCall(PetscLogEventEnd(SNES_FunctionEval,snes,x,y,0));
2446     }
2447   } else if (snes->vec_rhs) {
2448     PetscCall(MatMult(snes->jacobian, x, y));
2449   } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetFunction() or SNESSetDM() before SNESComputeFunction(), likely called from SNESSolve().");
2450   if (snes->vec_rhs) {
2451     PetscCall(VecAXPY(y,-1.0,snes->vec_rhs));
2452   }
2453   snes->nfuncs++;
2454   /*
2455      domainerror might not be set on all processes; so we tag vector locally with Inf and the next inner product or norm will
2456      propagate the value to all processes
2457   */
2458   if (snes->domainerror) {
2459     PetscCall(VecSetInf(y));
2460   }
2461   PetscFunctionReturn(0);
2462 }
2463 
2464 /*@
2465    SNESComputeMFFunction - Calls the function that has been set with SNESSetMFFunction().
2466 
2467    Collective on SNES
2468 
2469    Input Parameters:
2470 +  snes - the SNES context
2471 -  x - input vector
2472 
2473    Output Parameter:
2474 .  y - function vector, as set by SNESSetMFFunction()
2475 
2476    Notes:
2477        SNESComputeMFFunction() is used within the matrix vector products called by the matrix created with MatCreateSNESMF()
2478    so users would not generally call this routine themselves.
2479 
2480        Since this function is intended for use with finite differencing it does not subtract the right hand side vector provided with SNESSolve()
2481     while SNESComputeFunction() does. As such, this routine cannot be used with  MatMFFDSetBase() with a provided F function value even if it applies the
2482     same function as SNESComputeFunction() if a SNESSolve() right hand side vector is use because the two functions difference would include this right hand side function.
2483 
2484    Level: developer
2485 
2486 .seealso: `SNESSetFunction()`, `SNESGetFunction()`, `SNESComputeFunction()`, `MatCreateSNESMF`
2487 @*/
2488 PetscErrorCode  SNESComputeMFFunction(SNES snes,Vec x,Vec y)
2489 {
2490   DM             dm;
2491   DMSNES         sdm;
2492 
2493   PetscFunctionBegin;
2494   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2495   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
2496   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
2497   PetscCheckSameComm(snes,1,x,2);
2498   PetscCheckSameComm(snes,1,y,3);
2499   PetscCall(VecValidValues(x,2,PETSC_TRUE));
2500 
2501   PetscCall(SNESGetDM(snes,&dm));
2502   PetscCall(DMGetDMSNES(dm,&sdm));
2503   PetscCall(PetscLogEventBegin(SNES_FunctionEval,snes,x,y,0));
2504   PetscCall(VecLockReadPush(x));
2505   PetscStackPush("SNES user function");
2506   /* ensure domainerror is false prior to computefunction evaluation (may not have been reset) */
2507   snes->domainerror = PETSC_FALSE;
2508   PetscCall((*sdm->ops->computemffunction)(snes,x,y,sdm->mffunctionctx));
2509   PetscStackPop;
2510   PetscCall(VecLockReadPop(x));
2511   PetscCall(PetscLogEventEnd(SNES_FunctionEval,snes,x,y,0));
2512   snes->nfuncs++;
2513   /*
2514      domainerror might not be set on all processes; so we tag vector locally with Inf and the next inner product or norm will
2515      propagate the value to all processes
2516   */
2517   if (snes->domainerror) {
2518     PetscCall(VecSetInf(y));
2519   }
2520   PetscFunctionReturn(0);
2521 }
2522 
2523 /*@
2524    SNESComputeNGS - Calls the Gauss-Seidel function that has been set with  SNESSetNGS().
2525 
2526    Collective on SNES
2527 
2528    Input Parameters:
2529 +  snes - the SNES context
2530 .  x - input vector
2531 -  b - rhs vector
2532 
2533    Output Parameter:
2534 .  x - new solution vector
2535 
2536    Notes:
2537    SNESComputeNGS() is typically used within composed nonlinear solver
2538    implementations, so most users would not generally call this routine
2539    themselves.
2540 
2541    Level: developer
2542 
2543 .seealso: `SNESSetNGS()`, `SNESComputeFunction()`
2544 @*/
2545 PetscErrorCode  SNESComputeNGS(SNES snes,Vec b,Vec x)
2546 {
2547   DM             dm;
2548   DMSNES         sdm;
2549 
2550   PetscFunctionBegin;
2551   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2552   PetscValidHeaderSpecific(x,VEC_CLASSID,3);
2553   if (b) PetscValidHeaderSpecific(b,VEC_CLASSID,2);
2554   PetscCheckSameComm(snes,1,x,3);
2555   if (b) PetscCheckSameComm(snes,1,b,2);
2556   if (b) PetscCall(VecValidValues(b,2,PETSC_TRUE));
2557   PetscCall(PetscLogEventBegin(SNES_NGSEval,snes,x,b,0));
2558   PetscCall(SNESGetDM(snes,&dm));
2559   PetscCall(DMGetDMSNES(dm,&sdm));
2560   if (sdm->ops->computegs) {
2561     if (b) PetscCall(VecLockReadPush(b));
2562     PetscStackPush("SNES user NGS");
2563     PetscCall((*sdm->ops->computegs)(snes,x,b,sdm->gsctx));
2564     PetscStackPop;
2565     if (b) PetscCall(VecLockReadPop(b));
2566   } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetNGS() before SNESComputeNGS(), likely called from SNESSolve().");
2567   PetscCall(PetscLogEventEnd(SNES_NGSEval,snes,x,b,0));
2568   PetscFunctionReturn(0);
2569 }
2570 
2571 PetscErrorCode SNESTestJacobian(SNES snes)
2572 {
2573   Mat               A,B,C,D,jacobian;
2574   Vec               x = snes->vec_sol,f = snes->vec_func;
2575   PetscReal         nrm,gnorm;
2576   PetscReal         threshold = 1.e-5;
2577   MatType           mattype;
2578   PetscInt          m,n,M,N;
2579   void              *functx;
2580   PetscBool         complete_print = PETSC_FALSE,threshold_print = PETSC_FALSE,test = PETSC_FALSE,flg,istranspose;
2581   PetscViewer       viewer,mviewer;
2582   MPI_Comm          comm;
2583   PetscInt          tabs;
2584   static PetscBool  directionsprinted = PETSC_FALSE;
2585   PetscViewerFormat format;
2586 
2587   PetscFunctionBegin;
2588   PetscObjectOptionsBegin((PetscObject)snes);
2589   PetscCall(PetscOptionsName("-snes_test_jacobian","Compare hand-coded and finite difference Jacobians","None",&test));
2590   PetscCall(PetscOptionsReal("-snes_test_jacobian", "Threshold for element difference between hand-coded and finite difference being meaningful", "None", threshold, &threshold,NULL));
2591   PetscCall(PetscOptionsViewer("-snes_test_jacobian_view","View difference between hand-coded and finite difference Jacobians element entries","None",&mviewer,&format,&complete_print));
2592   if (!complete_print) {
2593     PetscCall(PetscOptionsDeprecated("-snes_test_jacobian_display","-snes_test_jacobian_view","3.13",NULL));
2594     PetscCall(PetscOptionsViewer("-snes_test_jacobian_display","Display difference between hand-coded and finite difference Jacobians","None",&mviewer,&format,&complete_print));
2595   }
2596   /* for compatibility with PETSc 3.9 and older. */
2597   PetscCall(PetscOptionsDeprecated("-snes_test_jacobian_display_threshold","-snes_test_jacobian","3.13","-snes_test_jacobian accepts an optional threshold (since v3.10)"));
2598   PetscCall(PetscOptionsReal("-snes_test_jacobian_display_threshold", "Display difference between hand-coded and finite difference Jacobians which exceed input threshold", "None", threshold, &threshold, &threshold_print));
2599   PetscOptionsEnd();
2600   if (!test) PetscFunctionReturn(0);
2601 
2602   PetscCall(PetscObjectGetComm((PetscObject)snes,&comm));
2603   PetscCall(PetscViewerASCIIGetStdout(comm,&viewer));
2604   PetscCall(PetscViewerASCIIGetTab(viewer, &tabs));
2605   PetscCall(PetscViewerASCIISetTab(viewer, ((PetscObject)snes)->tablevel));
2606   PetscCall(PetscViewerASCIIPrintf(viewer,"  ---------- Testing Jacobian -------------\n"));
2607   if (!complete_print && !directionsprinted) {
2608     PetscCall(PetscViewerASCIIPrintf(viewer,"  Run with -snes_test_jacobian_view and optionally -snes_test_jacobian <threshold> to show difference\n"));
2609     PetscCall(PetscViewerASCIIPrintf(viewer,"    of hand-coded and finite difference Jacobian entries greater than <threshold>.\n"));
2610   }
2611   if (!directionsprinted) {
2612     PetscCall(PetscViewerASCIIPrintf(viewer,"  Testing hand-coded Jacobian, if (for double precision runs) ||J - Jfd||_F/||J||_F is\n"));
2613     PetscCall(PetscViewerASCIIPrintf(viewer,"    O(1.e-8), the hand-coded Jacobian is probably correct.\n"));
2614     directionsprinted = PETSC_TRUE;
2615   }
2616   if (complete_print) {
2617     PetscCall(PetscViewerPushFormat(mviewer,format));
2618   }
2619 
2620   PetscCall(PetscObjectTypeCompare((PetscObject)snes->jacobian,MATMFFD,&flg));
2621   if (!flg) jacobian = snes->jacobian;
2622   else jacobian = snes->jacobian_pre;
2623 
2624   if (!x) {
2625     PetscCall(MatCreateVecs(jacobian, &x, NULL));
2626   } else {
2627     PetscCall(PetscObjectReference((PetscObject) x));
2628   }
2629   if (!f) {
2630     PetscCall(VecDuplicate(x, &f));
2631   } else {
2632     PetscCall(PetscObjectReference((PetscObject) f));
2633   }
2634   /* evaluate the function at this point because SNESComputeJacobianDefault() assumes that the function has been evaluated and put into snes->vec_func */
2635   PetscCall(SNESComputeFunction(snes,x,f));
2636   PetscCall(VecDestroy(&f));
2637   PetscCall(PetscObjectTypeCompare((PetscObject)snes,SNESKSPTRANSPOSEONLY,&istranspose));
2638   while (jacobian) {
2639     Mat JT = NULL, Jsave = NULL;
2640 
2641     if (istranspose) {
2642       PetscCall(MatCreateTranspose(jacobian,&JT));
2643       Jsave = jacobian;
2644       jacobian = JT;
2645     }
2646     PetscCall(PetscObjectBaseTypeCompareAny((PetscObject)jacobian,&flg,MATSEQAIJ,MATMPIAIJ,MATSEQDENSE,MATMPIDENSE,MATSEQBAIJ,MATMPIBAIJ,MATSEQSBAIJ,MATMPISBAIJ,""));
2647     if (flg) {
2648       A    = jacobian;
2649       PetscCall(PetscObjectReference((PetscObject)A));
2650     } else {
2651       PetscCall(MatComputeOperator(jacobian,MATAIJ,&A));
2652     }
2653 
2654     PetscCall(MatGetType(A,&mattype));
2655     PetscCall(MatGetSize(A,&M,&N));
2656     PetscCall(MatGetLocalSize(A,&m,&n));
2657     PetscCall(MatCreate(PetscObjectComm((PetscObject)A),&B));
2658     PetscCall(MatSetType(B,mattype));
2659     PetscCall(MatSetSizes(B,m,n,M,N));
2660     PetscCall(MatSetBlockSizesFromMats(B,A,A));
2661     PetscCall(MatSetUp(B));
2662     PetscCall(MatSetOption(B,MAT_NEW_NONZERO_ALLOCATION_ERR,PETSC_FALSE));
2663 
2664     PetscCall(SNESGetFunction(snes,NULL,NULL,&functx));
2665     PetscCall(SNESComputeJacobianDefault(snes,x,B,B,functx));
2666 
2667     PetscCall(MatDuplicate(B,MAT_COPY_VALUES,&D));
2668     PetscCall(MatAYPX(D,-1.0,A,DIFFERENT_NONZERO_PATTERN));
2669     PetscCall(MatNorm(D,NORM_FROBENIUS,&nrm));
2670     PetscCall(MatNorm(A,NORM_FROBENIUS,&gnorm));
2671     PetscCall(MatDestroy(&D));
2672     if (!gnorm) gnorm = 1; /* just in case */
2673     PetscCall(PetscViewerASCIIPrintf(viewer,"  ||J - Jfd||_F/||J||_F = %g, ||J - Jfd||_F = %g\n",(double)(nrm/gnorm),(double)nrm));
2674 
2675     if (complete_print) {
2676       PetscCall(PetscViewerASCIIPrintf(viewer,"  Hand-coded Jacobian ----------\n"));
2677       PetscCall(MatView(A,mviewer));
2678       PetscCall(PetscViewerASCIIPrintf(viewer,"  Finite difference Jacobian ----------\n"));
2679       PetscCall(MatView(B,mviewer));
2680     }
2681 
2682     if (threshold_print || complete_print) {
2683       PetscInt          Istart, Iend, *ccols, bncols, cncols, j, row;
2684       PetscScalar       *cvals;
2685       const PetscInt    *bcols;
2686       const PetscScalar *bvals;
2687 
2688       PetscCall(MatCreate(PetscObjectComm((PetscObject)A),&C));
2689       PetscCall(MatSetType(C,mattype));
2690       PetscCall(MatSetSizes(C,m,n,M,N));
2691       PetscCall(MatSetBlockSizesFromMats(C,A,A));
2692       PetscCall(MatSetUp(C));
2693       PetscCall(MatSetOption(C,MAT_NEW_NONZERO_ALLOCATION_ERR,PETSC_FALSE));
2694 
2695       PetscCall(MatAYPX(B,-1.0,A,DIFFERENT_NONZERO_PATTERN));
2696       PetscCall(MatGetOwnershipRange(B,&Istart,&Iend));
2697 
2698       for (row = Istart; row < Iend; row++) {
2699         PetscCall(MatGetRow(B,row,&bncols,&bcols,&bvals));
2700         PetscCall(PetscMalloc2(bncols,&ccols,bncols,&cvals));
2701         for (j = 0, cncols = 0; j < bncols; j++) {
2702           if (PetscAbsScalar(bvals[j]) > threshold) {
2703             ccols[cncols] = bcols[j];
2704             cvals[cncols] = bvals[j];
2705             cncols += 1;
2706           }
2707         }
2708         if (cncols) {
2709           PetscCall(MatSetValues(C,1,&row,cncols,ccols,cvals,INSERT_VALUES));
2710         }
2711         PetscCall(MatRestoreRow(B,row,&bncols,&bcols,&bvals));
2712         PetscCall(PetscFree2(ccols,cvals));
2713       }
2714       PetscCall(MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY));
2715       PetscCall(MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY));
2716       PetscCall(PetscViewerASCIIPrintf(viewer,"  Hand-coded minus finite-difference Jacobian with tolerance %g ----------\n",(double)threshold));
2717       PetscCall(MatView(C,complete_print ? mviewer : viewer));
2718       PetscCall(MatDestroy(&C));
2719     }
2720     PetscCall(MatDestroy(&A));
2721     PetscCall(MatDestroy(&B));
2722     PetscCall(MatDestroy(&JT));
2723     if (Jsave) jacobian = Jsave;
2724     if (jacobian != snes->jacobian_pre) {
2725       jacobian = snes->jacobian_pre;
2726       PetscCall(PetscViewerASCIIPrintf(viewer,"  ---------- Testing Jacobian for preconditioner -------------\n"));
2727     }
2728     else jacobian = NULL;
2729   }
2730   PetscCall(VecDestroy(&x));
2731   if (complete_print) {
2732     PetscCall(PetscViewerPopFormat(mviewer));
2733   }
2734   if (mviewer) PetscCall(PetscViewerDestroy(&mviewer));
2735   PetscCall(PetscViewerASCIISetTab(viewer,tabs));
2736   PetscFunctionReturn(0);
2737 }
2738 
2739 /*@
2740    SNESComputeJacobian - Computes the Jacobian matrix that has been set with SNESSetJacobian().
2741 
2742    Collective on SNES
2743 
2744    Input Parameters:
2745 +  snes - the SNES context
2746 -  x - input vector
2747 
2748    Output Parameters:
2749 +  A - Jacobian matrix
2750 -  B - optional preconditioning matrix
2751 
2752   Options Database Keys:
2753 +    -snes_lag_preconditioner <lag> - how often to rebuild preconditioner
2754 .    -snes_lag_jacobian <lag> - how often to rebuild Jacobian
2755 .    -snes_test_jacobian <optional threshold> - compare the user provided Jacobian with one compute via finite differences to check for errors.  If a threshold is given, display only those entries whose difference is greater than the threshold.
2756 .    -snes_test_jacobian_view - display the user provided Jacobian, the finite difference Jacobian and the difference between them to help users detect the location of errors in the user provided Jacobian
2757 .    -snes_compare_explicit - Compare the computed Jacobian to the finite difference Jacobian and output the differences
2758 .    -snes_compare_explicit_draw  - Compare the computed Jacobian to the finite difference Jacobian and draw the result
2759 .    -snes_compare_explicit_contour  - Compare the computed Jacobian to the finite difference Jacobian and draw a contour plot with the result
2760 .    -snes_compare_operator  - Make the comparison options above use the operator instead of the preconditioning matrix
2761 .    -snes_compare_coloring - Compute the finite difference Jacobian using coloring and display norms of difference
2762 .    -snes_compare_coloring_display - Compute the finite difference Jacobian using coloring and display verbose differences
2763 .    -snes_compare_coloring_threshold - Display only those matrix entries that differ by more than a given threshold
2764 .    -snes_compare_coloring_threshold_atol - Absolute tolerance for difference in matrix entries to be displayed by -snes_compare_coloring_threshold
2765 .    -snes_compare_coloring_threshold_rtol - Relative tolerance for difference in matrix entries to be displayed by -snes_compare_coloring_threshold
2766 .    -snes_compare_coloring_draw - Compute the finite difference Jacobian using coloring and draw differences
2767 -    -snes_compare_coloring_draw_contour - Compute the finite difference Jacobian using coloring and show contours of matrices and differences
2768 
2769    Notes:
2770    Most users should not need to explicitly call this routine, as it
2771    is used internally within the nonlinear solvers.
2772 
2773    Developer Notes:
2774     This has duplicative ways of checking the accuracy of the user provided Jacobian (see the options above). This is for historical reasons, the routine SNESTestJacobian() use to used
2775       for with the SNESType of test that has been removed.
2776 
2777    Level: developer
2778 
2779 .seealso: `SNESSetJacobian()`, `KSPSetOperators()`, `MatStructure`, `SNESSetLagPreconditioner()`, `SNESSetLagJacobian()`
2780 @*/
2781 PetscErrorCode  SNESComputeJacobian(SNES snes,Vec X,Mat A,Mat B)
2782 {
2783   PetscBool      flag;
2784   DM             dm;
2785   DMSNES         sdm;
2786   KSP            ksp;
2787 
2788   PetscFunctionBegin;
2789   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
2790   PetscValidHeaderSpecific(X,VEC_CLASSID,2);
2791   PetscCheckSameComm(snes,1,X,2);
2792   PetscCall(VecValidValues(X,2,PETSC_TRUE));
2793   PetscCall(SNESGetDM(snes,&dm));
2794   PetscCall(DMGetDMSNES(dm,&sdm));
2795 
2796   PetscCheck(sdm->ops->computejacobian,PetscObjectComm((PetscObject)snes),PETSC_ERR_USER,"Must call SNESSetJacobian(), DMSNESSetJacobian(), DMDASNESSetJacobianLocal(), etc");
2797 
2798   /* make sure that MatAssemblyBegin/End() is called on A matrix if it is matrix free */
2799 
2800   if (snes->lagjacobian == -2) {
2801     snes->lagjacobian = -1;
2802 
2803     PetscCall(PetscInfo(snes,"Recomputing Jacobian/preconditioner because lag is -2 (means compute Jacobian, but then never again) \n"));
2804   } else if (snes->lagjacobian == -1) {
2805     PetscCall(PetscInfo(snes,"Reusing Jacobian/preconditioner because lag is -1\n"));
2806     PetscCall(PetscObjectTypeCompare((PetscObject)A,MATMFFD,&flag));
2807     if (flag) {
2808       PetscCall(MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY));
2809       PetscCall(MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY));
2810     }
2811     PetscFunctionReturn(0);
2812   } else if (snes->lagjacobian > 1 && (snes->iter + snes->jac_iter) % snes->lagjacobian) {
2813     PetscCall(PetscInfo(snes,"Reusing Jacobian/preconditioner because lag is %" PetscInt_FMT " and SNES iteration is %" PetscInt_FMT "\n",snes->lagjacobian,snes->iter));
2814     PetscCall(PetscObjectTypeCompare((PetscObject)A,MATMFFD,&flag));
2815     if (flag) {
2816       PetscCall(MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY));
2817       PetscCall(MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY));
2818     }
2819     PetscFunctionReturn(0);
2820   }
2821   if (snes->npc && snes->npcside == PC_LEFT) {
2822     PetscCall(MatAssemblyBegin(A,MAT_FINAL_ASSEMBLY));
2823     PetscCall(MatAssemblyEnd(A,MAT_FINAL_ASSEMBLY));
2824     PetscFunctionReturn(0);
2825   }
2826 
2827   PetscCall(PetscLogEventBegin(SNES_JacobianEval,snes,X,A,B));
2828   PetscCall(VecLockReadPush(X));
2829   PetscStackPush("SNES user Jacobian function");
2830   PetscCall((*sdm->ops->computejacobian)(snes,X,A,B,sdm->jacobianctx));
2831   PetscStackPop;
2832   PetscCall(VecLockReadPop(X));
2833   PetscCall(PetscLogEventEnd(SNES_JacobianEval,snes,X,A,B));
2834 
2835   /* attach latest linearization point to the preconditioning matrix */
2836   PetscCall(PetscObjectCompose((PetscObject)B,"__SNES_latest_X",(PetscObject)X));
2837 
2838   /* the next line ensures that snes->ksp exists */
2839   PetscCall(SNESGetKSP(snes,&ksp));
2840   if (snes->lagpreconditioner == -2) {
2841     PetscCall(PetscInfo(snes,"Rebuilding preconditioner exactly once since lag is -2\n"));
2842     PetscCall(KSPSetReusePreconditioner(snes->ksp,PETSC_FALSE));
2843     snes->lagpreconditioner = -1;
2844   } else if (snes->lagpreconditioner == -1) {
2845     PetscCall(PetscInfo(snes,"Reusing preconditioner because lag is -1\n"));
2846     PetscCall(KSPSetReusePreconditioner(snes->ksp,PETSC_TRUE));
2847   } else if (snes->lagpreconditioner > 1 && (snes->iter + snes->pre_iter) % snes->lagpreconditioner) {
2848     PetscCall(PetscInfo(snes,"Reusing preconditioner because lag is %" PetscInt_FMT " and SNES iteration is %" PetscInt_FMT "\n",snes->lagpreconditioner,snes->iter));
2849     PetscCall(KSPSetReusePreconditioner(snes->ksp,PETSC_TRUE));
2850   } else {
2851     PetscCall(PetscInfo(snes,"Rebuilding preconditioner\n"));
2852     PetscCall(KSPSetReusePreconditioner(snes->ksp,PETSC_FALSE));
2853   }
2854 
2855   PetscCall(SNESTestJacobian(snes));
2856   /* make sure user returned a correct Jacobian and preconditioner */
2857   /* PetscValidHeaderSpecific(A,MAT_CLASSID,3);
2858     PetscValidHeaderSpecific(B,MAT_CLASSID,4);   */
2859   {
2860     PetscBool flag = PETSC_FALSE,flag_draw = PETSC_FALSE,flag_contour = PETSC_FALSE,flag_operator = PETSC_FALSE;
2861     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject) snes)->options,((PetscObject)snes)->prefix,"-snes_compare_explicit",NULL,NULL,&flag));
2862     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject) snes)->options,((PetscObject)snes)->prefix,"-snes_compare_explicit_draw",NULL,NULL,&flag_draw));
2863     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject) snes)->options,((PetscObject)snes)->prefix,"-snes_compare_explicit_draw_contour",NULL,NULL,&flag_contour));
2864     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject) snes)->options,((PetscObject)snes)->prefix,"-snes_compare_operator",NULL,NULL,&flag_operator));
2865     if (flag || flag_draw || flag_contour) {
2866       Mat          Bexp_mine = NULL,Bexp,FDexp;
2867       PetscViewer  vdraw,vstdout;
2868       PetscBool    flg;
2869       if (flag_operator) {
2870         PetscCall(MatComputeOperator(A,MATAIJ,&Bexp_mine));
2871         Bexp = Bexp_mine;
2872       } else {
2873         /* See if the preconditioning matrix can be viewed and added directly */
2874         PetscCall(PetscObjectBaseTypeCompareAny((PetscObject)B,&flg,MATSEQAIJ,MATMPIAIJ,MATSEQDENSE,MATMPIDENSE,MATSEQBAIJ,MATMPIBAIJ,MATSEQSBAIJ,MATMPIBAIJ,""));
2875         if (flg) Bexp = B;
2876         else {
2877           /* If the "preconditioning" matrix is itself MATSHELL or some other type without direct support */
2878           PetscCall(MatComputeOperator(B,MATAIJ,&Bexp_mine));
2879           Bexp = Bexp_mine;
2880         }
2881       }
2882       PetscCall(MatConvert(Bexp,MATSAME,MAT_INITIAL_MATRIX,&FDexp));
2883       PetscCall(SNESComputeJacobianDefault(snes,X,FDexp,FDexp,NULL));
2884       PetscCall(PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)snes),&vstdout));
2885       if (flag_draw || flag_contour) {
2886         PetscCall(PetscViewerDrawOpen(PetscObjectComm((PetscObject)snes),NULL,"Explicit Jacobians",PETSC_DECIDE,PETSC_DECIDE,300,300,&vdraw));
2887         if (flag_contour) PetscCall(PetscViewerPushFormat(vdraw,PETSC_VIEWER_DRAW_CONTOUR));
2888       } else vdraw = NULL;
2889       PetscCall(PetscViewerASCIIPrintf(vstdout,"Explicit %s\n",flag_operator ? "Jacobian" : "preconditioning Jacobian"));
2890       if (flag) PetscCall(MatView(Bexp,vstdout));
2891       if (vdraw) PetscCall(MatView(Bexp,vdraw));
2892       PetscCall(PetscViewerASCIIPrintf(vstdout,"Finite difference Jacobian\n"));
2893       if (flag) PetscCall(MatView(FDexp,vstdout));
2894       if (vdraw) PetscCall(MatView(FDexp,vdraw));
2895       PetscCall(MatAYPX(FDexp,-1.0,Bexp,SAME_NONZERO_PATTERN));
2896       PetscCall(PetscViewerASCIIPrintf(vstdout,"User-provided matrix minus finite difference Jacobian\n"));
2897       if (flag) PetscCall(MatView(FDexp,vstdout));
2898       if (vdraw) {              /* Always use contour for the difference */
2899         PetscCall(PetscViewerPushFormat(vdraw,PETSC_VIEWER_DRAW_CONTOUR));
2900         PetscCall(MatView(FDexp,vdraw));
2901         PetscCall(PetscViewerPopFormat(vdraw));
2902       }
2903       if (flag_contour) PetscCall(PetscViewerPopFormat(vdraw));
2904       PetscCall(PetscViewerDestroy(&vdraw));
2905       PetscCall(MatDestroy(&Bexp_mine));
2906       PetscCall(MatDestroy(&FDexp));
2907     }
2908   }
2909   {
2910     PetscBool flag = PETSC_FALSE,flag_display = PETSC_FALSE,flag_draw = PETSC_FALSE,flag_contour = PETSC_FALSE,flag_threshold = PETSC_FALSE;
2911     PetscReal threshold_atol = PETSC_SQRT_MACHINE_EPSILON,threshold_rtol = 10*PETSC_SQRT_MACHINE_EPSILON;
2912     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring",NULL,NULL,&flag));
2913     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_display",NULL,NULL,&flag_display));
2914     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_draw",NULL,NULL,&flag_draw));
2915     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_draw_contour",NULL,NULL,&flag_contour));
2916     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_threshold",NULL,NULL,&flag_threshold));
2917     if (flag_threshold) {
2918       PetscCall(PetscOptionsGetReal(((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_threshold_rtol",&threshold_rtol,NULL));
2919       PetscCall(PetscOptionsGetReal(((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_compare_coloring_threshold_atol",&threshold_atol,NULL));
2920     }
2921     if (flag || flag_display || flag_draw || flag_contour || flag_threshold) {
2922       Mat            Bfd;
2923       PetscViewer    vdraw,vstdout;
2924       MatColoring    coloring;
2925       ISColoring     iscoloring;
2926       MatFDColoring  matfdcoloring;
2927       PetscErrorCode (*func)(SNES,Vec,Vec,void*);
2928       void           *funcctx;
2929       PetscReal      norm1,norm2,normmax;
2930 
2931       PetscCall(MatDuplicate(B,MAT_DO_NOT_COPY_VALUES,&Bfd));
2932       PetscCall(MatColoringCreate(Bfd,&coloring));
2933       PetscCall(MatColoringSetType(coloring,MATCOLORINGSL));
2934       PetscCall(MatColoringSetFromOptions(coloring));
2935       PetscCall(MatColoringApply(coloring,&iscoloring));
2936       PetscCall(MatColoringDestroy(&coloring));
2937       PetscCall(MatFDColoringCreate(Bfd,iscoloring,&matfdcoloring));
2938       PetscCall(MatFDColoringSetFromOptions(matfdcoloring));
2939       PetscCall(MatFDColoringSetUp(Bfd,iscoloring,matfdcoloring));
2940       PetscCall(ISColoringDestroy(&iscoloring));
2941 
2942       /* This method of getting the function is currently unreliable since it doesn't work for DM local functions. */
2943       PetscCall(SNESGetFunction(snes,NULL,&func,&funcctx));
2944       PetscCall(MatFDColoringSetFunction(matfdcoloring,(PetscErrorCode (*)(void))func,funcctx));
2945       PetscCall(PetscObjectSetOptionsPrefix((PetscObject)matfdcoloring,((PetscObject)snes)->prefix));
2946       PetscCall(PetscObjectAppendOptionsPrefix((PetscObject)matfdcoloring,"coloring_"));
2947       PetscCall(MatFDColoringSetFromOptions(matfdcoloring));
2948       PetscCall(MatFDColoringApply(Bfd,matfdcoloring,X,snes));
2949       PetscCall(MatFDColoringDestroy(&matfdcoloring));
2950 
2951       PetscCall(PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)snes),&vstdout));
2952       if (flag_draw || flag_contour) {
2953         PetscCall(PetscViewerDrawOpen(PetscObjectComm((PetscObject)snes),NULL,"Colored Jacobians",PETSC_DECIDE,PETSC_DECIDE,300,300,&vdraw));
2954         if (flag_contour) PetscCall(PetscViewerPushFormat(vdraw,PETSC_VIEWER_DRAW_CONTOUR));
2955       } else vdraw = NULL;
2956       PetscCall(PetscViewerASCIIPrintf(vstdout,"Explicit preconditioning Jacobian\n"));
2957       if (flag_display) PetscCall(MatView(B,vstdout));
2958       if (vdraw) PetscCall(MatView(B,vdraw));
2959       PetscCall(PetscViewerASCIIPrintf(vstdout,"Colored Finite difference Jacobian\n"));
2960       if (flag_display) PetscCall(MatView(Bfd,vstdout));
2961       if (vdraw) PetscCall(MatView(Bfd,vdraw));
2962       PetscCall(MatAYPX(Bfd,-1.0,B,SAME_NONZERO_PATTERN));
2963       PetscCall(MatNorm(Bfd,NORM_1,&norm1));
2964       PetscCall(MatNorm(Bfd,NORM_FROBENIUS,&norm2));
2965       PetscCall(MatNorm(Bfd,NORM_MAX,&normmax));
2966       PetscCall(PetscViewerASCIIPrintf(vstdout,"User-provided matrix minus finite difference Jacobian, norm1=%g normFrob=%g normmax=%g\n",(double)norm1,(double)norm2,(double)normmax));
2967       if (flag_display) PetscCall(MatView(Bfd,vstdout));
2968       if (vdraw) {              /* Always use contour for the difference */
2969         PetscCall(PetscViewerPushFormat(vdraw,PETSC_VIEWER_DRAW_CONTOUR));
2970         PetscCall(MatView(Bfd,vdraw));
2971         PetscCall(PetscViewerPopFormat(vdraw));
2972       }
2973       if (flag_contour) PetscCall(PetscViewerPopFormat(vdraw));
2974 
2975       if (flag_threshold) {
2976         PetscInt bs,rstart,rend,i;
2977         PetscCall(MatGetBlockSize(B,&bs));
2978         PetscCall(MatGetOwnershipRange(B,&rstart,&rend));
2979         for (i=rstart; i<rend; i++) {
2980           const PetscScalar *ba,*ca;
2981           const PetscInt    *bj,*cj;
2982           PetscInt          bn,cn,j,maxentrycol = -1,maxdiffcol = -1,maxrdiffcol = -1;
2983           PetscReal         maxentry = 0,maxdiff = 0,maxrdiff = 0;
2984           PetscCall(MatGetRow(B,i,&bn,&bj,&ba));
2985           PetscCall(MatGetRow(Bfd,i,&cn,&cj,&ca));
2986           PetscCheck(bn == cn,((PetscObject)A)->comm,PETSC_ERR_PLIB,"Unexpected different nonzero pattern in -snes_compare_coloring_threshold");
2987           for (j=0; j<bn; j++) {
2988             PetscReal rdiff = PetscAbsScalar(ca[j]) / (threshold_atol + threshold_rtol*PetscAbsScalar(ba[j]));
2989             if (PetscAbsScalar(ba[j]) > PetscAbs(maxentry)) {
2990               maxentrycol = bj[j];
2991               maxentry    = PetscRealPart(ba[j]);
2992             }
2993             if (PetscAbsScalar(ca[j]) > PetscAbs(maxdiff)) {
2994               maxdiffcol = bj[j];
2995               maxdiff    = PetscRealPart(ca[j]);
2996             }
2997             if (rdiff > maxrdiff) {
2998               maxrdiffcol = bj[j];
2999               maxrdiff    = rdiff;
3000             }
3001           }
3002           if (maxrdiff > 1) {
3003             PetscCall(PetscViewerASCIIPrintf(vstdout,"row %" PetscInt_FMT " (maxentry=%g at %" PetscInt_FMT ", maxdiff=%g at %" PetscInt_FMT ", maxrdiff=%g at %" PetscInt_FMT "):",i,(double)maxentry,maxentrycol,(double)maxdiff,maxdiffcol,(double)maxrdiff,maxrdiffcol));
3004             for (j=0; j<bn; j++) {
3005               PetscReal rdiff;
3006               rdiff = PetscAbsScalar(ca[j]) / (threshold_atol + threshold_rtol*PetscAbsScalar(ba[j]));
3007               if (rdiff > 1) {
3008                 PetscCall(PetscViewerASCIIPrintf(vstdout," (%" PetscInt_FMT ",%g:%g)",bj[j],(double)PetscRealPart(ba[j]),(double)PetscRealPart(ca[j])));
3009               }
3010             }
3011             PetscCall(PetscViewerASCIIPrintf(vstdout,"\n"));
3012           }
3013           PetscCall(MatRestoreRow(B,i,&bn,&bj,&ba));
3014           PetscCall(MatRestoreRow(Bfd,i,&cn,&cj,&ca));
3015         }
3016       }
3017       PetscCall(PetscViewerDestroy(&vdraw));
3018       PetscCall(MatDestroy(&Bfd));
3019     }
3020   }
3021   PetscFunctionReturn(0);
3022 }
3023 
3024 /*MC
3025     SNESJacobianFunction - Function used to convey the nonlinear Jacobian of the function to be solved by SNES
3026 
3027      Synopsis:
3028      #include "petscsnes.h"
3029      PetscErrorCode SNESJacobianFunction(SNES snes,Vec x,Mat Amat,Mat Pmat,void *ctx);
3030 
3031      Collective on snes
3032 
3033     Input Parameters:
3034 +  x - input vector, the Jacobian is to be computed at this value
3035 -  ctx - [optional] user-defined Jacobian context
3036 
3037     Output Parameters:
3038 +  Amat - the matrix that defines the (approximate) Jacobian
3039 -  Pmat - the matrix to be used in constructing the preconditioner, usually the same as Amat.
3040 
3041    Level: intermediate
3042 
3043 .seealso: `SNESSetFunction()`, `SNESGetFunction()`, `SNESSetJacobian()`, `SNESGetJacobian()`
3044 M*/
3045 
3046 /*@C
3047    SNESSetJacobian - Sets the function to compute Jacobian as well as the
3048    location to store the matrix.
3049 
3050    Logically Collective on SNES
3051 
3052    Input Parameters:
3053 +  snes - the SNES context
3054 .  Amat - the matrix that defines the (approximate) Jacobian
3055 .  Pmat - the matrix to be used in constructing the preconditioner, usually the same as Amat.
3056 .  J - Jacobian evaluation routine (if NULL then SNES retains any previously set value), see SNESJacobianFunction for details
3057 -  ctx - [optional] user-defined context for private data for the
3058          Jacobian evaluation routine (may be NULL) (if NULL then SNES retains any previously set value)
3059 
3060    Notes:
3061    If the Amat matrix and Pmat matrix are different you must call MatAssemblyBegin/End() on
3062    each matrix.
3063 
3064    If you know the operator Amat has a null space you can use MatSetNullSpace() and MatSetTransposeNullSpace() to supply the null
3065    space to Amat and the KSP solvers will automatically use that null space as needed during the solution process.
3066 
3067    If using SNESComputeJacobianDefaultColor() to assemble a Jacobian, the ctx argument
3068    must be a MatFDColoring.
3069 
3070    Other defect-correction schemes can be used by computing a different matrix in place of the Jacobian.  One common
3071    example is to use the "Picard linearization" which only differentiates through the highest order parts of each term.
3072 
3073    Level: beginner
3074 
3075 .seealso: `KSPSetOperators()`, `SNESSetFunction()`, `MatMFFDComputeJacobian()`, `SNESComputeJacobianDefaultColor()`, `MatStructure`, `J`,
3076           `SNESSetPicard()`, `SNESJacobianFunction`
3077 @*/
3078 PetscErrorCode  SNESSetJacobian(SNES snes,Mat Amat,Mat Pmat,PetscErrorCode (*J)(SNES,Vec,Mat,Mat,void*),void *ctx)
3079 {
3080   DM             dm;
3081 
3082   PetscFunctionBegin;
3083   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3084   if (Amat) PetscValidHeaderSpecific(Amat,MAT_CLASSID,2);
3085   if (Pmat) PetscValidHeaderSpecific(Pmat,MAT_CLASSID,3);
3086   if (Amat) PetscCheckSameComm(snes,1,Amat,2);
3087   if (Pmat) PetscCheckSameComm(snes,1,Pmat,3);
3088   PetscCall(SNESGetDM(snes,&dm));
3089   PetscCall(DMSNESSetJacobian(dm,J,ctx));
3090   if (Amat) {
3091     PetscCall(PetscObjectReference((PetscObject)Amat));
3092     PetscCall(MatDestroy(&snes->jacobian));
3093 
3094     snes->jacobian = Amat;
3095   }
3096   if (Pmat) {
3097     PetscCall(PetscObjectReference((PetscObject)Pmat));
3098     PetscCall(MatDestroy(&snes->jacobian_pre));
3099 
3100     snes->jacobian_pre = Pmat;
3101   }
3102   PetscFunctionReturn(0);
3103 }
3104 
3105 /*@C
3106    SNESGetJacobian - Returns the Jacobian matrix and optionally the user
3107    provided context for evaluating the Jacobian.
3108 
3109    Not Collective, but Mat object will be parallel if SNES object is
3110 
3111    Input Parameter:
3112 .  snes - the nonlinear solver context
3113 
3114    Output Parameters:
3115 +  Amat - location to stash (approximate) Jacobian matrix (or NULL)
3116 .  Pmat - location to stash matrix used to compute the preconditioner (or NULL)
3117 .  J - location to put Jacobian function (or NULL), see SNESJacobianFunction for details on its calling sequence
3118 -  ctx - location to stash Jacobian ctx (or NULL)
3119 
3120    Level: advanced
3121 
3122 .seealso: `SNESSetJacobian()`, `SNESComputeJacobian()`, `SNESJacobianFunction`, `SNESGetFunction()`
3123 @*/
3124 PetscErrorCode SNESGetJacobian(SNES snes,Mat *Amat,Mat *Pmat,PetscErrorCode (**J)(SNES,Vec,Mat,Mat,void*),void **ctx)
3125 {
3126   DM             dm;
3127   DMSNES         sdm;
3128 
3129   PetscFunctionBegin;
3130   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3131   if (Amat) *Amat = snes->jacobian;
3132   if (Pmat) *Pmat = snes->jacobian_pre;
3133   PetscCall(SNESGetDM(snes,&dm));
3134   PetscCall(DMGetDMSNES(dm,&sdm));
3135   if (J) *J = sdm->ops->computejacobian;
3136   if (ctx) *ctx = sdm->jacobianctx;
3137   PetscFunctionReturn(0);
3138 }
3139 
3140 static PetscErrorCode SNESSetDefaultComputeJacobian(SNES snes)
3141 {
3142   DM             dm;
3143   DMSNES         sdm;
3144 
3145   PetscFunctionBegin;
3146   PetscCall(SNESGetDM(snes,&dm));
3147   PetscCall(DMGetDMSNES(dm,&sdm));
3148   if (!sdm->ops->computejacobian && snes->jacobian_pre) {
3149     DM        dm;
3150     PetscBool isdense,ismf;
3151 
3152     PetscCall(SNESGetDM(snes,&dm));
3153     PetscCall(PetscObjectTypeCompareAny((PetscObject)snes->jacobian_pre,&isdense,MATSEQDENSE,MATMPIDENSE,MATDENSE,NULL));
3154     PetscCall(PetscObjectTypeCompareAny((PetscObject)snes->jacobian_pre,&ismf,MATMFFD,MATSHELL,NULL));
3155     if (isdense) {
3156       PetscCall(DMSNESSetJacobian(dm,SNESComputeJacobianDefault,NULL));
3157     } else if (!ismf) {
3158       PetscCall(DMSNESSetJacobian(dm,SNESComputeJacobianDefaultColor,NULL));
3159     }
3160   }
3161   PetscFunctionReturn(0);
3162 }
3163 
3164 /*@
3165    SNESSetUp - Sets up the internal data structures for the later use
3166    of a nonlinear solver.
3167 
3168    Collective on SNES
3169 
3170    Input Parameters:
3171 .  snes - the SNES context
3172 
3173    Notes:
3174    For basic use of the SNES solvers the user need not explicitly call
3175    SNESSetUp(), since these actions will automatically occur during
3176    the call to SNESSolve().  However, if one wishes to control this
3177    phase separately, SNESSetUp() should be called after SNESCreate()
3178    and optional routines of the form SNESSetXXX(), but before SNESSolve().
3179 
3180    Level: advanced
3181 
3182 .seealso: `SNESCreate()`, `SNESSolve()`, `SNESDestroy()`
3183 @*/
3184 PetscErrorCode  SNESSetUp(SNES snes)
3185 {
3186   DM             dm;
3187   DMSNES         sdm;
3188   SNESLineSearch linesearch, pclinesearch;
3189   void           *lsprectx,*lspostctx;
3190   PetscErrorCode (*precheck)(SNESLineSearch,Vec,Vec,PetscBool*,void*);
3191   PetscErrorCode (*postcheck)(SNESLineSearch,Vec,Vec,Vec,PetscBool*,PetscBool*,void*);
3192   PetscErrorCode (*func)(SNES,Vec,Vec,void*);
3193   Vec            f,fpc;
3194   void           *funcctx;
3195   PetscErrorCode (*jac)(SNES,Vec,Mat,Mat,void*);
3196   void           *jacctx,*appctx;
3197   Mat            j,jpre;
3198 
3199   PetscFunctionBegin;
3200   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3201   if (snes->setupcalled) PetscFunctionReturn(0);
3202   PetscCall(PetscLogEventBegin(SNES_Setup,snes,0,0,0));
3203 
3204   if (!((PetscObject)snes)->type_name) {
3205     PetscCall(SNESSetType(snes,SNESNEWTONLS));
3206   }
3207 
3208   PetscCall(SNESGetFunction(snes,&snes->vec_func,NULL,NULL));
3209 
3210   PetscCall(SNESGetDM(snes,&dm));
3211   PetscCall(DMGetDMSNES(dm,&sdm));
3212   PetscCheck(sdm->ops->computefunction,PetscObjectComm((PetscObject)dm),PETSC_ERR_ARG_WRONGSTATE,"Function never provided to SNES object");
3213   PetscCall(SNESSetDefaultComputeJacobian(snes));
3214 
3215   if (!snes->vec_func) {
3216     PetscCall(DMCreateGlobalVector(dm,&snes->vec_func));
3217   }
3218 
3219   if (!snes->ksp) {
3220     PetscCall(SNESGetKSP(snes, &snes->ksp));
3221   }
3222 
3223   if (snes->linesearch) {
3224     PetscCall(SNESGetLineSearch(snes, &snes->linesearch));
3225     PetscCall(SNESLineSearchSetFunction(snes->linesearch,SNESComputeFunction));
3226   }
3227 
3228   if (snes->npc && snes->npcside == PC_LEFT) {
3229     snes->mf          = PETSC_TRUE;
3230     snes->mf_operator = PETSC_FALSE;
3231   }
3232 
3233   if (snes->npc) {
3234     /* copy the DM over */
3235     PetscCall(SNESGetDM(snes,&dm));
3236     PetscCall(SNESSetDM(snes->npc,dm));
3237 
3238     PetscCall(SNESGetFunction(snes,&f,&func,&funcctx));
3239     PetscCall(VecDuplicate(f,&fpc));
3240     PetscCall(SNESSetFunction(snes->npc,fpc,func,funcctx));
3241     PetscCall(SNESGetJacobian(snes,&j,&jpre,&jac,&jacctx));
3242     PetscCall(SNESSetJacobian(snes->npc,j,jpre,jac,jacctx));
3243     PetscCall(SNESGetApplicationContext(snes,&appctx));
3244     PetscCall(SNESSetApplicationContext(snes->npc,appctx));
3245     PetscCall(VecDestroy(&fpc));
3246 
3247     /* copy the function pointers over */
3248     PetscCall(PetscObjectCopyFortranFunctionPointers((PetscObject)snes,(PetscObject)snes->npc));
3249 
3250     /* default to 1 iteration */
3251     PetscCall(SNESSetTolerances(snes->npc,0.0,0.0,0.0,1,snes->npc->max_funcs));
3252     if (snes->npcside == PC_RIGHT) {
3253       PetscCall(SNESSetNormSchedule(snes->npc,SNES_NORM_FINAL_ONLY));
3254     } else {
3255       PetscCall(SNESSetNormSchedule(snes->npc,SNES_NORM_NONE));
3256     }
3257     PetscCall(SNESSetFromOptions(snes->npc));
3258 
3259     /* copy the line search context over */
3260     if (snes->linesearch && snes->npc->linesearch) {
3261       PetscCall(SNESGetLineSearch(snes,&linesearch));
3262       PetscCall(SNESGetLineSearch(snes->npc,&pclinesearch));
3263       PetscCall(SNESLineSearchGetPreCheck(linesearch,&precheck,&lsprectx));
3264       PetscCall(SNESLineSearchGetPostCheck(linesearch,&postcheck,&lspostctx));
3265       PetscCall(SNESLineSearchSetPreCheck(pclinesearch,precheck,lsprectx));
3266       PetscCall(SNESLineSearchSetPostCheck(pclinesearch,postcheck,lspostctx));
3267       PetscCall(PetscObjectCopyFortranFunctionPointers((PetscObject)linesearch, (PetscObject)pclinesearch));
3268     }
3269   }
3270   if (snes->mf) {
3271     PetscCall(SNESSetUpMatrixFree_Private(snes, snes->mf_operator, snes->mf_version));
3272   }
3273   if (snes->ops->usercompute && !snes->user) {
3274     PetscCall((*snes->ops->usercompute)(snes,(void**)&snes->user));
3275   }
3276 
3277   snes->jac_iter = 0;
3278   snes->pre_iter = 0;
3279 
3280   if (snes->ops->setup) {
3281     PetscCall((*snes->ops->setup)(snes));
3282   }
3283 
3284   PetscCall(SNESSetDefaultComputeJacobian(snes));
3285 
3286   if (snes->npc && snes->npcside == PC_LEFT) {
3287     if (snes->functype == SNES_FUNCTION_PRECONDITIONED) {
3288       if (snes->linesearch) {
3289         PetscCall(SNESGetLineSearch(snes,&linesearch));
3290         PetscCall(SNESLineSearchSetFunction(linesearch,SNESComputeFunctionDefaultNPC));
3291       }
3292     }
3293   }
3294   PetscCall(PetscLogEventEnd(SNES_Setup,snes,0,0,0));
3295   snes->setupcalled = PETSC_TRUE;
3296   PetscFunctionReturn(0);
3297 }
3298 
3299 /*@
3300    SNESReset - Resets a SNES context to the snessetupcalled = 0 state and removes any allocated Vecs and Mats
3301 
3302    Collective on SNES
3303 
3304    Input Parameter:
3305 .  snes - iterative context obtained from SNESCreate()
3306 
3307    Level: intermediate
3308 
3309    Notes:
3310     Also calls the application context destroy routine set with SNESSetComputeApplicationContext()
3311 
3312 .seealso: `SNESCreate()`, `SNESSetUp()`, `SNESSolve()`
3313 @*/
3314 PetscErrorCode  SNESReset(SNES snes)
3315 {
3316   PetscFunctionBegin;
3317   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3318   if (snes->ops->userdestroy && snes->user) {
3319     PetscCall((*snes->ops->userdestroy)((void**)&snes->user));
3320     snes->user = NULL;
3321   }
3322   if (snes->npc) {
3323     PetscCall(SNESReset(snes->npc));
3324   }
3325 
3326   if (snes->ops->reset) {
3327     PetscCall((*snes->ops->reset)(snes));
3328   }
3329   if (snes->ksp) {
3330     PetscCall(KSPReset(snes->ksp));
3331   }
3332 
3333   if (snes->linesearch) {
3334     PetscCall(SNESLineSearchReset(snes->linesearch));
3335   }
3336 
3337   PetscCall(VecDestroy(&snes->vec_rhs));
3338   PetscCall(VecDestroy(&snes->vec_sol));
3339   PetscCall(VecDestroy(&snes->vec_sol_update));
3340   PetscCall(VecDestroy(&snes->vec_func));
3341   PetscCall(MatDestroy(&snes->jacobian));
3342   PetscCall(MatDestroy(&snes->jacobian_pre));
3343   PetscCall(MatDestroy(&snes->picard));
3344   PetscCall(VecDestroyVecs(snes->nwork,&snes->work));
3345   PetscCall(VecDestroyVecs(snes->nvwork,&snes->vwork));
3346 
3347   snes->alwayscomputesfinalresidual = PETSC_FALSE;
3348 
3349   snes->nwork       = snes->nvwork = 0;
3350   snes->setupcalled = PETSC_FALSE;
3351   PetscFunctionReturn(0);
3352 }
3353 
3354 /*@
3355    SNESConvergedReasonViewCancel - Clears all the reasonview functions for a SNES object.
3356 
3357    Collective on SNES
3358 
3359    Input Parameter:
3360 .  snes - iterative context obtained from SNESCreate()
3361 
3362    Level: intermediate
3363 
3364 .seealso: `SNESCreate()`, `SNESDestroy()`, `SNESReset()`
3365 @*/
3366 PetscErrorCode  SNESConvergedReasonViewCancel(SNES snes)
3367 {
3368   PetscInt       i;
3369 
3370   PetscFunctionBegin;
3371   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3372   for (i=0; i<snes->numberreasonviews; i++) {
3373     if (snes->reasonviewdestroy[i]) {
3374       PetscCall((*snes->reasonviewdestroy[i])(&snes->reasonviewcontext[i]));
3375     }
3376   }
3377   snes->numberreasonviews = 0;
3378   PetscFunctionReturn(0);
3379 }
3380 
3381 /*@C
3382    SNESDestroy - Destroys the nonlinear solver context that was created
3383    with SNESCreate().
3384 
3385    Collective on SNES
3386 
3387    Input Parameter:
3388 .  snes - the SNES context
3389 
3390    Level: beginner
3391 
3392 .seealso: `SNESCreate()`, `SNESSolve()`
3393 @*/
3394 PetscErrorCode  SNESDestroy(SNES *snes)
3395 {
3396   PetscFunctionBegin;
3397   if (!*snes) PetscFunctionReturn(0);
3398   PetscValidHeaderSpecific((*snes),SNES_CLASSID,1);
3399   if (--((PetscObject)(*snes))->refct > 0) {*snes = NULL; PetscFunctionReturn(0);}
3400 
3401   PetscCall(SNESReset((*snes)));
3402   PetscCall(SNESDestroy(&(*snes)->npc));
3403 
3404   /* if memory was published with SAWs then destroy it */
3405   PetscCall(PetscObjectSAWsViewOff((PetscObject)*snes));
3406   if ((*snes)->ops->destroy) PetscCall((*((*snes))->ops->destroy)((*snes)));
3407 
3408   if ((*snes)->dm) PetscCall(DMCoarsenHookRemove((*snes)->dm,DMCoarsenHook_SNESVecSol,DMRestrictHook_SNESVecSol,*snes));
3409   PetscCall(DMDestroy(&(*snes)->dm));
3410   PetscCall(KSPDestroy(&(*snes)->ksp));
3411   PetscCall(SNESLineSearchDestroy(&(*snes)->linesearch));
3412 
3413   PetscCall(PetscFree((*snes)->kspconvctx));
3414   if ((*snes)->ops->convergeddestroy) {
3415     PetscCall((*(*snes)->ops->convergeddestroy)((*snes)->cnvP));
3416   }
3417   if ((*snes)->conv_hist_alloc) {
3418     PetscCall(PetscFree2((*snes)->conv_hist,(*snes)->conv_hist_its));
3419   }
3420   PetscCall(SNESMonitorCancel((*snes)));
3421   PetscCall(SNESConvergedReasonViewCancel((*snes)));
3422   PetscCall(PetscHeaderDestroy(snes));
3423   PetscFunctionReturn(0);
3424 }
3425 
3426 /* ----------- Routines to set solver parameters ---------- */
3427 
3428 /*@
3429    SNESSetLagPreconditioner - Determines when the preconditioner is rebuilt in the nonlinear solve.
3430 
3431    Logically Collective on SNES
3432 
3433    Input Parameters:
3434 +  snes - the SNES context
3435 -  lag - 1 means rebuild every time the Jacobian is computed within a single nonlinear solve, 2 means every second time
3436          the Jacobian is built etc. -2 indicates rebuild preconditioner at next chance but then never rebuild after that
3437 
3438    Options Database Keys:
3439 +    -snes_lag_jacobian_persists <true,false> - sets the persistence
3440 .    -snes_lag_jacobian <-2,1,2,...> - sets the lag
3441 .    -snes_lag_preconditioner_persists <true,false> - sets the persistence
3442 -    -snes_lag_preconditioner <-2,1,2,...> - sets the lag
3443 
3444    Notes:
3445    The default is 1
3446    The preconditioner is ALWAYS built in the first iteration of a nonlinear solve unless lag is -1 or SNESSetLagPreconditionerPersists() was called
3447 
3448    SNESSetLagPreconditionerPersists() allows using the same uniform lagging (for example every second solve) across multiple solves.
3449 
3450    Level: intermediate
3451 
3452 .seealso: `SNESSetTrustRegionTolerance()`, `SNESGetLagPreconditioner()`, `SNESSetLagJacobian()`, `SNESGetLagJacobian()`, `SNESSetLagPreconditionerPersists()`,
3453           `SNESSetLagJacobianPersists()`
3454 
3455 @*/
3456 PetscErrorCode  SNESSetLagPreconditioner(SNES snes,PetscInt lag)
3457 {
3458   PetscFunctionBegin;
3459   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3460   PetscCheck(lag >= -2,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Lag must be -2, -1, 1 or greater");
3461   PetscCheck(lag,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Lag cannot be 0");
3462   PetscValidLogicalCollectiveInt(snes,lag,2);
3463   snes->lagpreconditioner = lag;
3464   PetscFunctionReturn(0);
3465 }
3466 
3467 /*@
3468    SNESSetGridSequence - sets the number of steps of grid sequencing that SNES does
3469 
3470    Logically Collective on SNES
3471 
3472    Input Parameters:
3473 +  snes - the SNES context
3474 -  steps - the number of refinements to do, defaults to 0
3475 
3476    Options Database Keys:
3477 .    -snes_grid_sequence <steps> - Use grid sequencing to generate initial guess
3478 
3479    Level: intermediate
3480 
3481    Notes:
3482    Use SNESGetSolution() to extract the fine grid solution after grid sequencing.
3483 
3484 .seealso: `SNESSetTrustRegionTolerance()`, `SNESGetLagPreconditioner()`, `SNESSetLagJacobian()`, `SNESGetLagJacobian()`, `SNESGetGridSequence()`
3485 
3486 @*/
3487 PetscErrorCode  SNESSetGridSequence(SNES snes,PetscInt steps)
3488 {
3489   PetscFunctionBegin;
3490   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3491   PetscValidLogicalCollectiveInt(snes,steps,2);
3492   snes->gridsequence = steps;
3493   PetscFunctionReturn(0);
3494 }
3495 
3496 /*@
3497    SNESGetGridSequence - gets the number of steps of grid sequencing that SNES does
3498 
3499    Logically Collective on SNES
3500 
3501    Input Parameter:
3502 .  snes - the SNES context
3503 
3504    Output Parameter:
3505 .  steps - the number of refinements to do, defaults to 0
3506 
3507    Options Database Keys:
3508 .    -snes_grid_sequence <steps> - set number of refinements
3509 
3510    Level: intermediate
3511 
3512    Notes:
3513    Use SNESGetSolution() to extract the fine grid solution after grid sequencing.
3514 
3515 .seealso: `SNESSetTrustRegionTolerance()`, `SNESGetLagPreconditioner()`, `SNESSetLagJacobian()`, `SNESGetLagJacobian()`, `SNESSetGridSequence()`
3516 
3517 @*/
3518 PetscErrorCode  SNESGetGridSequence(SNES snes,PetscInt *steps)
3519 {
3520   PetscFunctionBegin;
3521   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3522   *steps = snes->gridsequence;
3523   PetscFunctionReturn(0);
3524 }
3525 
3526 /*@
3527    SNESGetLagPreconditioner - Indicates how often the preconditioner is rebuilt
3528 
3529    Not Collective
3530 
3531    Input Parameter:
3532 .  snes - the SNES context
3533 
3534    Output Parameter:
3535 .   lag - -1 indicates NEVER rebuild, 1 means rebuild every time the Jacobian is computed within a single nonlinear solve, 2 means every second time
3536          the Jacobian is built etc. -2 indicates rebuild preconditioner at next chance but then never rebuild after that
3537 
3538    Options Database Keys:
3539 +    -snes_lag_jacobian_persists <true,false> - sets the persistence
3540 .    -snes_lag_jacobian <-2,1,2,...> - sets the lag
3541 .    -snes_lag_preconditioner_persists <true,false> - sets the persistence
3542 -    -snes_lag_preconditioner <-2,1,2,...> - sets the lag
3543 
3544    Notes:
3545    The default is 1
3546    The preconditioner is ALWAYS built in the first iteration of a nonlinear solve unless lag is -1
3547 
3548    Level: intermediate
3549 
3550 .seealso: `SNESSetTrustRegionTolerance()`, `SNESSetLagPreconditioner()`, `SNESSetLagJacobianPersists()`, `SNESSetLagPreconditionerPersists()`
3551 
3552 @*/
3553 PetscErrorCode  SNESGetLagPreconditioner(SNES snes,PetscInt *lag)
3554 {
3555   PetscFunctionBegin;
3556   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3557   *lag = snes->lagpreconditioner;
3558   PetscFunctionReturn(0);
3559 }
3560 
3561 /*@
3562    SNESSetLagJacobian - Determines when the Jacobian is rebuilt in the nonlinear solve. See SNESSetLagPreconditioner() for determining how
3563      often the preconditioner is rebuilt.
3564 
3565    Logically Collective on SNES
3566 
3567    Input Parameters:
3568 +  snes - the SNES context
3569 -  lag - -1 indicates NEVER rebuild, 1 means rebuild every time the Jacobian is computed within a single nonlinear solve, 2 means every second time
3570          the Jacobian is built etc. -2 means rebuild at next chance but then never again
3571 
3572    Options Database Keys:
3573 +    -snes_lag_jacobian_persists <true,false> - sets the persistence
3574 .    -snes_lag_jacobian <-2,1,2,...> - sets the lag
3575 .    -snes_lag_preconditioner_persists <true,false> - sets the persistence
3576 -    -snes_lag_preconditioner <-2,1,2,...> - sets the lag.
3577 
3578    Notes:
3579    The default is 1
3580    The Jacobian is ALWAYS built in the first iteration of a nonlinear solve unless lag is -1
3581    If  -1 is used before the very first nonlinear solve the CODE WILL FAIL! because no Jacobian is used, use -2 to indicate you want it recomputed
3582    at the next Newton step but never again (unless it is reset to another value)
3583 
3584    Level: intermediate
3585 
3586 .seealso: `SNESSetTrustRegionTolerance()`, `SNESGetLagPreconditioner()`, `SNESSetLagPreconditioner()`, `SNESGetLagJacobianPersists()`, `SNESSetLagPreconditionerPersists()`
3587 
3588 @*/
3589 PetscErrorCode  SNESSetLagJacobian(SNES snes,PetscInt lag)
3590 {
3591   PetscFunctionBegin;
3592   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3593   PetscCheck(lag >= -2,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Lag must be -2, -1, 1 or greater");
3594   PetscCheck(lag,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Lag cannot be 0");
3595   PetscValidLogicalCollectiveInt(snes,lag,2);
3596   snes->lagjacobian = lag;
3597   PetscFunctionReturn(0);
3598 }
3599 
3600 /*@
3601    SNESGetLagJacobian - Indicates how often the Jacobian is rebuilt. See SNESGetLagPreconditioner() to determine when the preconditioner is rebuilt
3602 
3603    Not Collective
3604 
3605    Input Parameter:
3606 .  snes - the SNES context
3607 
3608    Output Parameter:
3609 .   lag - -1 indicates NEVER rebuild, 1 means rebuild every time the Jacobian is computed within a single nonlinear solve, 2 means every second time
3610          the Jacobian is built etc.
3611 
3612    Notes:
3613    The default is 1
3614    The jacobian is ALWAYS built in the first iteration of a nonlinear solve unless lag is -1 or SNESSetLagJacobianPersists() was called.
3615 
3616    Level: intermediate
3617 
3618 .seealso: `SNESSetTrustRegionTolerance()`, `SNESSetLagJacobian()`, `SNESSetLagPreconditioner()`, `SNESGetLagPreconditioner()`, `SNESSetLagJacobianPersists()`, `SNESSetLagPreconditionerPersists()`
3619 
3620 @*/
3621 PetscErrorCode  SNESGetLagJacobian(SNES snes,PetscInt *lag)
3622 {
3623   PetscFunctionBegin;
3624   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3625   *lag = snes->lagjacobian;
3626   PetscFunctionReturn(0);
3627 }
3628 
3629 /*@
3630    SNESSetLagJacobianPersists - Set whether or not the Jacobian lagging persists through multiple solves
3631 
3632    Logically collective on SNES
3633 
3634    Input Parameters:
3635 +  snes - the SNES context
3636 -   flg - jacobian lagging persists if true
3637 
3638    Options Database Keys:
3639 +    -snes_lag_jacobian_persists <true,false> - sets the persistence
3640 .    -snes_lag_jacobian <-2,1,2,...> - sets the lag
3641 .    -snes_lag_preconditioner_persists <true,false> - sets the persistence
3642 -    -snes_lag_preconditioner <-2,1,2,...> - sets the lag
3643 
3644    Notes:
3645     This is useful both for nonlinear preconditioning, where it's appropriate to have the Jacobian be stale by
3646    several solves, and for implicit time-stepping, where Jacobian lagging in the inner nonlinear solve over several
3647    timesteps may present huge efficiency gains.
3648 
3649    Level: developer
3650 
3651 .seealso: `SNESSetLagPreconditionerPersists()`, `SNESSetLagJacobian()`, `SNESGetLagJacobian()`, `SNESGetNPC()`, `SNESSetLagJacobianPersists()`
3652 
3653 @*/
3654 PetscErrorCode  SNESSetLagJacobianPersists(SNES snes,PetscBool flg)
3655 {
3656   PetscFunctionBegin;
3657   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3658   PetscValidLogicalCollectiveBool(snes,flg,2);
3659   snes->lagjac_persist = flg;
3660   PetscFunctionReturn(0);
3661 }
3662 
3663 /*@
3664    SNESSetLagPreconditionerPersists - Set whether or not the preconditioner lagging persists through multiple nonlinear solves
3665 
3666    Logically Collective on SNES
3667 
3668    Input Parameters:
3669 +  snes - the SNES context
3670 -   flg - preconditioner lagging persists if true
3671 
3672    Options Database Keys:
3673 +    -snes_lag_jacobian_persists <true,false> - sets the persistence
3674 .    -snes_lag_jacobian <-2,1,2,...> - sets the lag
3675 .    -snes_lag_preconditioner_persists <true,false> - sets the persistence
3676 -    -snes_lag_preconditioner <-2,1,2,...> - sets the lag
3677 
3678    Notes:
3679     This is useful both for nonlinear preconditioning, where it's appropriate to have the preconditioner be stale
3680    by several solves, and for implicit time-stepping, where preconditioner lagging in the inner nonlinear solve over
3681    several timesteps may present huge efficiency gains.
3682 
3683    Level: developer
3684 
3685 .seealso: `SNESSetLagJacobianPersists()`, `SNESSetLagJacobian()`, `SNESGetLagJacobian()`, `SNESGetNPC()`, `SNESSetLagPreconditioner()`
3686 
3687 @*/
3688 PetscErrorCode  SNESSetLagPreconditionerPersists(SNES snes,PetscBool flg)
3689 {
3690   PetscFunctionBegin;
3691   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3692   PetscValidLogicalCollectiveBool(snes,flg,2);
3693   snes->lagpre_persist = flg;
3694   PetscFunctionReturn(0);
3695 }
3696 
3697 /*@
3698    SNESSetForceIteration - force SNESSolve() to take at least one iteration regardless of the initial residual norm
3699 
3700    Logically Collective on SNES
3701 
3702    Input Parameters:
3703 +  snes - the SNES context
3704 -  force - PETSC_TRUE require at least one iteration
3705 
3706    Options Database Keys:
3707 .    -snes_force_iteration <force> - Sets forcing an iteration
3708 
3709    Notes:
3710    This is used sometimes with TS to prevent TS from detecting a false steady state solution
3711 
3712    Level: intermediate
3713 
3714 .seealso: `SNESSetTrustRegionTolerance()`, `SNESSetDivergenceTolerance()`
3715 @*/
3716 PetscErrorCode  SNESSetForceIteration(SNES snes,PetscBool force)
3717 {
3718   PetscFunctionBegin;
3719   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3720   snes->forceiteration = force;
3721   PetscFunctionReturn(0);
3722 }
3723 
3724 /*@
3725    SNESGetForceIteration - Whether or not to force SNESSolve() take at least one iteration regardless of the initial residual norm
3726 
3727    Logically Collective on SNES
3728 
3729    Input Parameters:
3730 .  snes - the SNES context
3731 
3732    Output Parameter:
3733 .  force - PETSC_TRUE requires at least one iteration.
3734 
3735    Level: intermediate
3736 
3737 .seealso: `SNESSetForceIteration()`, `SNESSetTrustRegionTolerance()`, `SNESSetDivergenceTolerance()`
3738 @*/
3739 PetscErrorCode  SNESGetForceIteration(SNES snes,PetscBool *force)
3740 {
3741   PetscFunctionBegin;
3742   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3743   *force = snes->forceiteration;
3744   PetscFunctionReturn(0);
3745 }
3746 
3747 /*@
3748    SNESSetTolerances - Sets various parameters used in convergence tests.
3749 
3750    Logically Collective on SNES
3751 
3752    Input Parameters:
3753 +  snes - the SNES context
3754 .  abstol - absolute convergence tolerance
3755 .  rtol - relative convergence tolerance
3756 .  stol -  convergence tolerance in terms of the norm of the change in the solution between steps,  || delta x || < stol*|| x ||
3757 .  maxit - maximum number of iterations
3758 -  maxf - maximum number of function evaluations (-1 indicates no limit)
3759 
3760    Options Database Keys:
3761 +    -snes_atol <abstol> - Sets abstol
3762 .    -snes_rtol <rtol> - Sets rtol
3763 .    -snes_stol <stol> - Sets stol
3764 .    -snes_max_it <maxit> - Sets maxit
3765 -    -snes_max_funcs <maxf> - Sets maxf
3766 
3767    Notes:
3768    The default maximum number of iterations is 50.
3769    The default maximum number of function evaluations is 1000.
3770 
3771    Level: intermediate
3772 
3773 .seealso: `SNESSetTrustRegionTolerance()`, `SNESSetDivergenceTolerance()`, `SNESSetForceIteration()`
3774 @*/
3775 PetscErrorCode  SNESSetTolerances(SNES snes,PetscReal abstol,PetscReal rtol,PetscReal stol,PetscInt maxit,PetscInt maxf)
3776 {
3777   PetscFunctionBegin;
3778   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3779   PetscValidLogicalCollectiveReal(snes,abstol,2);
3780   PetscValidLogicalCollectiveReal(snes,rtol,3);
3781   PetscValidLogicalCollectiveReal(snes,stol,4);
3782   PetscValidLogicalCollectiveInt(snes,maxit,5);
3783   PetscValidLogicalCollectiveInt(snes,maxf,6);
3784 
3785   if (abstol != PETSC_DEFAULT) {
3786     PetscCheck(abstol >= 0.0,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_OUTOFRANGE,"Absolute tolerance %g must be non-negative",(double)abstol);
3787     snes->abstol = abstol;
3788   }
3789   if (rtol != PETSC_DEFAULT) {
3790     PetscCheck(rtol >= 0.0 && 1.0 > rtol,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_OUTOFRANGE,"Relative tolerance %g must be non-negative and less than 1.0",(double)rtol);
3791     snes->rtol = rtol;
3792   }
3793   if (stol != PETSC_DEFAULT) {
3794     PetscCheck(stol >= 0.0,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_OUTOFRANGE,"Step tolerance %g must be non-negative",(double)stol);
3795     snes->stol = stol;
3796   }
3797   if (maxit != PETSC_DEFAULT) {
3798     PetscCheck(maxit >= 0,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_OUTOFRANGE,"Maximum number of iterations %" PetscInt_FMT " must be non-negative",maxit);
3799     snes->max_its = maxit;
3800   }
3801   if (maxf != PETSC_DEFAULT) {
3802     PetscCheck(maxf >= -1,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_OUTOFRANGE,"Maximum number of function evaluations %" PetscInt_FMT " must be -1 or nonnegative",maxf);
3803     snes->max_funcs = maxf;
3804   }
3805   snes->tolerancesset = PETSC_TRUE;
3806   PetscFunctionReturn(0);
3807 }
3808 
3809 /*@
3810    SNESSetDivergenceTolerance - Sets the divergence tolerance used for the SNES divergence test.
3811 
3812    Logically Collective on SNES
3813 
3814    Input Parameters:
3815 +  snes - the SNES context
3816 -  divtol - the divergence tolerance. Use -1 to deactivate the test.
3817 
3818    Options Database Keys:
3819 .    -snes_divergence_tolerance <divtol> - Sets divtol
3820 
3821    Notes:
3822    The default divergence tolerance is 1e4.
3823 
3824    Level: intermediate
3825 
3826 .seealso: `SNESSetTolerances()`, `SNESGetDivergenceTolerance`
3827 @*/
3828 PetscErrorCode  SNESSetDivergenceTolerance(SNES snes,PetscReal divtol)
3829 {
3830   PetscFunctionBegin;
3831   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3832   PetscValidLogicalCollectiveReal(snes,divtol,2);
3833 
3834   if (divtol != PETSC_DEFAULT) {
3835     snes->divtol = divtol;
3836   }
3837   else {
3838     snes->divtol = 1.0e4;
3839   }
3840   PetscFunctionReturn(0);
3841 }
3842 
3843 /*@
3844    SNESGetTolerances - Gets various parameters used in convergence tests.
3845 
3846    Not Collective
3847 
3848    Input Parameters:
3849 +  snes - the SNES context
3850 .  atol - absolute convergence tolerance
3851 .  rtol - relative convergence tolerance
3852 .  stol -  convergence tolerance in terms of the norm
3853            of the change in the solution between steps
3854 .  maxit - maximum number of iterations
3855 -  maxf - maximum number of function evaluations
3856 
3857    Notes:
3858    The user can specify NULL for any parameter that is not needed.
3859 
3860    Level: intermediate
3861 
3862 .seealso: `SNESSetTolerances()`
3863 @*/
3864 PetscErrorCode  SNESGetTolerances(SNES snes,PetscReal *atol,PetscReal *rtol,PetscReal *stol,PetscInt *maxit,PetscInt *maxf)
3865 {
3866   PetscFunctionBegin;
3867   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3868   if (atol)  *atol  = snes->abstol;
3869   if (rtol)  *rtol  = snes->rtol;
3870   if (stol)  *stol  = snes->stol;
3871   if (maxit) *maxit = snes->max_its;
3872   if (maxf)  *maxf  = snes->max_funcs;
3873   PetscFunctionReturn(0);
3874 }
3875 
3876 /*@
3877    SNESGetDivergenceTolerance - Gets divergence tolerance used in divergence test.
3878 
3879    Not Collective
3880 
3881    Input Parameters:
3882 +  snes - the SNES context
3883 -  divtol - divergence tolerance
3884 
3885    Level: intermediate
3886 
3887 .seealso: `SNESSetDivergenceTolerance()`
3888 @*/
3889 PetscErrorCode  SNESGetDivergenceTolerance(SNES snes,PetscReal *divtol)
3890 {
3891   PetscFunctionBegin;
3892   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3893   if (divtol) *divtol = snes->divtol;
3894   PetscFunctionReturn(0);
3895 }
3896 
3897 /*@
3898    SNESSetTrustRegionTolerance - Sets the trust region parameter tolerance.
3899 
3900    Logically Collective on SNES
3901 
3902    Input Parameters:
3903 +  snes - the SNES context
3904 -  tol - tolerance
3905 
3906    Options Database Key:
3907 .  -snes_trtol <tol> - Sets tol
3908 
3909    Level: intermediate
3910 
3911 .seealso: `SNESSetTolerances()`
3912 @*/
3913 PetscErrorCode  SNESSetTrustRegionTolerance(SNES snes,PetscReal tol)
3914 {
3915   PetscFunctionBegin;
3916   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
3917   PetscValidLogicalCollectiveReal(snes,tol,2);
3918   snes->deltatol = tol;
3919   PetscFunctionReturn(0);
3920 }
3921 
3922 PETSC_INTERN PetscErrorCode  SNESMonitorRange_Private(SNES,PetscInt,PetscReal*);
3923 
3924 PetscErrorCode  SNESMonitorLGRange(SNES snes,PetscInt n,PetscReal rnorm,void *monctx)
3925 {
3926   PetscDrawLG      lg;
3927   PetscReal        x,y,per;
3928   PetscViewer      v = (PetscViewer)monctx;
3929   static PetscReal prev; /* should be in the context */
3930   PetscDraw        draw;
3931 
3932   PetscFunctionBegin;
3933   PetscValidHeaderSpecific(v,PETSC_VIEWER_CLASSID,4);
3934   PetscCall(PetscViewerDrawGetDrawLG(v,0,&lg));
3935   if (!n) PetscCall(PetscDrawLGReset(lg));
3936   PetscCall(PetscDrawLGGetDraw(lg,&draw));
3937   PetscCall(PetscDrawSetTitle(draw,"Residual norm"));
3938   x    = (PetscReal)n;
3939   if (rnorm > 0.0) y = PetscLog10Real(rnorm);
3940   else y = -15.0;
3941   PetscCall(PetscDrawLGAddPoint(lg,&x,&y));
3942   if (n < 20 || !(n % 5) || snes->reason) {
3943     PetscCall(PetscDrawLGDraw(lg));
3944     PetscCall(PetscDrawLGSave(lg));
3945   }
3946 
3947   PetscCall(PetscViewerDrawGetDrawLG(v,1,&lg));
3948   if (!n) PetscCall(PetscDrawLGReset(lg));
3949   PetscCall(PetscDrawLGGetDraw(lg,&draw));
3950   PetscCall(PetscDrawSetTitle(draw,"% elemts > .2*max elemt"));
3951   PetscCall(SNESMonitorRange_Private(snes,n,&per));
3952   x    = (PetscReal)n;
3953   y    = 100.0*per;
3954   PetscCall(PetscDrawLGAddPoint(lg,&x,&y));
3955   if (n < 20 || !(n % 5) || snes->reason) {
3956     PetscCall(PetscDrawLGDraw(lg));
3957     PetscCall(PetscDrawLGSave(lg));
3958   }
3959 
3960   PetscCall(PetscViewerDrawGetDrawLG(v,2,&lg));
3961   if (!n) {prev = rnorm;PetscCall(PetscDrawLGReset(lg));}
3962   PetscCall(PetscDrawLGGetDraw(lg,&draw));
3963   PetscCall(PetscDrawSetTitle(draw,"(norm -oldnorm)/oldnorm"));
3964   x    = (PetscReal)n;
3965   y    = (prev - rnorm)/prev;
3966   PetscCall(PetscDrawLGAddPoint(lg,&x,&y));
3967   if (n < 20 || !(n % 5) || snes->reason) {
3968     PetscCall(PetscDrawLGDraw(lg));
3969     PetscCall(PetscDrawLGSave(lg));
3970   }
3971 
3972   PetscCall(PetscViewerDrawGetDrawLG(v,3,&lg));
3973   if (!n) PetscCall(PetscDrawLGReset(lg));
3974   PetscCall(PetscDrawLGGetDraw(lg,&draw));
3975   PetscCall(PetscDrawSetTitle(draw,"(norm -oldnorm)/oldnorm*(% > .2 max)"));
3976   x    = (PetscReal)n;
3977   y    = (prev - rnorm)/(prev*per);
3978   if (n > 2) { /*skip initial crazy value */
3979     PetscCall(PetscDrawLGAddPoint(lg,&x,&y));
3980   }
3981   if (n < 20 || !(n % 5) || snes->reason) {
3982     PetscCall(PetscDrawLGDraw(lg));
3983     PetscCall(PetscDrawLGSave(lg));
3984   }
3985   prev = rnorm;
3986   PetscFunctionReturn(0);
3987 }
3988 
3989 /*@
3990    SNESMonitor - runs the user provided monitor routines, if they exist
3991 
3992    Collective on SNES
3993 
3994    Input Parameters:
3995 +  snes - nonlinear solver context obtained from SNESCreate()
3996 .  iter - iteration number
3997 -  rnorm - relative norm of the residual
3998 
3999    Notes:
4000    This routine is called by the SNES implementations.
4001    It does not typically need to be called by the user.
4002 
4003    Level: developer
4004 
4005 .seealso: `SNESMonitorSet()`
4006 @*/
4007 PetscErrorCode  SNESMonitor(SNES snes,PetscInt iter,PetscReal rnorm)
4008 {
4009   PetscInt       i,n = snes->numbermonitors;
4010 
4011   PetscFunctionBegin;
4012   PetscCall(VecLockReadPush(snes->vec_sol));
4013   for (i=0; i<n; i++) {
4014     PetscCall((*snes->monitor[i])(snes,iter,rnorm,snes->monitorcontext[i]));
4015   }
4016   PetscCall(VecLockReadPop(snes->vec_sol));
4017   PetscFunctionReturn(0);
4018 }
4019 
4020 /* ------------ Routines to set performance monitoring options ----------- */
4021 
4022 /*MC
4023     SNESMonitorFunction - functional form passed to SNESMonitorSet() to monitor convergence of nonlinear solver
4024 
4025      Synopsis:
4026      #include <petscsnes.h>
4027 $    PetscErrorCode SNESMonitorFunction(SNES snes,PetscInt its, PetscReal norm,void *mctx)
4028 
4029      Collective on snes
4030 
4031     Input Parameters:
4032 +    snes - the SNES context
4033 .    its - iteration number
4034 .    norm - 2-norm function value (may be estimated)
4035 -    mctx - [optional] monitoring context
4036 
4037    Level: advanced
4038 
4039 .seealso: `SNESMonitorSet()`, `SNESMonitorGet()`
4040 M*/
4041 
4042 /*@C
4043    SNESMonitorSet - Sets an ADDITIONAL function that is to be used at every
4044    iteration of the nonlinear solver to display the iteration's
4045    progress.
4046 
4047    Logically Collective on SNES
4048 
4049    Input Parameters:
4050 +  snes - the SNES context
4051 .  f - the monitor function, see SNESMonitorFunction for the calling sequence
4052 .  mctx - [optional] user-defined context for private data for the
4053           monitor routine (use NULL if no context is desired)
4054 -  monitordestroy - [optional] routine that frees monitor context
4055           (may be NULL)
4056 
4057    Options Database Keys:
4058 +    -snes_monitor        - sets SNESMonitorDefault()
4059 .    -snes_monitor draw::draw_lg - sets line graph monitor,
4060 -    -snes_monitor_cancel - cancels all monitors that have
4061                             been hardwired into a code by
4062                             calls to SNESMonitorSet(), but
4063                             does not cancel those set via
4064                             the options database.
4065 
4066    Notes:
4067    Several different monitoring routines may be set by calling
4068    SNESMonitorSet() multiple times; all will be called in the
4069    order in which they were set.
4070 
4071    Fortran Notes:
4072     Only a single monitor function can be set for each SNES object
4073 
4074    Level: intermediate
4075 
4076 .seealso: `SNESMonitorDefault()`, `SNESMonitorCancel()`, `SNESMonitorFunction`
4077 @*/
4078 PetscErrorCode  SNESMonitorSet(SNES snes,PetscErrorCode (*f)(SNES,PetscInt,PetscReal,void*),void *mctx,PetscErrorCode (*monitordestroy)(void**))
4079 {
4080   PetscInt       i;
4081   PetscBool      identical;
4082 
4083   PetscFunctionBegin;
4084   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4085   for (i=0; i<snes->numbermonitors;i++) {
4086     PetscCall(PetscMonitorCompare((PetscErrorCode (*)(void))f,mctx,monitordestroy,(PetscErrorCode (*)(void))snes->monitor[i],snes->monitorcontext[i],snes->monitordestroy[i],&identical));
4087     if (identical) PetscFunctionReturn(0);
4088   }
4089   PetscCheck(snes->numbermonitors < MAXSNESMONITORS,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many monitors set");
4090   snes->monitor[snes->numbermonitors]          = f;
4091   snes->monitordestroy[snes->numbermonitors]   = monitordestroy;
4092   snes->monitorcontext[snes->numbermonitors++] = (void*)mctx;
4093   PetscFunctionReturn(0);
4094 }
4095 
4096 /*@
4097    SNESMonitorCancel - Clears all the monitor functions for a SNES object.
4098 
4099    Logically Collective on SNES
4100 
4101    Input Parameters:
4102 .  snes - the SNES context
4103 
4104    Options Database Key:
4105 .  -snes_monitor_cancel - cancels all monitors that have been hardwired
4106     into a code by calls to SNESMonitorSet(), but does not cancel those
4107     set via the options database
4108 
4109    Notes:
4110    There is no way to clear one specific monitor from a SNES object.
4111 
4112    Level: intermediate
4113 
4114 .seealso: `SNESMonitorDefault()`, `SNESMonitorSet()`
4115 @*/
4116 PetscErrorCode  SNESMonitorCancel(SNES snes)
4117 {
4118   PetscInt       i;
4119 
4120   PetscFunctionBegin;
4121   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4122   for (i=0; i<snes->numbermonitors; i++) {
4123     if (snes->monitordestroy[i]) {
4124       PetscCall((*snes->monitordestroy[i])(&snes->monitorcontext[i]));
4125     }
4126   }
4127   snes->numbermonitors = 0;
4128   PetscFunctionReturn(0);
4129 }
4130 
4131 /*MC
4132     SNESConvergenceTestFunction - functional form used for testing of convergence of nonlinear solver
4133 
4134      Synopsis:
4135      #include <petscsnes.h>
4136 $     PetscErrorCode SNESConvergenceTest(SNES snes,PetscInt it,PetscReal xnorm,PetscReal gnorm,PetscReal f,SNESConvergedReason *reason,void *cctx)
4137 
4138      Collective on snes
4139 
4140     Input Parameters:
4141 +    snes - the SNES context
4142 .    it - current iteration (0 is the first and is before any Newton step)
4143 .    xnorm - 2-norm of current iterate
4144 .    gnorm - 2-norm of current step
4145 .    f - 2-norm of function
4146 -    cctx - [optional] convergence context
4147 
4148     Output Parameter:
4149 .    reason - reason for convergence/divergence, only needs to be set when convergence or divergence is detected
4150 
4151    Level: intermediate
4152 
4153 .seealso: `SNESSetConvergenceTest()`, `SNESGetConvergenceTest()`
4154 M*/
4155 
4156 /*@C
4157    SNESSetConvergenceTest - Sets the function that is to be used
4158    to test for convergence of the nonlinear iterative solution.
4159 
4160    Logically Collective on SNES
4161 
4162    Input Parameters:
4163 +  snes - the SNES context
4164 .  SNESConvergenceTestFunction - routine to test for convergence
4165 .  cctx - [optional] context for private data for the convergence routine  (may be NULL)
4166 -  destroy - [optional] destructor for the context (may be NULL; PETSC_NULL_FUNCTION in Fortran)
4167 
4168    Level: advanced
4169 
4170 .seealso: `SNESConvergedDefault()`, `SNESConvergedSkip()`, `SNESConvergenceTestFunction`
4171 @*/
4172 PetscErrorCode  SNESSetConvergenceTest(SNES snes,PetscErrorCode (*SNESConvergenceTestFunction)(SNES,PetscInt,PetscReal,PetscReal,PetscReal,SNESConvergedReason*,void*),void *cctx,PetscErrorCode (*destroy)(void*))
4173 {
4174   PetscFunctionBegin;
4175   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4176   if (!SNESConvergenceTestFunction) SNESConvergenceTestFunction = SNESConvergedSkip;
4177   if (snes->ops->convergeddestroy) {
4178     PetscCall((*snes->ops->convergeddestroy)(snes->cnvP));
4179   }
4180   snes->ops->converged        = SNESConvergenceTestFunction;
4181   snes->ops->convergeddestroy = destroy;
4182   snes->cnvP                  = cctx;
4183   PetscFunctionReturn(0);
4184 }
4185 
4186 /*@
4187    SNESGetConvergedReason - Gets the reason the SNES iteration was stopped.
4188 
4189    Not Collective
4190 
4191    Input Parameter:
4192 .  snes - the SNES context
4193 
4194    Output Parameter:
4195 .  reason - negative value indicates diverged, positive value converged, see SNESConvergedReason or the
4196             manual pages for the individual convergence tests for complete lists
4197 
4198    Options Database:
4199 .   -snes_converged_reason - prints the reason to standard out
4200 
4201    Level: intermediate
4202 
4203    Notes:
4204     Should only be called after the call the SNESSolve() is complete, if it is called earlier it returns the value SNES__CONVERGED_ITERATING.
4205 
4206 .seealso: `SNESSetConvergenceTest()`, `SNESSetConvergedReason()`, `SNESConvergedReason`
4207 @*/
4208 PetscErrorCode SNESGetConvergedReason(SNES snes,SNESConvergedReason *reason)
4209 {
4210   PetscFunctionBegin;
4211   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4212   PetscValidPointer(reason,2);
4213   *reason = snes->reason;
4214   PetscFunctionReturn(0);
4215 }
4216 
4217 /*@C
4218    SNESGetConvergedReasonString - Return a human readable string for snes converged reason
4219 
4220    Not Collective
4221 
4222    Input Parameter:
4223 .  snes - the SNES context
4224 
4225    Output Parameter:
4226 .  strreason - a human readable string that describes SNES converged reason
4227 
4228    Level: beginner
4229 
4230 .seealso: `SNESGetConvergedReason()`
4231 @*/
4232 PetscErrorCode SNESGetConvergedReasonString(SNES snes, const char** strreason)
4233 {
4234   PetscFunctionBegin;
4235   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4236   PetscValidPointer(strreason,2);
4237   *strreason = SNESConvergedReasons[snes->reason];
4238   PetscFunctionReturn(0);
4239 }
4240 
4241 /*@
4242    SNESSetConvergedReason - Sets the reason the SNES iteration was stopped.
4243 
4244    Not Collective
4245 
4246    Input Parameters:
4247 +  snes - the SNES context
4248 -  reason - negative value indicates diverged, positive value converged, see SNESConvergedReason or the
4249             manual pages for the individual convergence tests for complete lists
4250 
4251    Level: intermediate
4252 
4253 .seealso: `SNESGetConvergedReason()`, `SNESSetConvergenceTest()`, `SNESConvergedReason`
4254 @*/
4255 PetscErrorCode SNESSetConvergedReason(SNES snes,SNESConvergedReason reason)
4256 {
4257   PetscFunctionBegin;
4258   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4259   snes->reason = reason;
4260   PetscFunctionReturn(0);
4261 }
4262 
4263 /*@
4264    SNESSetConvergenceHistory - Sets the array used to hold the convergence history.
4265 
4266    Logically Collective on SNES
4267 
4268    Input Parameters:
4269 +  snes - iterative context obtained from SNESCreate()
4270 .  a   - array to hold history, this array will contain the function norms computed at each step
4271 .  its - integer array holds the number of linear iterations for each solve.
4272 .  na  - size of a and its
4273 -  reset - PETSC_TRUE indicates each new nonlinear solve resets the history counter to zero,
4274            else it continues storing new values for new nonlinear solves after the old ones
4275 
4276    Notes:
4277    If 'a' and 'its' are NULL then space is allocated for the history. If 'na' PETSC_DECIDE or PETSC_DEFAULT then a
4278    default array of length 10000 is allocated.
4279 
4280    This routine is useful, e.g., when running a code for purposes
4281    of accurate performance monitoring, when no I/O should be done
4282    during the section of code that is being timed.
4283 
4284    Level: intermediate
4285 
4286 .seealso: `SNESGetConvergenceHistory()`
4287 
4288 @*/
4289 PetscErrorCode  SNESSetConvergenceHistory(SNES snes,PetscReal a[],PetscInt its[],PetscInt na,PetscBool reset)
4290 {
4291   PetscFunctionBegin;
4292   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4293   if (a) PetscValidRealPointer(a,2);
4294   if (its) PetscValidIntPointer(its,3);
4295   if (!a) {
4296     if (na == PETSC_DECIDE || na == PETSC_DEFAULT) na = 1000;
4297     PetscCall(PetscCalloc2(na,&a,na,&its));
4298     snes->conv_hist_alloc = PETSC_TRUE;
4299   }
4300   snes->conv_hist       = a;
4301   snes->conv_hist_its   = its;
4302   snes->conv_hist_max   = (size_t)na;
4303   snes->conv_hist_len   = 0;
4304   snes->conv_hist_reset = reset;
4305   PetscFunctionReturn(0);
4306 }
4307 
4308 #if defined(PETSC_HAVE_MATLAB_ENGINE)
4309 #include <engine.h>   /* MATLAB include file */
4310 #include <mex.h>      /* MATLAB include file */
4311 
4312 PETSC_EXTERN mxArray *SNESGetConvergenceHistoryMatlab(SNES snes)
4313 {
4314   mxArray   *mat;
4315   PetscInt  i;
4316   PetscReal *ar;
4317 
4318   PetscFunctionBegin;
4319   mat = mxCreateDoubleMatrix(snes->conv_hist_len,1,mxREAL);
4320   ar  = (PetscReal*) mxGetData(mat);
4321   for (i=0; i<snes->conv_hist_len; i++) ar[i] = snes->conv_hist[i];
4322   PetscFunctionReturn(mat);
4323 }
4324 #endif
4325 
4326 /*@C
4327    SNESGetConvergenceHistory - Gets the array used to hold the convergence history.
4328 
4329    Not Collective
4330 
4331    Input Parameter:
4332 .  snes - iterative context obtained from SNESCreate()
4333 
4334    Output Parameters:
4335 +  a   - array to hold history
4336 .  its - integer array holds the number of linear iterations (or
4337          negative if not converged) for each solve.
4338 -  na  - size of a and its
4339 
4340    Notes:
4341     The calling sequence for this routine in Fortran is
4342 $   call SNESGetConvergenceHistory(SNES snes, integer na, integer ierr)
4343 
4344    This routine is useful, e.g., when running a code for purposes
4345    of accurate performance monitoring, when no I/O should be done
4346    during the section of code that is being timed.
4347 
4348    Level: intermediate
4349 
4350 .seealso: `SNESSetConvergenceHistory()`
4351 
4352 @*/
4353 PetscErrorCode  SNESGetConvergenceHistory(SNES snes,PetscReal *a[],PetscInt *its[],PetscInt *na)
4354 {
4355   PetscFunctionBegin;
4356   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4357   if (a)   *a   = snes->conv_hist;
4358   if (its) *its = snes->conv_hist_its;
4359   if (na)  *na  = (PetscInt) snes->conv_hist_len;
4360   PetscFunctionReturn(0);
4361 }
4362 
4363 /*@C
4364   SNESSetUpdate - Sets the general-purpose update function called
4365   at the beginning of every iteration of the nonlinear solve. Specifically
4366   it is called just before the Jacobian is "evaluated".
4367 
4368   Logically Collective on SNES
4369 
4370   Input Parameters:
4371 + snes - The nonlinear solver context
4372 - func - The function
4373 
4374   Calling sequence of func:
4375 $ func (SNES snes, PetscInt step);
4376 
4377 . step - The current step of the iteration
4378 
4379   Level: advanced
4380 
4381   Note:
4382      This is NOT what one uses to update the ghost points before a function evaluation, that should be done at the beginning of your FormFunction()
4383      This is not used by most users.
4384 
4385      There are a varity of function hooks one many set that are called at different stages of the nonlinear solution process, see the functions listed below.
4386 
4387 .seealso `SNESSetJacobian()`, `SNESSolve()`, `SNESLineSearchSetPreCheck()`, `SNESLineSearchSetPostCheck()`, `SNESNewtonTRSetPreCheck()`, `SNESNewtonTRSetPostCheck()`,
4388          `SNESMonitorSet()`, `SNESSetDivergenceTest()`
4389 @*/
4390 PetscErrorCode  SNESSetUpdate(SNES snes, PetscErrorCode (*func)(SNES, PetscInt))
4391 {
4392   PetscFunctionBegin;
4393   PetscValidHeaderSpecific(snes, SNES_CLASSID,1);
4394   snes->ops->update = func;
4395   PetscFunctionReturn(0);
4396 }
4397 
4398 /*
4399    SNESScaleStep_Private - Scales a step so that its length is less than the
4400    positive parameter delta.
4401 
4402     Input Parameters:
4403 +   snes - the SNES context
4404 .   y - approximate solution of linear system
4405 .   fnorm - 2-norm of current function
4406 -   delta - trust region size
4407 
4408     Output Parameters:
4409 +   gpnorm - predicted function norm at the new point, assuming local
4410     linearization.  The value is zero if the step lies within the trust
4411     region, and exceeds zero otherwise.
4412 -   ynorm - 2-norm of the step
4413 
4414     Note:
4415     For non-trust region methods such as SNESNEWTONLS, the parameter delta
4416     is set to be the maximum allowable step size.
4417 
4418 */
4419 PetscErrorCode SNESScaleStep_Private(SNES snes,Vec y,PetscReal *fnorm,PetscReal *delta,PetscReal *gpnorm,PetscReal *ynorm)
4420 {
4421   PetscReal      nrm;
4422   PetscScalar    cnorm;
4423 
4424   PetscFunctionBegin;
4425   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4426   PetscValidHeaderSpecific(y,VEC_CLASSID,2);
4427   PetscCheckSameComm(snes,1,y,2);
4428 
4429   PetscCall(VecNorm(y,NORM_2,&nrm));
4430   if (nrm > *delta) {
4431     nrm     = *delta/nrm;
4432     *gpnorm = (1.0 - nrm)*(*fnorm);
4433     cnorm   = nrm;
4434     PetscCall(VecScale(y,cnorm));
4435     *ynorm  = *delta;
4436   } else {
4437     *gpnorm = 0.0;
4438     *ynorm  = nrm;
4439   }
4440   PetscFunctionReturn(0);
4441 }
4442 
4443 /*@C
4444    SNESConvergedReasonView - Displays the reason a SNES solve converged or diverged to a viewer
4445 
4446    Collective on SNES
4447 
4448    Parameter:
4449 +  snes - iterative context obtained from SNESCreate()
4450 -  viewer - the viewer to display the reason
4451 
4452    Options Database Keys:
4453 +  -snes_converged_reason - print reason for converged or diverged, also prints number of iterations
4454 -  -snes_converged_reason ::failed - only print reason and number of iterations when diverged
4455 
4456   Notes:
4457      To change the format of the output call PetscViewerPushFormat(viewer,format) before this call. Use PETSC_VIEWER_DEFAULT for the default,
4458      use PETSC_VIEWER_FAILED to only display a reason if it fails.
4459 
4460    Level: beginner
4461 
4462 .seealso: `SNESCreate()`, `SNESSetUp()`, `SNESDestroy()`, `SNESSetTolerances()`, `SNESConvergedDefault()`, `SNESGetConvergedReason()`, `SNESConvergedReasonViewFromOptions()`,
4463           `PetscViewerPushFormat()`, `PetscViewerPopFormat()`
4464 
4465 @*/
4466 PetscErrorCode  SNESConvergedReasonView(SNES snes,PetscViewer viewer)
4467 {
4468   PetscViewerFormat format;
4469   PetscBool         isAscii;
4470 
4471   PetscFunctionBegin;
4472   if (!viewer) viewer = PETSC_VIEWER_STDOUT_(PetscObjectComm((PetscObject)snes));
4473   PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&isAscii));
4474   if (isAscii) {
4475     PetscCall(PetscViewerGetFormat(viewer, &format));
4476     PetscCall(PetscViewerASCIIAddTab(viewer,((PetscObject)snes)->tablevel));
4477     if (format == PETSC_VIEWER_ASCII_INFO_DETAIL) {
4478       DM              dm;
4479       Vec             u;
4480       PetscDS         prob;
4481       PetscInt        Nf, f;
4482       PetscErrorCode (**exactSol)(PetscInt, PetscReal, const PetscReal[], PetscInt, PetscScalar[], void *);
4483       void            **exactCtx;
4484       PetscReal       error;
4485 
4486       PetscCall(SNESGetDM(snes, &dm));
4487       PetscCall(SNESGetSolution(snes, &u));
4488       PetscCall(DMGetDS(dm, &prob));
4489       PetscCall(PetscDSGetNumFields(prob, &Nf));
4490       PetscCall(PetscMalloc2(Nf, &exactSol, Nf, &exactCtx));
4491       for (f = 0; f < Nf; ++f) PetscCall(PetscDSGetExactSolution(prob, f, &exactSol[f], &exactCtx[f]));
4492       PetscCall(DMComputeL2Diff(dm, 0.0, exactSol, exactCtx, u, &error));
4493       PetscCall(PetscFree2(exactSol, exactCtx));
4494       if (error < 1.0e-11) PetscCall(PetscViewerASCIIPrintf(viewer, "L_2 Error: < 1.0e-11\n"));
4495       else                 PetscCall(PetscViewerASCIIPrintf(viewer, "L_2 Error: %g\n", (double)error));
4496     }
4497     if (snes->reason > 0 && format != PETSC_VIEWER_FAILED) {
4498       if (((PetscObject) snes)->prefix) {
4499         PetscCall(PetscViewerASCIIPrintf(viewer,"Nonlinear %s solve converged due to %s iterations %" PetscInt_FMT "\n",((PetscObject) snes)->prefix,SNESConvergedReasons[snes->reason],snes->iter));
4500       } else {
4501         PetscCall(PetscViewerASCIIPrintf(viewer,"Nonlinear solve converged due to %s iterations %" PetscInt_FMT "\n",SNESConvergedReasons[snes->reason],snes->iter));
4502       }
4503     } else if (snes->reason <= 0) {
4504       if (((PetscObject) snes)->prefix) {
4505         PetscCall(PetscViewerASCIIPrintf(viewer,"Nonlinear %s solve did not converge due to %s iterations %" PetscInt_FMT "\n",((PetscObject) snes)->prefix,SNESConvergedReasons[snes->reason],snes->iter));
4506       } else {
4507         PetscCall(PetscViewerASCIIPrintf(viewer,"Nonlinear solve did not converge due to %s iterations %" PetscInt_FMT "\n",SNESConvergedReasons[snes->reason],snes->iter));
4508       }
4509     }
4510     PetscCall(PetscViewerASCIISubtractTab(viewer,((PetscObject)snes)->tablevel));
4511   }
4512   PetscFunctionReturn(0);
4513 }
4514 
4515 /*@C
4516    SNESConvergedReasonViewSet - Sets an ADDITIONAL function that is to be used at the
4517     end of the nonlinear solver to display the conver reason of the nonlinear solver.
4518 
4519    Logically Collective on SNES
4520 
4521    Input Parameters:
4522 +  snes - the SNES context
4523 .  f - the snes converged reason view function
4524 .  vctx - [optional] user-defined context for private data for the
4525           snes converged reason view routine (use NULL if no context is desired)
4526 -  reasonviewdestroy - [optional] routine that frees reasonview context
4527           (may be NULL)
4528 
4529    Options Database Keys:
4530 +    -snes_converged_reason        - sets a default SNESConvergedReasonView()
4531 -    -snes_converged_reason_view_cancel - cancels all converged reason viewers that have
4532                             been hardwired into a code by
4533                             calls to SNESConvergedReasonViewSet(), but
4534                             does not cancel those set via
4535                             the options database.
4536 
4537    Notes:
4538    Several different converged reason view routines may be set by calling
4539    SNESConvergedReasonViewSet() multiple times; all will be called in the
4540    order in which they were set.
4541 
4542    Level: intermediate
4543 
4544 .seealso: `SNESConvergedReasonView()`, `SNESConvergedReasonViewCancel()`
4545 @*/
4546 PetscErrorCode  SNESConvergedReasonViewSet(SNES snes,PetscErrorCode (*f)(SNES,void*),void *vctx,PetscErrorCode (*reasonviewdestroy)(void**))
4547 {
4548   PetscInt       i;
4549   PetscBool      identical;
4550 
4551   PetscFunctionBegin;
4552   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4553   for (i=0; i<snes->numberreasonviews;i++) {
4554     PetscCall(PetscMonitorCompare((PetscErrorCode (*)(void))f,vctx,reasonviewdestroy,(PetscErrorCode (*)(void))snes->reasonview[i],snes->reasonviewcontext[i],snes->reasonviewdestroy[i],&identical));
4555     if (identical) PetscFunctionReturn(0);
4556   }
4557   PetscCheck(snes->numberreasonviews < MAXSNESREASONVIEWS,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many SNES reasonview set");
4558   snes->reasonview[snes->numberreasonviews]          = f;
4559   snes->reasonviewdestroy[snes->numberreasonviews]   = reasonviewdestroy;
4560   snes->reasonviewcontext[snes->numberreasonviews++] = (void*)vctx;
4561   PetscFunctionReturn(0);
4562 }
4563 
4564 /*@
4565   SNESConvergedReasonViewFromOptions - Processes command line options to determine if/how a SNESReason is to be viewed.
4566                                        All the user-provided convergedReasonView routines will be involved as well, if they exist.
4567 
4568   Collective on SNES
4569 
4570   Input Parameters:
4571 . snes   - the SNES object
4572 
4573   Level: intermediate
4574 
4575 .seealso: `SNESCreate()`, `SNESSetUp()`, `SNESDestroy()`, `SNESSetTolerances()`, `SNESConvergedDefault()`, `SNESGetConvergedReason()`, `SNESConvergedReasonView()`
4576 
4577 @*/
4578 PetscErrorCode SNESConvergedReasonViewFromOptions(SNES snes)
4579 {
4580   PetscViewer       viewer;
4581   PetscBool         flg;
4582   static PetscBool  incall = PETSC_FALSE;
4583   PetscViewerFormat format;
4584   PetscInt          i;
4585 
4586   PetscFunctionBegin;
4587   if (incall) PetscFunctionReturn(0);
4588   incall = PETSC_TRUE;
4589 
4590   /* All user-provided viewers are called first, if they exist. */
4591   for (i=0; i<snes->numberreasonviews; i++) {
4592     PetscCall((*snes->reasonview[i])(snes,snes->reasonviewcontext[i]));
4593   }
4594 
4595   /* Call PETSc default routine if users ask for it */
4596   PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_converged_reason",&viewer,&format,&flg));
4597   if (flg) {
4598     PetscCall(PetscViewerPushFormat(viewer,format));
4599     PetscCall(SNESConvergedReasonView(snes,viewer));
4600     PetscCall(PetscViewerPopFormat(viewer));
4601     PetscCall(PetscViewerDestroy(&viewer));
4602   }
4603   incall = PETSC_FALSE;
4604   PetscFunctionReturn(0);
4605 }
4606 
4607 /*@
4608    SNESSolve - Solves a nonlinear system F(x) = b.
4609    Call SNESSolve() after calling SNESCreate() and optional routines of the form SNESSetXXX().
4610 
4611    Collective on SNES
4612 
4613    Input Parameters:
4614 +  snes - the SNES context
4615 .  b - the constant part of the equation F(x) = b, or NULL to use zero.
4616 -  x - the solution vector.
4617 
4618    Notes:
4619    The user should initialize the vector,x, with the initial guess
4620    for the nonlinear solve prior to calling SNESSolve().  In particular,
4621    to employ an initial guess of zero, the user should explicitly set
4622    this vector to zero by calling VecSet().
4623 
4624    Level: beginner
4625 
4626 .seealso: `SNESCreate()`, `SNESDestroy()`, `SNESSetFunction()`, `SNESSetJacobian()`, `SNESSetGridSequence()`, `SNESGetSolution()`,
4627           `SNESNewtonTRSetPreCheck()`, `SNESNewtonTRGetPreCheck()`, `SNESNewtonTRSetPostCheck()`, `SNESNewtonTRGetPostCheck()`,
4628           `SNESLineSearchSetPostCheck()`, `SNESLineSearchGetPostCheck()`, `SNESLineSearchSetPreCheck()`, `SNESLineSearchGetPreCheck()`
4629 @*/
4630 PetscErrorCode  SNESSolve(SNES snes,Vec b,Vec x)
4631 {
4632   PetscBool         flg;
4633   PetscInt          grid;
4634   Vec               xcreated = NULL;
4635   DM                dm;
4636 
4637   PetscFunctionBegin;
4638   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4639   if (x) PetscValidHeaderSpecific(x,VEC_CLASSID,3);
4640   if (x) PetscCheckSameComm(snes,1,x,3);
4641   if (b) PetscValidHeaderSpecific(b,VEC_CLASSID,2);
4642   if (b) PetscCheckSameComm(snes,1,b,2);
4643 
4644   /* High level operations using the nonlinear solver */
4645   {
4646     PetscViewer       viewer;
4647     PetscViewerFormat format;
4648     PetscInt          num;
4649     PetscBool         flg;
4650     static PetscBool  incall = PETSC_FALSE;
4651 
4652     if (!incall) {
4653       /* Estimate the convergence rate of the discretization */
4654       PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject) snes),((PetscObject)snes)->options, ((PetscObject) snes)->prefix, "-snes_convergence_estimate", &viewer, &format, &flg));
4655       if (flg) {
4656         PetscConvEst conv;
4657         DM           dm;
4658         PetscReal   *alpha; /* Convergence rate of the solution error for each field in the L_2 norm */
4659         PetscInt     Nf;
4660 
4661         incall = PETSC_TRUE;
4662         PetscCall(SNESGetDM(snes, &dm));
4663         PetscCall(DMGetNumFields(dm, &Nf));
4664         PetscCall(PetscCalloc1(Nf, &alpha));
4665         PetscCall(PetscConvEstCreate(PetscObjectComm((PetscObject) snes), &conv));
4666         PetscCall(PetscConvEstSetSolver(conv, (PetscObject) snes));
4667         PetscCall(PetscConvEstSetFromOptions(conv));
4668         PetscCall(PetscConvEstSetUp(conv));
4669         PetscCall(PetscConvEstGetConvRate(conv, alpha));
4670         PetscCall(PetscViewerPushFormat(viewer, format));
4671         PetscCall(PetscConvEstRateView(conv, alpha, viewer));
4672         PetscCall(PetscViewerPopFormat(viewer));
4673         PetscCall(PetscViewerDestroy(&viewer));
4674         PetscCall(PetscConvEstDestroy(&conv));
4675         PetscCall(PetscFree(alpha));
4676         incall = PETSC_FALSE;
4677       }
4678       /* Adaptively refine the initial grid */
4679       num  = 1;
4680       PetscCall(PetscOptionsGetInt(NULL, ((PetscObject) snes)->prefix, "-snes_adapt_initial", &num, &flg));
4681       if (flg) {
4682         DMAdaptor adaptor;
4683 
4684         incall = PETSC_TRUE;
4685         PetscCall(DMAdaptorCreate(PetscObjectComm((PetscObject)snes), &adaptor));
4686         PetscCall(DMAdaptorSetSolver(adaptor, snes));
4687         PetscCall(DMAdaptorSetSequenceLength(adaptor, num));
4688         PetscCall(DMAdaptorSetFromOptions(adaptor));
4689         PetscCall(DMAdaptorSetUp(adaptor));
4690         PetscCall(DMAdaptorAdapt(adaptor, x, DM_ADAPTATION_INITIAL, &dm, &x));
4691         PetscCall(DMAdaptorDestroy(&adaptor));
4692         incall = PETSC_FALSE;
4693       }
4694       /* Use grid sequencing to adapt */
4695       num  = 0;
4696       PetscCall(PetscOptionsGetInt(NULL, ((PetscObject) snes)->prefix, "-snes_adapt_sequence", &num, NULL));
4697       if (num) {
4698         DMAdaptor adaptor;
4699 
4700         incall = PETSC_TRUE;
4701         PetscCall(DMAdaptorCreate(PetscObjectComm((PetscObject)snes), &adaptor));
4702         PetscCall(DMAdaptorSetSolver(adaptor, snes));
4703         PetscCall(DMAdaptorSetSequenceLength(adaptor, num));
4704         PetscCall(DMAdaptorSetFromOptions(adaptor));
4705         PetscCall(DMAdaptorSetUp(adaptor));
4706         PetscCall(DMAdaptorAdapt(adaptor, x, DM_ADAPTATION_SEQUENTIAL, &dm, &x));
4707         PetscCall(DMAdaptorDestroy(&adaptor));
4708         incall = PETSC_FALSE;
4709       }
4710     }
4711   }
4712   if (!x) { x = snes->vec_sol; }
4713   if (!x) {
4714     PetscCall(SNESGetDM(snes,&dm));
4715     PetscCall(DMCreateGlobalVector(dm,&xcreated));
4716     x    = xcreated;
4717   }
4718   PetscCall(SNESViewFromOptions(snes,NULL,"-snes_view_pre"));
4719 
4720   for (grid=0; grid<snes->gridsequence; grid++) PetscCall(PetscViewerASCIIPushTab(PETSC_VIEWER_STDOUT_(PetscObjectComm((PetscObject)snes))));
4721   for (grid=0; grid<snes->gridsequence+1; grid++) {
4722 
4723     /* set solution vector */
4724     if (!grid) PetscCall(PetscObjectReference((PetscObject)x));
4725     PetscCall(VecDestroy(&snes->vec_sol));
4726     snes->vec_sol = x;
4727     PetscCall(SNESGetDM(snes,&dm));
4728 
4729     /* set affine vector if provided */
4730     if (b) PetscCall(PetscObjectReference((PetscObject)b));
4731     PetscCall(VecDestroy(&snes->vec_rhs));
4732     snes->vec_rhs = b;
4733 
4734     if (snes->vec_rhs) PetscCheck(snes->vec_func != snes->vec_rhs,PETSC_COMM_SELF,PETSC_ERR_ARG_IDN,"Right hand side vector cannot be function vector");
4735     PetscCheck(snes->vec_func != snes->vec_sol,PETSC_COMM_SELF,PETSC_ERR_ARG_IDN,"Solution vector cannot be function vector");
4736     PetscCheck(snes->vec_rhs  != snes->vec_sol,PETSC_COMM_SELF,PETSC_ERR_ARG_IDN,"Solution vector cannot be right hand side vector");
4737     if (!snes->vec_sol_update /* && snes->vec_sol */) {
4738       PetscCall(VecDuplicate(snes->vec_sol,&snes->vec_sol_update));
4739       PetscCall(PetscLogObjectParent((PetscObject)snes,(PetscObject)snes->vec_sol_update));
4740     }
4741     PetscCall(DMShellSetGlobalVector(dm,snes->vec_sol));
4742     PetscCall(SNESSetUp(snes));
4743 
4744     if (!grid) {
4745       if (snes->ops->computeinitialguess) {
4746         PetscCall((*snes->ops->computeinitialguess)(snes,snes->vec_sol,snes->initialguessP));
4747       }
4748     }
4749 
4750     if (snes->conv_hist_reset) snes->conv_hist_len = 0;
4751     if (snes->counters_reset) {snes->nfuncs = 0; snes->linear_its = 0; snes->numFailures = 0;}
4752 
4753     PetscCall(PetscLogEventBegin(SNES_Solve,snes,0,0,0));
4754     PetscCall((*snes->ops->solve)(snes));
4755     PetscCall(PetscLogEventEnd(SNES_Solve,snes,0,0,0));
4756     PetscCheck(snes->reason,PETSC_COMM_SELF,PETSC_ERR_PLIB,"Internal error, solver returned without setting converged reason");
4757     snes->domainerror = PETSC_FALSE; /* clear the flag if it has been set */
4758 
4759     if (snes->lagjac_persist) snes->jac_iter += snes->iter;
4760     if (snes->lagpre_persist) snes->pre_iter += snes->iter;
4761 
4762     PetscCall(PetscOptionsGetViewer(PetscObjectComm((PetscObject)snes),((PetscObject)snes)->options,((PetscObject)snes)->prefix,"-snes_test_local_min",NULL,NULL,&flg));
4763     if (flg && !PetscPreLoadingOn) PetscCall(SNESTestLocalMin(snes));
4764     /* Call converged reason views. This may involve user-provided viewers as well */
4765     PetscCall(SNESConvergedReasonViewFromOptions(snes));
4766 
4767     if (snes->errorifnotconverged) PetscCheck(snes->reason >= 0,PetscObjectComm((PetscObject)snes),PETSC_ERR_NOT_CONVERGED,"SNESSolve has not converged");
4768     if (snes->reason < 0) break;
4769     if (grid <  snes->gridsequence) {
4770       DM  fine;
4771       Vec xnew;
4772       Mat interp;
4773 
4774       PetscCall(DMRefine(snes->dm,PetscObjectComm((PetscObject)snes),&fine));
4775       PetscCheck(fine,PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_INCOMP,"DMRefine() did not perform any refinement, cannot continue grid sequencing");
4776       PetscCall(DMCreateInterpolation(snes->dm,fine,&interp,NULL));
4777       PetscCall(DMCreateGlobalVector(fine,&xnew));
4778       PetscCall(MatInterpolate(interp,x,xnew));
4779       PetscCall(DMInterpolate(snes->dm,interp,fine));
4780       PetscCall(MatDestroy(&interp));
4781       x    = xnew;
4782 
4783       PetscCall(SNESReset(snes));
4784       PetscCall(SNESSetDM(snes,fine));
4785       PetscCall(SNESResetFromOptions(snes));
4786       PetscCall(DMDestroy(&fine));
4787       PetscCall(PetscViewerASCIIPopTab(PETSC_VIEWER_STDOUT_(PetscObjectComm((PetscObject)snes))));
4788     }
4789   }
4790   PetscCall(SNESViewFromOptions(snes,NULL,"-snes_view"));
4791   PetscCall(VecViewFromOptions(snes->vec_sol,(PetscObject)snes,"-snes_view_solution"));
4792   PetscCall(DMMonitor(snes->dm));
4793   PetscCall(SNESMonitorPauseFinal_Internal(snes));
4794 
4795   PetscCall(VecDestroy(&xcreated));
4796   PetscCall(PetscObjectSAWsBlock((PetscObject)snes));
4797   PetscFunctionReturn(0);
4798 }
4799 
4800 /* --------- Internal routines for SNES Package --------- */
4801 
4802 /*@C
4803    SNESSetType - Sets the method for the nonlinear solver.
4804 
4805    Collective on SNES
4806 
4807    Input Parameters:
4808 +  snes - the SNES context
4809 -  type - a known method
4810 
4811    Options Database Key:
4812 .  -snes_type <type> - Sets the method; use -help for a list
4813    of available methods (for instance, newtonls or newtontr)
4814 
4815    Notes:
4816    See "petsc/include/petscsnes.h" for available methods (for instance)
4817 +    SNESNEWTONLS - Newton's method with line search
4818      (systems of nonlinear equations)
4819 -    SNESNEWTONTR - Newton's method with trust region
4820      (systems of nonlinear equations)
4821 
4822   Normally, it is best to use the SNESSetFromOptions() command and then
4823   set the SNES solver type from the options database rather than by using
4824   this routine.  Using the options database provides the user with
4825   maximum flexibility in evaluating the many nonlinear solvers.
4826   The SNESSetType() routine is provided for those situations where it
4827   is necessary to set the nonlinear solver independently of the command
4828   line or options database.  This might be the case, for example, when
4829   the choice of solver changes during the execution of the program,
4830   and the user's application is taking responsibility for choosing the
4831   appropriate method.
4832 
4833     Developer Notes:
4834     SNESRegister() adds a constructor for a new SNESType to SNESList, SNESSetType() locates
4835     the constructor in that list and calls it to create the spexific object.
4836 
4837   Level: intermediate
4838 
4839 .seealso: `SNESType`, `SNESCreate()`, `SNESDestroy()`, `SNESGetType()`, `SNESSetFromOptions()`
4840 
4841 @*/
4842 PetscErrorCode  SNESSetType(SNES snes,SNESType type)
4843 {
4844   PetscBool      match;
4845   PetscErrorCode (*r)(SNES);
4846 
4847   PetscFunctionBegin;
4848   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4849   PetscValidCharPointer(type,2);
4850 
4851   PetscCall(PetscObjectTypeCompare((PetscObject)snes,type,&match));
4852   if (match) PetscFunctionReturn(0);
4853 
4854   PetscCall(PetscFunctionListFind(SNESList,type,&r));
4855   PetscCheck(r,PETSC_COMM_SELF,PETSC_ERR_ARG_UNKNOWN_TYPE,"Unable to find requested SNES type %s",type);
4856   /* Destroy the previous private SNES context */
4857   if (snes->ops->destroy) {
4858     PetscCall((*(snes)->ops->destroy)(snes));
4859     snes->ops->destroy = NULL;
4860   }
4861   /* Reinitialize function pointers in SNESOps structure */
4862   snes->ops->setup          = NULL;
4863   snes->ops->solve          = NULL;
4864   snes->ops->view           = NULL;
4865   snes->ops->setfromoptions = NULL;
4866   snes->ops->destroy        = NULL;
4867 
4868   /* It may happen the user has customized the line search before calling SNESSetType */
4869   if (((PetscObject)snes)->type_name) PetscCall(SNESLineSearchDestroy(&snes->linesearch));
4870 
4871   /* Call the SNESCreate_XXX routine for this particular Nonlinear solver */
4872   snes->setupcalled = PETSC_FALSE;
4873 
4874   PetscCall(PetscObjectChangeTypeName((PetscObject)snes,type));
4875   PetscCall((*r)(snes));
4876   PetscFunctionReturn(0);
4877 }
4878 
4879 /*@C
4880    SNESGetType - Gets the SNES method type and name (as a string).
4881 
4882    Not Collective
4883 
4884    Input Parameter:
4885 .  snes - nonlinear solver context
4886 
4887    Output Parameter:
4888 .  type - SNES method (a character string)
4889 
4890    Level: intermediate
4891 
4892 @*/
4893 PetscErrorCode  SNESGetType(SNES snes,SNESType *type)
4894 {
4895   PetscFunctionBegin;
4896   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4897   PetscValidPointer(type,2);
4898   *type = ((PetscObject)snes)->type_name;
4899   PetscFunctionReturn(0);
4900 }
4901 
4902 /*@
4903   SNESSetSolution - Sets the solution vector for use by the SNES routines.
4904 
4905   Logically Collective on SNES
4906 
4907   Input Parameters:
4908 + snes - the SNES context obtained from SNESCreate()
4909 - u    - the solution vector
4910 
4911   Level: beginner
4912 
4913 @*/
4914 PetscErrorCode SNESSetSolution(SNES snes, Vec u)
4915 {
4916   DM             dm;
4917 
4918   PetscFunctionBegin;
4919   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
4920   PetscValidHeaderSpecific(u, VEC_CLASSID, 2);
4921   PetscCall(PetscObjectReference((PetscObject) u));
4922   PetscCall(VecDestroy(&snes->vec_sol));
4923 
4924   snes->vec_sol = u;
4925 
4926   PetscCall(SNESGetDM(snes, &dm));
4927   PetscCall(DMShellSetGlobalVector(dm, u));
4928   PetscFunctionReturn(0);
4929 }
4930 
4931 /*@
4932    SNESGetSolution - Returns the vector where the approximate solution is
4933    stored. This is the fine grid solution when using SNESSetGridSequence().
4934 
4935    Not Collective, but Vec is parallel if SNES is parallel
4936 
4937    Input Parameter:
4938 .  snes - the SNES context
4939 
4940    Output Parameter:
4941 .  x - the solution
4942 
4943    Level: intermediate
4944 
4945 .seealso: `SNESGetSolutionUpdate()`, `SNESGetFunction()`
4946 @*/
4947 PetscErrorCode  SNESGetSolution(SNES snes,Vec *x)
4948 {
4949   PetscFunctionBegin;
4950   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4951   PetscValidPointer(x,2);
4952   *x = snes->vec_sol;
4953   PetscFunctionReturn(0);
4954 }
4955 
4956 /*@
4957    SNESGetSolutionUpdate - Returns the vector where the solution update is
4958    stored.
4959 
4960    Not Collective, but Vec is parallel if SNES is parallel
4961 
4962    Input Parameter:
4963 .  snes - the SNES context
4964 
4965    Output Parameter:
4966 .  x - the solution update
4967 
4968    Level: advanced
4969 
4970 .seealso: `SNESGetSolution()`, `SNESGetFunction()`
4971 @*/
4972 PetscErrorCode  SNESGetSolutionUpdate(SNES snes,Vec *x)
4973 {
4974   PetscFunctionBegin;
4975   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
4976   PetscValidPointer(x,2);
4977   *x = snes->vec_sol_update;
4978   PetscFunctionReturn(0);
4979 }
4980 
4981 /*@C
4982    SNESGetFunction - Returns the vector where the function is stored.
4983 
4984    Not Collective, but Vec is parallel if SNES is parallel. Collective if Vec is requested, but has not been created yet.
4985 
4986    Input Parameter:
4987 .  snes - the SNES context
4988 
4989    Output Parameters:
4990 +  r - the vector that is used to store residuals (or NULL if you don't want it)
4991 .  f - the function (or NULL if you don't want it); see SNESFunction for calling sequence details
4992 -  ctx - the function context (or NULL if you don't want it)
4993 
4994    Level: advanced
4995 
4996     Notes: The vector r DOES NOT, in general contain the current value of the SNES nonlinear function
4997 
4998 .seealso: `SNESSetFunction()`, `SNESGetSolution()`, `SNESFunction`
4999 @*/
5000 PetscErrorCode  SNESGetFunction(SNES snes,Vec *r,PetscErrorCode (**f)(SNES,Vec,Vec,void*),void **ctx)
5001 {
5002   DM             dm;
5003 
5004   PetscFunctionBegin;
5005   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5006   if (r) {
5007     if (!snes->vec_func) {
5008       if (snes->vec_rhs) {
5009         PetscCall(VecDuplicate(snes->vec_rhs,&snes->vec_func));
5010       } else if (snes->vec_sol) {
5011         PetscCall(VecDuplicate(snes->vec_sol,&snes->vec_func));
5012       } else if (snes->dm) {
5013         PetscCall(DMCreateGlobalVector(snes->dm,&snes->vec_func));
5014       }
5015     }
5016     *r = snes->vec_func;
5017   }
5018   PetscCall(SNESGetDM(snes,&dm));
5019   PetscCall(DMSNESGetFunction(dm,f,ctx));
5020   PetscFunctionReturn(0);
5021 }
5022 
5023 /*@C
5024    SNESGetNGS - Returns the NGS function and context.
5025 
5026    Input Parameter:
5027 .  snes - the SNES context
5028 
5029    Output Parameters:
5030 +  f - the function (or NULL) see SNESNGSFunction for details
5031 -  ctx    - the function context (or NULL)
5032 
5033    Level: advanced
5034 
5035 .seealso: `SNESSetNGS()`, `SNESGetFunction()`
5036 @*/
5037 
5038 PetscErrorCode SNESGetNGS (SNES snes, PetscErrorCode (**f)(SNES, Vec, Vec, void*), void ** ctx)
5039 {
5040   DM             dm;
5041 
5042   PetscFunctionBegin;
5043   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5044   PetscCall(SNESGetDM(snes,&dm));
5045   PetscCall(DMSNESGetNGS(dm,f,ctx));
5046   PetscFunctionReturn(0);
5047 }
5048 
5049 /*@C
5050    SNESSetOptionsPrefix - Sets the prefix used for searching for all
5051    SNES options in the database.
5052 
5053    Logically Collective on SNES
5054 
5055    Input Parameters:
5056 +  snes - the SNES context
5057 -  prefix - the prefix to prepend to all option names
5058 
5059    Notes:
5060    A hyphen (-) must NOT be given at the beginning of the prefix name.
5061    The first character of all runtime options is AUTOMATICALLY the hyphen.
5062 
5063    Level: advanced
5064 
5065 .seealso: `SNESSetFromOptions()`
5066 @*/
5067 PetscErrorCode  SNESSetOptionsPrefix(SNES snes,const char prefix[])
5068 {
5069   PetscFunctionBegin;
5070   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5071   PetscCall(PetscObjectSetOptionsPrefix((PetscObject)snes,prefix));
5072   if (!snes->ksp) PetscCall(SNESGetKSP(snes,&snes->ksp));
5073   if (snes->linesearch) {
5074     PetscCall(SNESGetLineSearch(snes,&snes->linesearch));
5075     PetscCall(PetscObjectSetOptionsPrefix((PetscObject)snes->linesearch,prefix));
5076   }
5077   PetscCall(KSPSetOptionsPrefix(snes->ksp,prefix));
5078   PetscFunctionReturn(0);
5079 }
5080 
5081 /*@C
5082    SNESAppendOptionsPrefix - Appends to the prefix used for searching for all
5083    SNES options in the database.
5084 
5085    Logically Collective on SNES
5086 
5087    Input Parameters:
5088 +  snes - the SNES context
5089 -  prefix - the prefix to prepend to all option names
5090 
5091    Notes:
5092    A hyphen (-) must NOT be given at the beginning of the prefix name.
5093    The first character of all runtime options is AUTOMATICALLY the hyphen.
5094 
5095    Level: advanced
5096 
5097 .seealso: `SNESGetOptionsPrefix()`
5098 @*/
5099 PetscErrorCode  SNESAppendOptionsPrefix(SNES snes,const char prefix[])
5100 {
5101   PetscFunctionBegin;
5102   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5103   PetscCall(PetscObjectAppendOptionsPrefix((PetscObject)snes,prefix));
5104   if (!snes->ksp) PetscCall(SNESGetKSP(snes,&snes->ksp));
5105   if (snes->linesearch) {
5106     PetscCall(SNESGetLineSearch(snes,&snes->linesearch));
5107     PetscCall(PetscObjectAppendOptionsPrefix((PetscObject)snes->linesearch,prefix));
5108   }
5109   PetscCall(KSPAppendOptionsPrefix(snes->ksp,prefix));
5110   PetscFunctionReturn(0);
5111 }
5112 
5113 /*@C
5114    SNESGetOptionsPrefix - Sets the prefix used for searching for all
5115    SNES options in the database.
5116 
5117    Not Collective
5118 
5119    Input Parameter:
5120 .  snes - the SNES context
5121 
5122    Output Parameter:
5123 .  prefix - pointer to the prefix string used
5124 
5125    Notes:
5126     On the fortran side, the user should pass in a string 'prefix' of
5127    sufficient length to hold the prefix.
5128 
5129    Level: advanced
5130 
5131 .seealso: `SNESAppendOptionsPrefix()`
5132 @*/
5133 PetscErrorCode  SNESGetOptionsPrefix(SNES snes,const char *prefix[])
5134 {
5135   PetscFunctionBegin;
5136   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5137   PetscCall(PetscObjectGetOptionsPrefix((PetscObject)snes,prefix));
5138   PetscFunctionReturn(0);
5139 }
5140 
5141 /*@C
5142   SNESRegister - Adds a method to the nonlinear solver package.
5143 
5144    Not collective
5145 
5146    Input Parameters:
5147 +  name_solver - name of a new user-defined solver
5148 -  routine_create - routine to create method context
5149 
5150    Notes:
5151    SNESRegister() may be called multiple times to add several user-defined solvers.
5152 
5153    Sample usage:
5154 .vb
5155    SNESRegister("my_solver",MySolverCreate);
5156 .ve
5157 
5158    Then, your solver can be chosen with the procedural interface via
5159 $     SNESSetType(snes,"my_solver")
5160    or at runtime via the option
5161 $     -snes_type my_solver
5162 
5163    Level: advanced
5164 
5165     Note: If your function is not being put into a shared library then use SNESRegister() instead
5166 
5167 .seealso: `SNESRegisterAll()`, `SNESRegisterDestroy()`
5168 
5169   Level: advanced
5170 @*/
5171 PetscErrorCode  SNESRegister(const char sname[],PetscErrorCode (*function)(SNES))
5172 {
5173   PetscFunctionBegin;
5174   PetscCall(SNESInitializePackage());
5175   PetscCall(PetscFunctionListAdd(&SNESList,sname,function));
5176   PetscFunctionReturn(0);
5177 }
5178 
5179 PetscErrorCode  SNESTestLocalMin(SNES snes)
5180 {
5181   PetscInt       N,i,j;
5182   Vec            u,uh,fh;
5183   PetscScalar    value;
5184   PetscReal      norm;
5185 
5186   PetscFunctionBegin;
5187   PetscCall(SNESGetSolution(snes,&u));
5188   PetscCall(VecDuplicate(u,&uh));
5189   PetscCall(VecDuplicate(u,&fh));
5190 
5191   /* currently only works for sequential */
5192   PetscCall(PetscPrintf(PetscObjectComm((PetscObject)snes),"Testing FormFunction() for local min\n"));
5193   PetscCall(VecGetSize(u,&N));
5194   for (i=0; i<N; i++) {
5195     PetscCall(VecCopy(u,uh));
5196     PetscCall(PetscPrintf(PetscObjectComm((PetscObject)snes),"i = %" PetscInt_FMT "\n",i));
5197     for (j=-10; j<11; j++) {
5198       value = PetscSign(j)*PetscExpReal(PetscAbs(j)-10.0);
5199       PetscCall(VecSetValue(uh,i,value,ADD_VALUES));
5200       PetscCall(SNESComputeFunction(snes,uh,fh));
5201       PetscCall(VecNorm(fh,NORM_2,&norm));
5202       PetscCall(PetscPrintf(PetscObjectComm((PetscObject)snes),"       j norm %" PetscInt_FMT " %18.16e\n",j,(double)norm));
5203       value = -value;
5204       PetscCall(VecSetValue(uh,i,value,ADD_VALUES));
5205     }
5206   }
5207   PetscCall(VecDestroy(&uh));
5208   PetscCall(VecDestroy(&fh));
5209   PetscFunctionReturn(0);
5210 }
5211 
5212 /*@
5213    SNESKSPSetUseEW - Sets SNES use Eisenstat-Walker method for
5214    computing relative tolerance for linear solvers within an inexact
5215    Newton method.
5216 
5217    Logically Collective on SNES
5218 
5219    Input Parameters:
5220 +  snes - SNES context
5221 -  flag - PETSC_TRUE or PETSC_FALSE
5222 
5223     Options Database:
5224 +  -snes_ksp_ew - use Eisenstat-Walker method for determining linear system convergence
5225 .  -snes_ksp_ew_version ver - version of  Eisenstat-Walker method
5226 .  -snes_ksp_ew_rtol0 <rtol0> - Sets rtol0
5227 .  -snes_ksp_ew_rtolmax <rtolmax> - Sets rtolmax
5228 .  -snes_ksp_ew_gamma <gamma> - Sets gamma
5229 .  -snes_ksp_ew_alpha <alpha> - Sets alpha
5230 .  -snes_ksp_ew_alpha2 <alpha2> - Sets alpha2
5231 -  -snes_ksp_ew_threshold <threshold> - Sets threshold
5232 
5233    Notes:
5234    Currently, the default is to use a constant relative tolerance for
5235    the inner linear solvers.  Alternatively, one can use the
5236    Eisenstat-Walker method, where the relative convergence tolerance
5237    is reset at each Newton iteration according progress of the nonlinear
5238    solver.
5239 
5240    Level: advanced
5241 
5242    Reference:
5243    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an
5244    inexact Newton method", SISC 17 (1), pp.16-32, 1996.
5245 
5246 .seealso: `SNESKSPGetUseEW()`, `SNESKSPGetParametersEW()`, `SNESKSPSetParametersEW()`
5247 @*/
5248 PetscErrorCode  SNESKSPSetUseEW(SNES snes,PetscBool flag)
5249 {
5250   PetscFunctionBegin;
5251   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5252   PetscValidLogicalCollectiveBool(snes,flag,2);
5253   snes->ksp_ewconv = flag;
5254   PetscFunctionReturn(0);
5255 }
5256 
5257 /*@
5258    SNESKSPGetUseEW - Gets if SNES is using Eisenstat-Walker method
5259    for computing relative tolerance for linear solvers within an
5260    inexact Newton method.
5261 
5262    Not Collective
5263 
5264    Input Parameter:
5265 .  snes - SNES context
5266 
5267    Output Parameter:
5268 .  flag - PETSC_TRUE or PETSC_FALSE
5269 
5270    Notes:
5271    Currently, the default is to use a constant relative tolerance for
5272    the inner linear solvers.  Alternatively, one can use the
5273    Eisenstat-Walker method, where the relative convergence tolerance
5274    is reset at each Newton iteration according progress of the nonlinear
5275    solver.
5276 
5277    Level: advanced
5278 
5279    Reference:
5280    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an
5281    inexact Newton method", SISC 17 (1), pp.16-32, 1996.
5282 
5283 .seealso: `SNESKSPSetUseEW()`, `SNESKSPGetParametersEW()`, `SNESKSPSetParametersEW()`
5284 @*/
5285 PetscErrorCode  SNESKSPGetUseEW(SNES snes, PetscBool  *flag)
5286 {
5287   PetscFunctionBegin;
5288   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5289   PetscValidBoolPointer(flag,2);
5290   *flag = snes->ksp_ewconv;
5291   PetscFunctionReturn(0);
5292 }
5293 
5294 /*@
5295    SNESKSPSetParametersEW - Sets parameters for Eisenstat-Walker
5296    convergence criteria for the linear solvers within an inexact
5297    Newton method.
5298 
5299    Logically Collective on SNES
5300 
5301    Input Parameters:
5302 +    snes - SNES context
5303 .    version - version 1, 2 (default is 2) or 3
5304 .    rtol_0 - initial relative tolerance (0 <= rtol_0 < 1)
5305 .    rtol_max - maximum relative tolerance (0 <= rtol_max < 1)
5306 .    gamma - multiplicative factor for version 2 rtol computation
5307              (0 <= gamma2 <= 1)
5308 .    alpha - power for version 2 rtol computation (1 < alpha <= 2)
5309 .    alpha2 - power for safeguard
5310 -    threshold - threshold for imposing safeguard (0 < threshold < 1)
5311 
5312    Note:
5313    Version 3 was contributed by Luis Chacon, June 2006.
5314 
5315    Use PETSC_DEFAULT to retain the default for any of the parameters.
5316 
5317    Level: advanced
5318 
5319    Reference:
5320    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an
5321    inexact Newton method", Utah State University Math. Stat. Dept. Res.
5322    Report 6/94/75, June, 1994, to appear in SIAM J. Sci. Comput.
5323 
5324 .seealso: `SNESKSPSetUseEW()`, `SNESKSPGetUseEW()`, `SNESKSPGetParametersEW()`
5325 @*/
5326 PetscErrorCode  SNESKSPSetParametersEW(SNES snes,PetscInt version,PetscReal rtol_0,PetscReal rtol_max,PetscReal gamma,PetscReal alpha,PetscReal alpha2,PetscReal threshold)
5327 {
5328   SNESKSPEW *kctx;
5329 
5330   PetscFunctionBegin;
5331   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5332   kctx = (SNESKSPEW*)snes->kspconvctx;
5333   PetscCheck(kctx,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context existing");
5334   PetscValidLogicalCollectiveInt(snes,version,2);
5335   PetscValidLogicalCollectiveReal(snes,rtol_0,3);
5336   PetscValidLogicalCollectiveReal(snes,rtol_max,4);
5337   PetscValidLogicalCollectiveReal(snes,gamma,5);
5338   PetscValidLogicalCollectiveReal(snes,alpha,6);
5339   PetscValidLogicalCollectiveReal(snes,alpha2,7);
5340   PetscValidLogicalCollectiveReal(snes,threshold,8);
5341 
5342   if (version != PETSC_DEFAULT)   kctx->version   = version;
5343   if (rtol_0 != PETSC_DEFAULT)    kctx->rtol_0    = rtol_0;
5344   if (rtol_max != PETSC_DEFAULT)  kctx->rtol_max  = rtol_max;
5345   if (gamma != PETSC_DEFAULT)     kctx->gamma     = gamma;
5346   if (alpha != PETSC_DEFAULT)     kctx->alpha     = alpha;
5347   if (alpha2 != PETSC_DEFAULT)    kctx->alpha2    = alpha2;
5348   if (threshold != PETSC_DEFAULT) kctx->threshold = threshold;
5349 
5350   PetscCheck(kctx->version >= 1 && kctx->version <= 3,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Only versions 1, 2 and 3 are supported: %" PetscInt_FMT,kctx->version);
5351   PetscCheck(kctx->rtol_0 >= 0.0 && kctx->rtol_0 < 1.0,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= rtol_0 < 1.0: %g",(double)kctx->rtol_0);
5352   PetscCheck(kctx->rtol_max >= 0.0 && kctx->rtol_max < 1.0,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= rtol_max (%g) < 1.0",(double)kctx->rtol_max);
5353   PetscCheck(kctx->gamma >= 0.0 && kctx->gamma <= 1.0,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= gamma (%g) <= 1.0",(double)kctx->gamma);
5354   PetscCheck(kctx->alpha > 1.0 && kctx->alpha <= 2.0,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"1.0 < alpha (%g) <= 2.0",(double)kctx->alpha);
5355   PetscCheck(kctx->threshold > 0.0 && kctx->threshold < 1.0,PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"0.0 < threshold (%g) < 1.0",(double)kctx->threshold);
5356   PetscFunctionReturn(0);
5357 }
5358 
5359 /*@
5360    SNESKSPGetParametersEW - Gets parameters for Eisenstat-Walker
5361    convergence criteria for the linear solvers within an inexact
5362    Newton method.
5363 
5364    Not Collective
5365 
5366    Input Parameter:
5367 .    snes - SNES context
5368 
5369    Output Parameters:
5370 +    version - version 1, 2 (default is 2) or 3
5371 .    rtol_0 - initial relative tolerance (0 <= rtol_0 < 1)
5372 .    rtol_max - maximum relative tolerance (0 <= rtol_max < 1)
5373 .    gamma - multiplicative factor for version 2 rtol computation (0 <= gamma2 <= 1)
5374 .    alpha - power for version 2 rtol computation (1 < alpha <= 2)
5375 .    alpha2 - power for safeguard
5376 -    threshold - threshold for imposing safeguard (0 < threshold < 1)
5377 
5378    Level: advanced
5379 
5380 .seealso: `SNESKSPSetUseEW()`, `SNESKSPGetUseEW()`, `SNESKSPSetParametersEW()`
5381 @*/
5382 PetscErrorCode  SNESKSPGetParametersEW(SNES snes,PetscInt *version,PetscReal *rtol_0,PetscReal *rtol_max,PetscReal *gamma,PetscReal *alpha,PetscReal *alpha2,PetscReal *threshold)
5383 {
5384   SNESKSPEW *kctx;
5385 
5386   PetscFunctionBegin;
5387   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5388   kctx = (SNESKSPEW*)snes->kspconvctx;
5389   PetscCheck(kctx,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context existing");
5390   if (version)   *version   = kctx->version;
5391   if (rtol_0)    *rtol_0    = kctx->rtol_0;
5392   if (rtol_max)  *rtol_max  = kctx->rtol_max;
5393   if (gamma)     *gamma     = kctx->gamma;
5394   if (alpha)     *alpha     = kctx->alpha;
5395   if (alpha2)    *alpha2    = kctx->alpha2;
5396   if (threshold) *threshold = kctx->threshold;
5397   PetscFunctionReturn(0);
5398 }
5399 
5400  PetscErrorCode KSPPreSolve_SNESEW(KSP ksp, Vec b, Vec x, SNES snes)
5401 {
5402   SNESKSPEW      *kctx = (SNESKSPEW*)snes->kspconvctx;
5403   PetscReal      rtol  = PETSC_DEFAULT,stol;
5404 
5405   PetscFunctionBegin;
5406   if (!snes->ksp_ewconv) PetscFunctionReturn(0);
5407   if (!snes->iter) {
5408     rtol = kctx->rtol_0; /* first time in, so use the original user rtol */
5409     PetscCall(VecNorm(snes->vec_func,NORM_2,&kctx->norm_first));
5410   }
5411   else {
5412     if (kctx->version == 1) {
5413       rtol = (snes->norm - kctx->lresid_last)/kctx->norm_last;
5414       if (rtol < 0.0) rtol = -rtol;
5415       stol = PetscPowReal(kctx->rtol_last,kctx->alpha2);
5416       if (stol > kctx->threshold) rtol = PetscMax(rtol,stol);
5417     } else if (kctx->version == 2) {
5418       rtol = kctx->gamma * PetscPowReal(snes->norm/kctx->norm_last,kctx->alpha);
5419       stol = kctx->gamma * PetscPowReal(kctx->rtol_last,kctx->alpha);
5420       if (stol > kctx->threshold) rtol = PetscMax(rtol,stol);
5421     } else if (kctx->version == 3) { /* contributed by Luis Chacon, June 2006. */
5422       rtol = kctx->gamma * PetscPowReal(snes->norm/kctx->norm_last,kctx->alpha);
5423       /* safeguard: avoid sharp decrease of rtol */
5424       stol = kctx->gamma*PetscPowReal(kctx->rtol_last,kctx->alpha);
5425       stol = PetscMax(rtol,stol);
5426       rtol = PetscMin(kctx->rtol_0,stol);
5427       /* safeguard: avoid oversolving */
5428       stol = kctx->gamma*(kctx->norm_first*snes->rtol)/snes->norm;
5429       stol = PetscMax(rtol,stol);
5430       rtol = PetscMin(kctx->rtol_0,stol);
5431     } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Only versions 1, 2 or 3 are supported: %" PetscInt_FMT,kctx->version);
5432   }
5433   /* safeguard: avoid rtol greater than one */
5434   rtol = PetscMin(rtol,kctx->rtol_max);
5435   PetscCall(KSPSetTolerances(ksp,rtol,PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT));
5436   PetscCall(PetscInfo(snes,"iter %" PetscInt_FMT ", Eisenstat-Walker (version %" PetscInt_FMT ") KSP rtol=%g\n",snes->iter,kctx->version,(double)rtol));
5437   PetscFunctionReturn(0);
5438 }
5439 
5440 PetscErrorCode KSPPostSolve_SNESEW(KSP ksp, Vec b, Vec x, SNES snes)
5441 {
5442   SNESKSPEW      *kctx = (SNESKSPEW*)snes->kspconvctx;
5443   PCSide         pcside;
5444   Vec            lres;
5445 
5446   PetscFunctionBegin;
5447   if (!snes->ksp_ewconv) PetscFunctionReturn(0);
5448   PetscCall(KSPGetTolerances(ksp,&kctx->rtol_last,NULL,NULL,NULL));
5449   kctx->norm_last = snes->norm;
5450   if (kctx->version == 1) {
5451     PC        pc;
5452     PetscBool isNone;
5453 
5454     PetscCall(KSPGetPC(ksp, &pc));
5455     PetscCall(PetscObjectTypeCompare((PetscObject) pc, PCNONE, &isNone));
5456     PetscCall(KSPGetPCSide(ksp,&pcside));
5457      if (pcside == PC_RIGHT || isNone) { /* XXX Should we also test KSP_UNPRECONDITIONED_NORM ? */
5458       /* KSP residual is true linear residual */
5459       PetscCall(KSPGetResidualNorm(ksp,&kctx->lresid_last));
5460     } else {
5461       /* KSP residual is preconditioned residual */
5462       /* compute true linear residual norm */
5463       PetscCall(VecDuplicate(b,&lres));
5464       PetscCall(MatMult(snes->jacobian,x,lres));
5465       PetscCall(VecAYPX(lres,-1.0,b));
5466       PetscCall(VecNorm(lres,NORM_2,&kctx->lresid_last));
5467       PetscCall(VecDestroy(&lres));
5468     }
5469   }
5470   PetscFunctionReturn(0);
5471 }
5472 
5473 /*@
5474    SNESGetKSP - Returns the KSP context for a SNES solver.
5475 
5476    Not Collective, but if SNES object is parallel, then KSP object is parallel
5477 
5478    Input Parameter:
5479 .  snes - the SNES context
5480 
5481    Output Parameter:
5482 .  ksp - the KSP context
5483 
5484    Notes:
5485    The user can then directly manipulate the KSP context to set various
5486    options, etc.  Likewise, the user can then extract and manipulate the
5487    PC contexts as well.
5488 
5489    Level: beginner
5490 
5491 .seealso: `KSPGetPC()`, `SNESCreate()`, `KSPCreate()`, `SNESSetKSP()`
5492 @*/
5493 PetscErrorCode  SNESGetKSP(SNES snes,KSP *ksp)
5494 {
5495   PetscFunctionBegin;
5496   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5497   PetscValidPointer(ksp,2);
5498 
5499   if (!snes->ksp) {
5500     PetscCall(KSPCreate(PetscObjectComm((PetscObject)snes),&snes->ksp));
5501     PetscCall(PetscObjectIncrementTabLevel((PetscObject)snes->ksp,(PetscObject)snes,1));
5502     PetscCall(PetscLogObjectParent((PetscObject)snes,(PetscObject)snes->ksp));
5503 
5504     PetscCall(KSPSetPreSolve(snes->ksp,(PetscErrorCode (*)(KSP,Vec,Vec,void*))KSPPreSolve_SNESEW,snes));
5505     PetscCall(KSPSetPostSolve(snes->ksp,(PetscErrorCode (*)(KSP,Vec,Vec,void*))KSPPostSolve_SNESEW,snes));
5506 
5507     PetscCall(KSPMonitorSetFromOptions(snes->ksp, "-snes_monitor_ksp", "snes_preconditioned_residual", snes));
5508     PetscCall(PetscObjectSetOptions((PetscObject)snes->ksp,((PetscObject)snes)->options));
5509   }
5510   *ksp = snes->ksp;
5511   PetscFunctionReturn(0);
5512 }
5513 
5514 #include <petsc/private/dmimpl.h>
5515 /*@
5516    SNESSetDM - Sets the DM that may be used by some nonlinear solvers or their underlying preconditioners
5517 
5518    Logically Collective on SNES
5519 
5520    Input Parameters:
5521 +  snes - the nonlinear solver context
5522 -  dm - the dm, cannot be NULL
5523 
5524    Notes:
5525    A DM can only be used for solving one problem at a time because information about the problem is stored on the DM,
5526    even when not using interfaces like DMSNESSetFunction().  Use DMClone() to get a distinct DM when solving different
5527    problems using the same function space.
5528 
5529    Level: intermediate
5530 
5531 .seealso: `SNESGetDM()`, `KSPSetDM()`, `KSPGetDM()`
5532 @*/
5533 PetscErrorCode  SNESSetDM(SNES snes,DM dm)
5534 {
5535   KSP            ksp;
5536   DMSNES         sdm;
5537 
5538   PetscFunctionBegin;
5539   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5540   PetscValidHeaderSpecific(dm,DM_CLASSID,2);
5541   PetscCall(PetscObjectReference((PetscObject)dm));
5542   if (snes->dm) {               /* Move the DMSNES context over to the new DM unless the new DM already has one */
5543     if (snes->dm->dmsnes && !dm->dmsnes) {
5544       PetscCall(DMCopyDMSNES(snes->dm,dm));
5545       PetscCall(DMGetDMSNES(snes->dm,&sdm));
5546       if (sdm->originaldm == snes->dm) sdm->originaldm = dm; /* Grant write privileges to the replacement DM */
5547     }
5548     PetscCall(DMCoarsenHookRemove(snes->dm,DMCoarsenHook_SNESVecSol,DMRestrictHook_SNESVecSol,snes));
5549     PetscCall(DMDestroy(&snes->dm));
5550   }
5551   snes->dm     = dm;
5552   snes->dmAuto = PETSC_FALSE;
5553 
5554   PetscCall(SNESGetKSP(snes,&ksp));
5555   PetscCall(KSPSetDM(ksp,dm));
5556   PetscCall(KSPSetDMActive(ksp,PETSC_FALSE));
5557   if (snes->npc) {
5558     PetscCall(SNESSetDM(snes->npc,snes->dm));
5559     PetscCall(SNESSetNPCSide(snes,snes->npcside));
5560   }
5561   PetscFunctionReturn(0);
5562 }
5563 
5564 /*@
5565    SNESGetDM - Gets the DM that may be used by some preconditioners
5566 
5567    Not Collective but DM obtained is parallel on SNES
5568 
5569    Input Parameter:
5570 . snes - the preconditioner context
5571 
5572    Output Parameter:
5573 .  dm - the dm
5574 
5575    Level: intermediate
5576 
5577 .seealso: `SNESSetDM()`, `KSPSetDM()`, `KSPGetDM()`
5578 @*/
5579 PetscErrorCode  SNESGetDM(SNES snes,DM *dm)
5580 {
5581   PetscFunctionBegin;
5582   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5583   if (!snes->dm) {
5584     PetscCall(DMShellCreate(PetscObjectComm((PetscObject)snes),&snes->dm));
5585     snes->dmAuto = PETSC_TRUE;
5586   }
5587   *dm = snes->dm;
5588   PetscFunctionReturn(0);
5589 }
5590 
5591 /*@
5592   SNESSetNPC - Sets the nonlinear preconditioner to be used.
5593 
5594   Collective on SNES
5595 
5596   Input Parameters:
5597 + snes - iterative context obtained from SNESCreate()
5598 - pc   - the preconditioner object
5599 
5600   Notes:
5601   Use SNESGetNPC() to retrieve the preconditioner context (for example,
5602   to configure it using the API).
5603 
5604   Level: developer
5605 
5606 .seealso: `SNESGetNPC()`, `SNESHasNPC()`
5607 @*/
5608 PetscErrorCode SNESSetNPC(SNES snes, SNES pc)
5609 {
5610   PetscFunctionBegin;
5611   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
5612   PetscValidHeaderSpecific(pc, SNES_CLASSID, 2);
5613   PetscCheckSameComm(snes, 1, pc, 2);
5614   PetscCall(PetscObjectReference((PetscObject) pc));
5615   PetscCall(SNESDestroy(&snes->npc));
5616   snes->npc = pc;
5617   PetscCall(PetscLogObjectParent((PetscObject)snes, (PetscObject)snes->npc));
5618   PetscFunctionReturn(0);
5619 }
5620 
5621 /*@
5622   SNESGetNPC - Creates a nonlinear preconditioning solver (SNES) to be used to precondition the nonlinear solver.
5623 
5624   Not Collective; but any changes to the obtained SNES object must be applied collectively
5625 
5626   Input Parameter:
5627 . snes - iterative context obtained from SNESCreate()
5628 
5629   Output Parameter:
5630 . pc - preconditioner context
5631 
5632   Options Database:
5633 . -npc_snes_type <type> - set the type of the SNES to use as the nonlinear preconditioner
5634 
5635   Notes:
5636     If a SNES was previously set with SNESSetNPC() then that SNES is returned, otherwise a new SNES object is created.
5637 
5638     The (preconditioner) SNES returned automatically inherits the same nonlinear function and Jacobian supplied to the original
5639     SNES during SNESSetUp()
5640 
5641   Level: developer
5642 
5643 .seealso: `SNESSetNPC()`, `SNESHasNPC()`, `SNES`, `SNESCreate()`
5644 @*/
5645 PetscErrorCode SNESGetNPC(SNES snes, SNES *pc)
5646 {
5647   const char     *optionsprefix;
5648 
5649   PetscFunctionBegin;
5650   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
5651   PetscValidPointer(pc, 2);
5652   if (!snes->npc) {
5653     PetscCall(SNESCreate(PetscObjectComm((PetscObject)snes),&snes->npc));
5654     PetscCall(PetscObjectIncrementTabLevel((PetscObject)snes->npc,(PetscObject)snes,1));
5655     PetscCall(PetscLogObjectParent((PetscObject)snes,(PetscObject)snes->npc));
5656     PetscCall(SNESGetOptionsPrefix(snes,&optionsprefix));
5657     PetscCall(SNESSetOptionsPrefix(snes->npc,optionsprefix));
5658     PetscCall(SNESAppendOptionsPrefix(snes->npc,"npc_"));
5659     PetscCall(SNESSetCountersReset(snes->npc,PETSC_FALSE));
5660   }
5661   *pc = snes->npc;
5662   PetscFunctionReturn(0);
5663 }
5664 
5665 /*@
5666   SNESHasNPC - Returns whether a nonlinear preconditioner exists
5667 
5668   Not Collective
5669 
5670   Input Parameter:
5671 . snes - iterative context obtained from SNESCreate()
5672 
5673   Output Parameter:
5674 . has_npc - whether the SNES has an NPC or not
5675 
5676   Level: developer
5677 
5678 .seealso: `SNESSetNPC()`, `SNESGetNPC()`
5679 @*/
5680 PetscErrorCode SNESHasNPC(SNES snes, PetscBool *has_npc)
5681 {
5682   PetscFunctionBegin;
5683   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
5684   *has_npc = (PetscBool) (snes->npc ? PETSC_TRUE : PETSC_FALSE);
5685   PetscFunctionReturn(0);
5686 }
5687 
5688 /*@
5689     SNESSetNPCSide - Sets the preconditioning side.
5690 
5691     Logically Collective on SNES
5692 
5693     Input Parameter:
5694 .   snes - iterative context obtained from SNESCreate()
5695 
5696     Output Parameter:
5697 .   side - the preconditioning side, where side is one of
5698 .vb
5699       PC_LEFT - left preconditioning
5700       PC_RIGHT - right preconditioning (default for most nonlinear solvers)
5701 .ve
5702 
5703     Options Database Keys:
5704 .   -snes_npc_side <right,left> - nonlinear preconditioner side
5705 
5706     Notes:
5707     SNESNRICHARDSON and SNESNCG only support left preconditioning.
5708 
5709     Level: intermediate
5710 
5711 .seealso: `SNESGetNPCSide()`, `KSPSetPCSide()`
5712 @*/
5713 PetscErrorCode  SNESSetNPCSide(SNES snes,PCSide side)
5714 {
5715   PetscFunctionBegin;
5716   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5717   PetscValidLogicalCollectiveEnum(snes,side,2);
5718   if (side == PC_SIDE_DEFAULT) side = PC_RIGHT;
5719   PetscCheck((side == PC_LEFT) || (side == PC_RIGHT),PetscObjectComm((PetscObject)snes),PETSC_ERR_ARG_WRONG,"Only PC_LEFT and PC_RIGHT are supported");
5720   snes->npcside = side;
5721   PetscFunctionReturn(0);
5722 }
5723 
5724 /*@
5725     SNESGetNPCSide - Gets the preconditioning side.
5726 
5727     Not Collective
5728 
5729     Input Parameter:
5730 .   snes - iterative context obtained from SNESCreate()
5731 
5732     Output Parameter:
5733 .   side - the preconditioning side, where side is one of
5734 .vb
5735       PC_LEFT - left preconditioning
5736       PC_RIGHT - right preconditioning (default for most nonlinear solvers)
5737 .ve
5738 
5739     Level: intermediate
5740 
5741 .seealso: `SNESSetNPCSide()`, `KSPGetPCSide()`
5742 @*/
5743 PetscErrorCode  SNESGetNPCSide(SNES snes,PCSide *side)
5744 {
5745   PetscFunctionBegin;
5746   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
5747   PetscValidPointer(side,2);
5748   *side = snes->npcside;
5749   PetscFunctionReturn(0);
5750 }
5751 
5752 /*@
5753   SNESSetLineSearch - Sets the linesearch on the SNES instance.
5754 
5755   Collective on SNES
5756 
5757   Input Parameters:
5758 + snes - iterative context obtained from SNESCreate()
5759 - linesearch   - the linesearch object
5760 
5761   Notes:
5762   Use SNESGetLineSearch() to retrieve the preconditioner context (for example,
5763   to configure it using the API).
5764 
5765   Level: developer
5766 
5767 .seealso: `SNESGetLineSearch()`
5768 @*/
5769 PetscErrorCode SNESSetLineSearch(SNES snes, SNESLineSearch linesearch)
5770 {
5771   PetscFunctionBegin;
5772   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
5773   PetscValidHeaderSpecific(linesearch, SNESLINESEARCH_CLASSID, 2);
5774   PetscCheckSameComm(snes, 1, linesearch, 2);
5775   PetscCall(PetscObjectReference((PetscObject) linesearch));
5776   PetscCall(SNESLineSearchDestroy(&snes->linesearch));
5777 
5778   snes->linesearch = linesearch;
5779 
5780   PetscCall(PetscLogObjectParent((PetscObject)snes, (PetscObject)snes->linesearch));
5781   PetscFunctionReturn(0);
5782 }
5783 
5784 /*@
5785   SNESGetLineSearch - Returns a pointer to the line search context set with SNESSetLineSearch()
5786   or creates a default line search instance associated with the SNES and returns it.
5787 
5788   Not Collective
5789 
5790   Input Parameter:
5791 . snes - iterative context obtained from SNESCreate()
5792 
5793   Output Parameter:
5794 . linesearch - linesearch context
5795 
5796   Level: beginner
5797 
5798 .seealso: `SNESSetLineSearch()`, `SNESLineSearchCreate()`
5799 @*/
5800 PetscErrorCode SNESGetLineSearch(SNES snes, SNESLineSearch *linesearch)
5801 {
5802   const char     *optionsprefix;
5803 
5804   PetscFunctionBegin;
5805   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
5806   PetscValidPointer(linesearch, 2);
5807   if (!snes->linesearch) {
5808     PetscCall(SNESGetOptionsPrefix(snes, &optionsprefix));
5809     PetscCall(SNESLineSearchCreate(PetscObjectComm((PetscObject)snes), &snes->linesearch));
5810     PetscCall(SNESLineSearchSetSNES(snes->linesearch, snes));
5811     PetscCall(SNESLineSearchAppendOptionsPrefix(snes->linesearch, optionsprefix));
5812     PetscCall(PetscObjectIncrementTabLevel((PetscObject) snes->linesearch, (PetscObject) snes, 1));
5813     PetscCall(PetscLogObjectParent((PetscObject)snes, (PetscObject)snes->linesearch));
5814   }
5815   *linesearch = snes->linesearch;
5816   PetscFunctionReturn(0);
5817 }
5818