Actual source code: snes.c

  1: #define PETSCSNES_DLL

 3:  #include include/private/snesimpl.h

  5: PetscTruth SNESRegisterAllCalled = PETSC_FALSE;
  6: PetscFList SNESList              = PETSC_NULL;

  8: /* Logging support */
  9: PetscCookie  SNES_COOKIE = 0;
 10: PetscEvent  SNES_Solve = 0, SNES_LineSearch = 0, SNES_FunctionEval = 0, SNES_JacobianEval = 0;

 14: /*@C
 15:    SNESView - Prints the SNES data structure.

 17:    Collective on SNES

 19:    Input Parameters:
 20: +  SNES - the SNES context
 21: -  viewer - visualization context

 23:    Options Database Key:
 24: .  -snes_view - Calls SNESView() at end of SNESSolve()

 26:    Notes:
 27:    The available visualization contexts include
 28: +     PETSC_VIEWER_STDOUT_SELF - standard output (default)
 29: -     PETSC_VIEWER_STDOUT_WORLD - synchronized standard
 30:          output where only the first processor opens
 31:          the file.  All other processors send their 
 32:          data to the first processor to print. 

 34:    The user can open an alternative visualization context with
 35:    PetscViewerASCIIOpen() - output to a specified file.

 37:    Level: beginner

 39: .keywords: SNES, view

 41: .seealso: PetscViewerASCIIOpen()
 42: @*/
 43: PetscErrorCode  SNESView(SNES snes,PetscViewer viewer)
 44: {
 45:   SNESKSPEW           *kctx;
 46:   PetscErrorCode      ierr;
 47:   KSP                 ksp;
 48:   SNESType            type;
 49:   PetscTruth          iascii,isstring;

 53:   if (!viewer) {
 54:     PetscViewerASCIIGetStdout(((PetscObject)snes)->comm,&viewer);
 55:   }

 59:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);
 60:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_STRING,&isstring);
 61:   if (iascii) {
 62:     if (((PetscObject)snes)->prefix) {
 63:       PetscViewerASCIIPrintf(viewer,"SNES Object:(%s)\n",((PetscObject)snes)->prefix);
 64:     } else {
 65:       PetscViewerASCIIPrintf(viewer,"SNES Object:\n");
 66:     }
 67:     SNESGetType(snes,&type);
 68:     if (type) {
 69:       PetscViewerASCIIPrintf(viewer,"  type: %s\n",type);
 70:     } else {
 71:       PetscViewerASCIIPrintf(viewer,"  type: not set yet\n");
 72:     }
 73:     if (snes->ops->view) {
 74:       PetscViewerASCIIPushTab(viewer);
 75:       (*snes->ops->view)(snes,viewer);
 76:       PetscViewerASCIIPopTab(viewer);
 77:     }
 78:     PetscViewerASCIIPrintf(viewer,"  maximum iterations=%D, maximum function evaluations=%D\n",snes->max_its,snes->max_funcs);
 79:     PetscViewerASCIIPrintf(viewer,"  tolerances: relative=%G, absolute=%G, solution=%G\n",
 80:                  snes->rtol,snes->abstol,snes->xtol);
 81:     PetscViewerASCIIPrintf(viewer,"  total number of linear solver iterations=%D\n",snes->linear_its);
 82:     PetscViewerASCIIPrintf(viewer,"  total number of function evaluations=%D\n",snes->nfuncs);
 83:     if (snes->ksp_ewconv) {
 84:       kctx = (SNESKSPEW *)snes->kspconvctx;
 85:       if (kctx) {
 86:         PetscViewerASCIIPrintf(viewer,"  Eisenstat-Walker computation of KSP relative tolerance (version %D)\n",kctx->version);
 87:         PetscViewerASCIIPrintf(viewer,"    rtol_0=%G, rtol_max=%G, threshold=%G\n",kctx->rtol_0,kctx->rtol_max,kctx->threshold);
 88:         PetscViewerASCIIPrintf(viewer,"    gamma=%G, alpha=%G, alpha2=%G\n",kctx->gamma,kctx->alpha,kctx->alpha2);
 89:       }
 90:     }
 91:   } else if (isstring) {
 92:     SNESGetType(snes,&type);
 93:     PetscViewerStringSPrintf(viewer," %-3.3s",type);
 94:   }
 95:   SNESGetKSP(snes,&ksp);
 96:   PetscViewerASCIIPushTab(viewer);
 97:   KSPView(ksp,viewer);
 98:   PetscViewerASCIIPopTab(viewer);
 99:   return(0);
100: }

102: /*
103:   We retain a list of functions that also take SNES command 
104:   line options. These are called at the end SNESSetFromOptions()
105: */
106: #define MAXSETFROMOPTIONS 5
107: static PetscInt numberofsetfromoptions;
108: static PetscErrorCode (*othersetfromoptions[MAXSETFROMOPTIONS])(SNES);

112: /*@C
113:   SNESAddOptionsChecker - Adds an additional function to check for SNES options.

115:   Not Collective

117:   Input Parameter:
118: . snescheck - function that checks for options

120:   Level: developer

122: .seealso: SNESSetFromOptions()
123: @*/
124: PetscErrorCode  SNESAddOptionsChecker(PetscErrorCode (*snescheck)(SNES))
125: {
127:   if (numberofsetfromoptions >= MAXSETFROMOPTIONS) {
128:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE, "Too many options checkers, only %D allowed", MAXSETFROMOPTIONS);
129:   }
130:   othersetfromoptions[numberofsetfromoptions++] = snescheck;
131:   return(0);
132: }

136: /*@
137:    SNESSetFromOptions - Sets various SNES and KSP parameters from user options.

139:    Collective on SNES

141:    Input Parameter:
142: .  snes - the SNES context

144:    Options Database Keys:
145: +  -snes_type <type> - ls, tr, umls, umtr, test
146: .  -snes_stol - convergence tolerance in terms of the norm
147:                 of the change in the solution between steps
148: .  -snes_atol <abstol> - absolute tolerance of residual norm
149: .  -snes_rtol <rtol> - relative decrease in tolerance norm from initial
150: .  -snes_max_it <max_it> - maximum number of iterations
151: .  -snes_max_funcs <max_funcs> - maximum number of function evaluations
152: .  -snes_max_fail <max_fail> - maximum number of failures
153: .  -snes_trtol <trtol> - trust region tolerance
154: .  -snes_no_convergence_test - skip convergence test in nonlinear 
155:                                solver; hence iterations will continue until max_it
156:                                or some other criterion is reached. Saves expense
157:                                of convergence test
158: .  -snes_monitor <optional filename> - prints residual norm at each iteration. if no
159:                                        filename given prints to stdout
160: .  -snes_monitor_solution - plots solution at each iteration
161: .  -snes_monitor_residual - plots residual (not its norm) at each iteration
162: .  -snes_monitor_solution_update - plots update to solution at each iteration 
163: .  -snes_monitor_draw - plots residual norm at each iteration 
164: .  -snes_fd - use finite differences to compute Jacobian; very slow, only for testing
165: .  -snes_mf_ksp_monitor - if using matrix-free multiply then print h at each KSP iteration
166: -  -snes_converged_reason - print the reason for convergence/divergence after each solve

168:     Options Database for Eisenstat-Walker method:
169: +  -snes_ksp_ew - use Eisenstat-Walker method for determining linear system convergence
170: .  -snes_ksp_ew_version ver - version of  Eisenstat-Walker method
171: .  -snes_ksp_ew_rtol0 <rtol0> - Sets rtol0
172: .  -snes_ksp_ew_rtolmax <rtolmax> - Sets rtolmax
173: .  -snes_ksp_ew_gamma <gamma> - Sets gamma
174: .  -snes_ksp_ew_alpha <alpha> - Sets alpha
175: .  -snes_ksp_ew_alpha2 <alpha2> - Sets alpha2 
176: -  -snes_ksp_ew_threshold <threshold> - Sets threshold

178:    Notes:
179:    To see all options, run your program with the -help option or consult
180:    the users manual.

182:    Level: beginner

184: .keywords: SNES, nonlinear, set, options, database

186: .seealso: SNESSetOptionsPrefix()
187: @*/
188: PetscErrorCode  SNESSetFromOptions(SNES snes)
189: {
190:   PetscTruth              flg;
191:   PetscInt                i,indx;
192:   const char              *deft = SNESLS;
193:   const char              *convtests[] = {"default","skip"};
194:   SNESKSPEW               *kctx = NULL;
195:   char                    type[256], monfilename[PETSC_MAX_PATH_LEN];
196:   PetscViewerASCIIMonitor monviewer;
197:   PetscErrorCode          ierr;


202:   PetscOptionsBegin(((PetscObject)snes)->comm,((PetscObject)snes)->prefix,"Nonlinear solver (SNES) options","SNES");
203:     if (!SNESRegisterAllCalled) {SNESRegisterAll(PETSC_NULL);}
204:     if (((PetscObject)snes)->type_name) { deft = ((PetscObject)snes)->type_name; }
205:     PetscOptionsList("-snes_type","Nonlinear solver method","SNESSetType",SNESList,deft,type,256,&flg);
206:     if (flg) {
207:       SNESSetType(snes,type);
208:     } else if (!((PetscObject)snes)->type_name) {
209:       SNESSetType(snes,deft);
210:     }
211:     PetscOptionsName("-snes_view","Print detailed information on solver used","SNESView",0);

213:     PetscOptionsReal("-snes_stol","Stop if step length less then","SNESSetTolerances",snes->xtol,&snes->xtol,0);
214:     PetscOptionsReal("-snes_atol","Stop if function norm less then","SNESSetTolerances",snes->abstol,&snes->abstol,0);

216:     PetscOptionsReal("-snes_rtol","Stop if decrease in function norm less then","SNESSetTolerances",snes->rtol,&snes->rtol,0);
217:     PetscOptionsInt("-snes_max_it","Maximum iterations","SNESSetTolerances",snes->max_its,&snes->max_its,PETSC_NULL);
218:     PetscOptionsInt("-snes_max_funcs","Maximum function evaluations","SNESSetTolerances",snes->max_funcs,&snes->max_funcs,PETSC_NULL);
219:     PetscOptionsInt("-snes_max_fail","Maximum failures","SNESSetTolerances",snes->maxFailures,&snes->maxFailures,PETSC_NULL);

221:     PetscOptionsEList("-snes_convergence_test","Convergence test","SNESSetConvergenceTest",convtests,2,"default",&indx,&flg);
222:     if (flg) {
223:       switch (indx) {
224:       case 0: SNESSetConvergenceTest(snes,SNESDefaultConverged,PETSC_NULL); break;
225:       case 1: SNESSetConvergenceTest(snes,SNESSkipConverged,PETSC_NULL);    break;
226:       }
227:     }

229:     PetscOptionsName("-snes_converged_reason","Print reason for converged or diverged","SNESSolve",&flg);
230:     if (flg) {
231:       snes->printreason = PETSC_TRUE;
232:     }

234:     kctx = (SNESKSPEW *)snes->kspconvctx;

236:     PetscOptionsTruth("-snes_ksp_ew","Use Eisentat-Walker linear system convergence test","SNESKSPSetUseEW",snes->ksp_ewconv,&snes->ksp_ewconv,PETSC_NULL);

238:     PetscOptionsInt("-snes_ksp_ew_version","Version 1, 2 or 3","SNESKSPSetParametersEW",kctx->version,&kctx->version,0);
239:     PetscOptionsReal("-snes_ksp_ew_rtol0","0 <= rtol0 < 1","SNESKSPSetParametersEW",kctx->rtol_0,&kctx->rtol_0,0);
240:     PetscOptionsReal("-snes_ksp_ew_rtolmax","0 <= rtolmax < 1","SNESKSPSetParametersEW",kctx->rtol_max,&kctx->rtol_max,0);
241:     PetscOptionsReal("-snes_ksp_ew_gamma","0 <= gamma <= 1","SNESKSPSetParametersEW",kctx->gamma,&kctx->gamma,0);
242:     PetscOptionsReal("-snes_ksp_ew_alpha","1 < alpha <= 2","SNESKSPSetParametersEW",kctx->alpha,&kctx->alpha,0);
243:     PetscOptionsReal("-snes_ksp_ew_alpha2","alpha2","SNESKSPSetParametersEW",kctx->alpha2,&kctx->alpha2,0);
244:     PetscOptionsReal("-snes_ksp_ew_threshold","0 < threshold < 1","SNESKSPSetParametersEW",kctx->threshold,&kctx->threshold,0);

246:     PetscOptionsName("-snes_monitor_cancel","Remove all monitors","SNESMonitorCancel",&flg);
247:     if (flg) {SNESMonitorCancel(snes);}

249:     PetscOptionsString("-snes_monitor","Monitor norm of function","SNESMonitorSet","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);
250:     if (flg) {
251:       PetscViewerASCIIMonitorCreate(((PetscObject)snes)->comm,monfilename,0,&monviewer);
252:       SNESMonitorSet(snes,SNESMonitorDefault,monviewer,(PetscErrorCode (*)(void*))PetscViewerASCIIMonitorDestroy);
253:     }

255:     PetscOptionsString("-snes_ratiomonitor","Monitor ratios of norms of function","SNESMonitorSetRatio","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);
256:     if (flg) {
257:       PetscViewerASCIIMonitorCreate(((PetscObject)snes)->comm,monfilename,0,&monviewer);
258:       SNESMonitorSetRatio(snes,monviewer);
259:     }

261:     PetscOptionsString("-snes_monitor_short","Monitor norm of function (fewer digits)","SNESMonitorSet","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);
262:     if (flg) {
263:       PetscViewerASCIIMonitorCreate(((PetscObject)snes)->comm,monfilename,0,&monviewer);
264:       SNESMonitorSet(snes,SNESMonitorDefaultShort,monviewer,(PetscErrorCode (*)(void*))PetscViewerASCIIMonitorDestroy);
265:     }

267:     PetscOptionsName("-snes_monitor_solution","Plot solution at each iteration","SNESMonitorSolution",&flg);
268:     if (flg) {SNESMonitorSet(snes,SNESMonitorSolution,0,0);}
269:     PetscOptionsName("-snes_monitor_solution_update","Plot correction at each iteration","SNESMonitorSolutionUpdate",&flg);
270:     if (flg) {SNESMonitorSet(snes,SNESMonitorSolutionUpdate,0,0);}
271:     PetscOptionsName("-snes_monitor_residual","Plot residual at each iteration","SNESMonitorResidual",&flg);
272:     if (flg) {SNESMonitorSet(snes,SNESMonitorResidual,0,0);}
273:     PetscOptionsName("-snes_monitor_draw","Plot function norm at each iteration","SNESMonitorLG",&flg);
274:     if (flg) {SNESMonitorSet(snes,SNESMonitorLG,PETSC_NULL,PETSC_NULL);}

276:     PetscOptionsName("-snes_fd","Use finite differences (slow) to compute Jacobian","SNESDefaultComputeJacobian",&flg);
277:     if (flg) {
278:       SNESSetJacobian(snes,snes->jacobian,snes->jacobian_pre,SNESDefaultComputeJacobian,snes->funP);
279:       PetscInfo(snes,"Setting default finite difference Jacobian matrix\n");
280:     }

282:     for(i = 0; i < numberofsetfromoptions; i++) {
283:       (*othersetfromoptions[i])(snes);
284:     }

286:     if (snes->ops->setfromoptions) {
287:       (*snes->ops->setfromoptions)(snes);
288:     }
289:   PetscOptionsEnd();

291:   KSPSetFromOptions(snes->ksp);

293:   return(0);
294: }


299: /*@
300:    SNESSetApplicationContext - Sets the optional user-defined context for 
301:    the nonlinear solvers.  

303:    Collective on SNES

305:    Input Parameters:
306: +  snes - the SNES context
307: -  usrP - optional user context

309:    Level: intermediate

311: .keywords: SNES, nonlinear, set, application, context

313: .seealso: SNESGetApplicationContext()
314: @*/
315: PetscErrorCode  SNESSetApplicationContext(SNES snes,void *usrP)
316: {
319:   snes->user                = usrP;
320:   return(0);
321: }

325: /*@C
326:    SNESGetApplicationContext - Gets the user-defined context for the 
327:    nonlinear solvers.  

329:    Not Collective

331:    Input Parameter:
332: .  snes - SNES context

334:    Output Parameter:
335: .  usrP - user context

337:    Level: intermediate

339: .keywords: SNES, nonlinear, get, application, context

341: .seealso: SNESSetApplicationContext()
342: @*/
343: PetscErrorCode  SNESGetApplicationContext(SNES snes,void **usrP)
344: {
347:   *usrP = snes->user;
348:   return(0);
349: }

353: /*@
354:    SNESGetIterationNumber - Gets the number of nonlinear iterations completed
355:    at this time.

357:    Not Collective

359:    Input Parameter:
360: .  snes - SNES context

362:    Output Parameter:
363: .  iter - iteration number

365:    Notes:
366:    For example, during the computation of iteration 2 this would return 1.

368:    This is useful for using lagged Jacobians (where one does not recompute the 
369:    Jacobian at each SNES iteration). For example, the code
370: .vb
371:       SNESGetIterationNumber(snes,&it);
372:       if (!(it % 2)) {
373:         [compute Jacobian here]
374:       }
375: .ve
376:    can be used in your ComputeJacobian() function to cause the Jacobian to be
377:    recomputed every second SNES iteration.

379:    Level: intermediate

381: .keywords: SNES, nonlinear, get, iteration, number, 

383: .seealso:   SNESGetFunctionNorm(), SNESGetLinearSolveIterations()
384: @*/
385: PetscErrorCode  SNESGetIterationNumber(SNES snes,PetscInt* iter)
386: {
390:   *iter = snes->iter;
391:   return(0);
392: }

396: /*@
397:    SNESGetFunctionNorm - Gets the norm of the current function that was set
398:    with SNESSSetFunction().

400:    Collective on SNES

402:    Input Parameter:
403: .  snes - SNES context

405:    Output Parameter:
406: .  fnorm - 2-norm of function

408:    Level: intermediate

410: .keywords: SNES, nonlinear, get, function, norm

412: .seealso: SNESGetFunction(), SNESGetIterationNumber(), SNESGetLinearSolveIterations()
413: @*/
414: PetscErrorCode  SNESGetFunctionNorm(SNES snes,PetscReal *fnorm)
415: {
419:   *fnorm = snes->norm;
420:   return(0);
421: }

425: /*@
426:    SNESGetNonlinearStepFailures - Gets the number of unsuccessful steps
427:    attempted by the nonlinear solver.

429:    Not Collective

431:    Input Parameter:
432: .  snes - SNES context

434:    Output Parameter:
435: .  nfails - number of unsuccessful steps attempted

437:    Notes:
438:    This counter is reset to zero for each successive call to SNESSolve().

440:    Level: intermediate

442: .keywords: SNES, nonlinear, get, number, unsuccessful, steps

444: .seealso: SNESGetMaxLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures(), SNESGetLinearSolveFailures(),
445:           SNESSetMaxNonlinearStepFailures(), SNESGetMaxNonlinearStepFailures()
446: @*/
447: PetscErrorCode  SNESGetNonlinearStepFailures(SNES snes,PetscInt* nfails)
448: {
452:   *nfails = snes->numFailures;
453:   return(0);
454: }

458: /*@
459:    SNESSetMaxNonlinearStepFailures - Sets the maximum number of unsuccessful steps
460:    attempted by the nonlinear solver before it gives up.

462:    Not Collective

464:    Input Parameters:
465: +  snes     - SNES context
466: -  maxFails - maximum of unsuccessful steps

468:    Level: intermediate

470: .keywords: SNES, nonlinear, set, maximum, unsuccessful, steps

472: .seealso: SNESGetMaxLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures(), SNESGetLinearSolveFailures(),
473:           SNESGetMaxNonlinearStepFailures(), SNESGetNonlinearStepFailures()
474: @*/
475: PetscErrorCode  SNESSetMaxNonlinearStepFailures(SNES snes, PetscInt maxFails)
476: {
479:   snes->maxFailures = maxFails;
480:   return(0);
481: }

485: /*@
486:    SNESGetMaxNonlinearStepFailures - Gets the maximum number of unsuccessful steps
487:    attempted by the nonlinear solver before it gives up.

489:    Not Collective

491:    Input Parameter:
492: .  snes     - SNES context

494:    Output Parameter:
495: .  maxFails - maximum of unsuccessful steps

497:    Level: intermediate

499: .keywords: SNES, nonlinear, get, maximum, unsuccessful, steps

501: .seealso: SNESGetMaxLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures(), SNESGetLinearSolveFailures(),
502:           SNESSetMaxNonlinearStepFailures(), SNESGetNonlinearStepFailures()
503:  
504: @*/
505: PetscErrorCode  SNESGetMaxNonlinearStepFailures(SNES snes, PetscInt *maxFails)
506: {
510:   *maxFails = snes->maxFailures;
511:   return(0);
512: }

516: /*@
517:    SNESGetNumberFunctionEvals - Gets the number of user provided function evaluations
518:      done by SNES.

520:    Not Collective

522:    Input Parameter:
523: .  snes     - SNES context

525:    Output Parameter:
526: .  nfuncs - number of evaluations

528:    Level: intermediate

530: .keywords: SNES, nonlinear, get, maximum, unsuccessful, steps

532: .seealso: SNESGetMaxLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures(), SNESGetLinearSolveFailures()
533: @*/
534: PetscErrorCode  SNESGetNumberFunctionEvals(SNES snes, PetscInt *nfuncs)
535: {
539:   *nfuncs = snes->nfuncs;
540:   return(0);
541: }

545: /*@
546:    SNESGetLinearSolveFailures - Gets the number of failed (non-converged)
547:    linear solvers.

549:    Not Collective

551:    Input Parameter:
552: .  snes - SNES context

554:    Output Parameter:
555: .  nfails - number of failed solves

557:    Notes:
558:    This counter is reset to zero for each successive call to SNESSolve().

560:    Level: intermediate

562: .keywords: SNES, nonlinear, get, number, unsuccessful, steps

564: .seealso: SNESGetMaxLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures()
565: @*/
566: PetscErrorCode  SNESGetLinearSolveFailures(SNES snes,PetscInt* nfails)
567: {
571:   *nfails = snes->numLinearSolveFailures;
572:   return(0);
573: }

577: /*@
578:    SNESSetMaxLinearSolveFailures - the number of failed linear solve attempts
579:    allowed before SNES returns with a diverged reason of SNES_DIVERGED_LINEAR_SOLVE

581:    Collective on SNES

583:    Input Parameters:
584: +  snes     - SNES context
585: -  maxFails - maximum allowed linear solve failures

587:    Level: intermediate

589:    Notes: By default this is 1; that is SNES returns on the first failed linear solve

591: .keywords: SNES, nonlinear, set, maximum, unsuccessful, steps

593: .seealso: SNESGetLinearSolveFailures(), SNESGetMaxLinearSolveFailures(), SNESGetLinearSolveIterations()
594: @*/
595: PetscErrorCode  SNESSetMaxLinearSolveFailures(SNES snes, PetscInt maxFails)
596: {
599:   snes->maxLinearSolveFailures = maxFails;
600:   return(0);
601: }

605: /*@
606:    SNESGetMaxLinearSolveFailures - gets the maximum number of linear solve failures that
607:      are allowed before SNES terminates

609:    Not Collective

611:    Input Parameter:
612: .  snes     - SNES context

614:    Output Parameter:
615: .  maxFails - maximum of unsuccessful solves allowed

617:    Level: intermediate

619:    Notes: By default this is 1; that is SNES returns on the first failed linear solve

621: .keywords: SNES, nonlinear, get, maximum, unsuccessful, steps

623: .seealso: SNESGetLinearSolveFailures(), SNESGetLinearSolverIterations(), SNESSetMaxLinearSolveFailures(),
624: @*/
625: PetscErrorCode  SNESGetMaxLinearSolveFailures(SNES snes, PetscInt *maxFails)
626: {
630:   *maxFails = snes->maxLinearSolveFailures;
631:   return(0);
632: }

636: /*@
637:    SNESGetLinearSolveIterations - Gets the total number of linear iterations
638:    used by the nonlinear solver.

640:    Not Collective

642:    Input Parameter:
643: .  snes - SNES context

645:    Output Parameter:
646: .  lits - number of linear iterations

648:    Notes:
649:    This counter is reset to zero for each successive call to SNESSolve().

651:    Level: intermediate

653: .keywords: SNES, nonlinear, get, number, linear, iterations

655: .seealso:  SNESGetIterationNumber(), SNESGetFunctionNorm()S, NESGetLinearSolveFailures(), SNESGetMaxLinearSolveFailures()
656: @*/
657: PetscErrorCode  SNESGetLinearSolveIterations(SNES snes,PetscInt* lits)
658: {
662:   *lits = snes->linear_its;
663:   return(0);
664: }

668: /*@
669:    SNESGetKSP - Returns the KSP context for a SNES solver.

671:    Not Collective, but if SNES object is parallel, then KSP object is parallel

673:    Input Parameter:
674: .  snes - the SNES context

676:    Output Parameter:
677: .  ksp - the KSP context

679:    Notes:
680:    The user can then directly manipulate the KSP context to set various
681:    options, etc.  Likewise, the user can then extract and manipulate the 
682:    PC contexts as well.

684:    Level: beginner

686: .keywords: SNES, nonlinear, get, KSP, context

688: .seealso: KSPGetPC(), SNESCreate(), KSPCreate(), SNESSetKSP()
689: @*/
690: PetscErrorCode  SNESGetKSP(SNES snes,KSP *ksp)
691: {
695:   *ksp = snes->ksp;
696:   return(0);
697: }

701: /*@
702:    SNESSetKSP - Sets a KSP context for the SNES object to use

704:    Not Collective, but the SNES and KSP objects must live on the same MPI_Comm

706:    Input Parameters:
707: +  snes - the SNES context
708: -  ksp - the KSP context

710:    Notes:
711:    The SNES object already has its KSP object, you can obtain with SNESGetKSP()
712:    so this routine is rarely needed.

714:    The KSP object that is already in the SNES object has its reference count
715:    decreased by one.

717:    Level: developer

719: .keywords: SNES, nonlinear, get, KSP, context

721: .seealso: KSPGetPC(), SNESCreate(), KSPCreate(), SNESSetKSP()
722: @*/
723: PetscErrorCode  SNESSetKSP(SNES snes,KSP ksp)
724: {

731:   PetscObjectReference((PetscObject)ksp);
732:   if (snes->ksp) {PetscObjectDereference((PetscObject)snes->ksp);}
733:   snes->ksp = ksp;
734:   return(0);
735: }

737: #if 0
740: static PetscErrorCode SNESPublish_Petsc(PetscObject obj)
741: {
743:   return(0);
744: }
745: #endif

747: /* -----------------------------------------------------------*/
750: /*@
751:    SNESCreate - Creates a nonlinear solver context.

753:    Collective on MPI_Comm

755:    Input Parameters:
756: .  comm - MPI communicator

758:    Output Parameter:
759: .  outsnes - the new SNES context

761:    Options Database Keys:
762: +   -snes_mf - Activates default matrix-free Jacobian-vector products,
763:                and no preconditioning matrix
764: .   -snes_mf_operator - Activates default matrix-free Jacobian-vector
765:                products, and a user-provided preconditioning matrix
766:                as set by SNESSetJacobian()
767: -   -snes_fd - Uses (slow!) finite differences to compute Jacobian

769:    Level: beginner

771: .keywords: SNES, nonlinear, create, context

773: .seealso: SNESSolve(), SNESDestroy(), SNES
774: @*/
775: PetscErrorCode  SNESCreate(MPI_Comm comm,SNES *outsnes)
776: {
777:   PetscErrorCode      ierr;
778:   SNES                snes;
779:   SNESKSPEW           *kctx;

783:   *outsnes = PETSC_NULL;
784: #ifndef PETSC_USE_DYNAMIC_LIBRARIES
785:   SNESInitializePackage(PETSC_NULL);
786: #endif

788:   PetscHeaderCreate(snes,_p_SNES,struct _SNESOps,SNES_COOKIE,0,"SNES",comm,SNESDestroy,SNESView);

790:   snes->ops->converged    = SNESDefaultConverged;
791:   snes->max_its           = 50;
792:   snes->max_funcs          = 10000;
793:   snes->norm                  = 0.0;
794:   snes->rtol                  = 1.e-8;
795:   snes->ttol              = 0.0;
796:   snes->abstol                  = 1.e-50;
797:   snes->xtol                  = 1.e-8;
798:   snes->deltatol          = 1.e-12;
799:   snes->nfuncs            = 0;
800:   snes->numFailures       = 0;
801:   snes->maxFailures       = 1;
802:   snes->linear_its        = 0;
803:   snes->numbermonitors    = 0;
804:   snes->data              = 0;
805:   snes->setupcalled       = PETSC_FALSE;
806:   snes->ksp_ewconv        = PETSC_FALSE;
807:   snes->vwork             = 0;
808:   snes->nwork             = 0;
809:   snes->conv_hist_len     = 0;
810:   snes->conv_hist_max     = 0;
811:   snes->conv_hist         = PETSC_NULL;
812:   snes->conv_hist_its     = PETSC_NULL;
813:   snes->conv_hist_reset   = PETSC_TRUE;
814:   snes->reason            = SNES_CONVERGED_ITERATING;

816:   snes->numLinearSolveFailures = 0;
817:   snes->maxLinearSolveFailures = 1;

819:   /* Create context to compute Eisenstat-Walker relative tolerance for KSP */
820:   PetscNewLog(snes,SNESKSPEW,&kctx);
821:   snes->kspconvctx  = (void*)kctx;
822:   kctx->version     = 2;
823:   kctx->rtol_0      = .3; /* Eisenstat and Walker suggest rtol_0=.5, but 
824:                              this was too large for some test cases */
825:   kctx->rtol_last   = 0;
826:   kctx->rtol_max    = .9;
827:   kctx->gamma       = 1.0;
828:   kctx->alpha       = .5*(1.0 + sqrt(5.0));
829:   kctx->alpha2      = kctx->alpha;
830:   kctx->threshold   = .1;
831:   kctx->lresid_last = 0;
832:   kctx->norm_last   = 0;

834:   KSPCreate(comm,&snes->ksp);
835:   PetscLogObjectParent(snes,snes->ksp);

837:   *outsnes = snes;
838:   PetscPublishAll(snes);
839:   return(0);
840: }

844: /*@C
845:    SNESSetFunction - Sets the function evaluation routine and function 
846:    vector for use by the SNES routines in solving systems of nonlinear
847:    equations.

849:    Collective on SNES

851:    Input Parameters:
852: +  snes - the SNES context
853: .  r - vector to store function value
854: .  func - function evaluation routine
855: -  ctx - [optional] user-defined context for private data for the 
856:          function evaluation routine (may be PETSC_NULL)

858:    Calling sequence of func:
859: $    func (SNES snes,Vec x,Vec f,void *ctx);

861: .  f - function vector
862: -  ctx - optional user-defined function context 

864:    Notes:
865:    The Newton-like methods typically solve linear systems of the form
866: $      f'(x) x = -f(x),
867:    where f'(x) denotes the Jacobian matrix and f(x) is the function.

869:    Level: beginner

871: .keywords: SNES, nonlinear, set, function

873: .seealso: SNESGetFunction(), SNESComputeFunction(), SNESSetJacobian()
874: @*/
875: PetscErrorCode  SNESSetFunction(SNES snes,Vec r,PetscErrorCode (*func)(SNES,Vec,Vec,void*),void *ctx)
876: {
882:   PetscObjectReference((PetscObject)r);
883:   if (snes->vec_func) { VecDestroy(snes->vec_func); }
884:   snes->ops->computefunction = func;
885:   snes->vec_func             = r;
886:   snes->funP                 = ctx;
887:   return(0);
888: }

890: /* --------------------------------------------------------------- */
893: /*@C
894:    SNESGetRhs - Gets the vector for solving F(x) = rhs. If rhs is not set
895:    it assumes a zero right hand side.

897:    Collective on SNES

899:    Input Parameter:
900: .  snes - the SNES context

902:    Output Parameter:
903: .  rhs - the right hand side vector or PETSC_NULL if the right hand side vector is null

905:    Level: intermediate

907: .keywords: SNES, nonlinear, get, function, right hand side

909: .seealso: SNESGetSolution(), SNESGetFunction(), SNESComputeFunction(), SNESSetJacobian(), SNESSetFunction()
910: @*/
911: PetscErrorCode  SNESGetRhs(SNES snes,Vec *rhs)
912: {
916:   *rhs = snes->vec_rhs;
917:   return(0);
918: }

922: /*@
923:    SNESComputeFunction - Calls the function that has been set with
924:                          SNESSetFunction().  

926:    Collective on SNES

928:    Input Parameters:
929: +  snes - the SNES context
930: -  x - input vector

932:    Output Parameter:
933: .  y - function vector, as set by SNESSetFunction()

935:    Notes:
936:    SNESComputeFunction() is typically used within nonlinear solvers
937:    implementations, so most users would not generally call this routine
938:    themselves.

940:    Level: developer

942: .keywords: SNES, nonlinear, compute, function

944: .seealso: SNESSetFunction(), SNESGetFunction()
945: @*/
946: PetscErrorCode  SNESComputeFunction(SNES snes,Vec x,Vec y)
947: {


958:   if (snes->ops->computefunction) {
959:     PetscStackPush("SNES user function");
960:     CHKMEMQ;
961:     (*snes->ops->computefunction)(snes,x,y,snes->funP);
962:     CHKMEMQ;
963:     PetscStackPop;
964:     if (PetscExceptionValue(ierr)) {
966:     }
967: 
968:   } else if (snes->vec_rhs) {
969:     MatMult(snes->jacobian, x, y);
970:   } else {
971:     SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetFunction() before SNESComputeFunction(), likely called from SNESSolve().");
972:   }
973:   if (snes->vec_rhs) {
974:     VecAXPY(y,-1.0,snes->vec_rhs);
975:   }
976:   snes->nfuncs++;
978:   return(0);
979: }

983: /*@
984:    SNESComputeJacobian - Computes the Jacobian matrix that has been
985:    set with SNESSetJacobian().

987:    Collective on SNES and Mat

989:    Input Parameters:
990: +  snes - the SNES context
991: -  x - input vector

993:    Output Parameters:
994: +  A - Jacobian matrix
995: .  B - optional preconditioning matrix
996: -  flag - flag indicating matrix structure (one of, SAME_NONZERO_PATTERN,DIFFERENT_NONZERO_PATTERN,SAME_PRECONDITIONER)

998:    Notes: 
999:    Most users should not need to explicitly call this routine, as it 
1000:    is used internally within the nonlinear solvers. 

1002:    See KSPSetOperators() for important information about setting the
1003:    flag parameter.

1005:    Level: developer

1007: .keywords: SNES, compute, Jacobian, matrix

1009: .seealso:  SNESSetJacobian(), KSPSetOperators(), MatStructure
1010: @*/
1011: PetscErrorCode  SNESComputeJacobian(SNES snes,Vec X,Mat *A,Mat *B,MatStructure *flg)
1012: {

1020:   if (!snes->ops->computejacobian) return(0);
1022:   *flg = DIFFERENT_NONZERO_PATTERN;
1023:   PetscStackPush("SNES user Jacobian function");
1024:   CHKMEMQ;
1025:   (*snes->ops->computejacobian)(snes,X,A,B,flg,snes->jacP);
1026:   CHKMEMQ;
1027:   PetscStackPop;
1029:   /* make sure user returned a correct Jacobian and preconditioner */
1032:   return(0);
1033: }

1037: /*@C
1038:    SNESSetJacobian - Sets the function to compute Jacobian as well as the
1039:    location to store the matrix.

1041:    Collective on SNES and Mat

1043:    Input Parameters:
1044: +  snes - the SNES context
1045: .  A - Jacobian matrix
1046: .  B - preconditioner matrix (usually same as the Jacobian)
1047: .  func - Jacobian evaluation routine
1048: -  ctx - [optional] user-defined context for private data for the 
1049:          Jacobian evaluation routine (may be PETSC_NULL)

1051:    Calling sequence of func:
1052: $     func (SNES snes,Vec x,Mat *A,Mat *B,int *flag,void *ctx);

1054: +  x - input vector
1055: .  A - Jacobian matrix
1056: .  B - preconditioner matrix, usually the same as A
1057: .  flag - flag indicating information about the preconditioner matrix
1058:    structure (same as flag in KSPSetOperators()), one of SAME_NONZERO_PATTERN,DIFFERENT_NONZERO_PATTERN,SAME_PRECONDITIONER
1059: -  ctx - [optional] user-defined Jacobian context

1061:    Notes: 
1062:    See KSPSetOperators() for important information about setting the flag
1063:    output parameter in the routine func().  Be sure to read this information!

1065:    The routine func() takes Mat * as the matrix arguments rather than Mat.  
1066:    This allows the Jacobian evaluation routine to replace A and/or B with a 
1067:    completely new new matrix structure (not just different matrix elements)
1068:    when appropriate, for instance, if the nonzero structure is changing
1069:    throughout the global iterations.

1071:    Level: beginner

1073: .keywords: SNES, nonlinear, set, Jacobian, matrix

1075: .seealso: KSPSetOperators(), SNESSetFunction(), MatMFFDComputeJacobian(), SNESDefaultComputeJacobianColor(), MatStructure
1076: @*/
1077: PetscErrorCode  SNESSetJacobian(SNES snes,Mat A,Mat B,PetscErrorCode (*func)(SNES,Vec,Mat*,Mat*,MatStructure*,void*),void *ctx)
1078: {

1087:   if (func) snes->ops->computejacobian = func;
1088:   if (ctx)  snes->jacP                 = ctx;
1089:   if (A) {
1090:     PetscObjectReference((PetscObject)A);
1091:     if (snes->jacobian) {MatDestroy(snes->jacobian);}
1092:     snes->jacobian = A;
1093:   }
1094:   if (B) {
1095:     PetscObjectReference((PetscObject)B);
1096:     if (snes->jacobian_pre) {MatDestroy(snes->jacobian_pre);}
1097:     snes->jacobian_pre = B;
1098:   }
1099:   return(0);
1100: }

1104: /*@C
1105:    SNESGetJacobian - Returns the Jacobian matrix and optionally the user 
1106:    provided context for evaluating the Jacobian.

1108:    Not Collective, but Mat object will be parallel if SNES object is

1110:    Input Parameter:
1111: .  snes - the nonlinear solver context

1113:    Output Parameters:
1114: +  A - location to stash Jacobian matrix (or PETSC_NULL)
1115: .  B - location to stash preconditioner matrix (or PETSC_NULL)
1116: .  func - location to put Jacobian function (or PETSC_NULL)
1117: -  ctx - location to stash Jacobian ctx (or PETSC_NULL)

1119:    Level: advanced

1121: .seealso: SNESSetJacobian(), SNESComputeJacobian()
1122: @*/
1123: PetscErrorCode  SNESGetJacobian(SNES snes,Mat *A,Mat *B,PetscErrorCode (**func)(SNES,Vec,Mat*,Mat*,MatStructure*,void*),void **ctx)
1124: {
1127:   if (A)    *A    = snes->jacobian;
1128:   if (B)    *B    = snes->jacobian_pre;
1129:   if (func) *func = snes->ops->computejacobian;
1130:   if (ctx)  *ctx  = snes->jacP;
1131:   return(0);
1132: }

1134: /* ----- Routines to initialize and destroy a nonlinear solver ---- */
1135: EXTERN PetscErrorCode  SNESDefaultMatrixFreeCreate2(SNES,Vec,Mat*);

1139: /*@
1140:    SNESSetUp - Sets up the internal data structures for the later use
1141:    of a nonlinear solver.

1143:    Collective on SNES

1145:    Input Parameters:
1146: .  snes - the SNES context

1148:    Notes:
1149:    For basic use of the SNES solvers the user need not explicitly call
1150:    SNESSetUp(), since these actions will automatically occur during
1151:    the call to SNESSolve().  However, if one wishes to control this
1152:    phase separately, SNESSetUp() should be called after SNESCreate()
1153:    and optional routines of the form SNESSetXXX(), but before SNESSolve().  

1155:    Level: advanced

1157: .keywords: SNES, nonlinear, setup

1159: .seealso: SNESCreate(), SNESSolve(), SNESDestroy()
1160: @*/
1161: PetscErrorCode  SNESSetUp(SNES snes)
1162: {
1164:   PetscTruth     flg;

1168:   if (snes->setupcalled) return(0);

1170:   if (!((PetscObject)snes)->type_name) {
1171:     SNESSetType(snes,SNESLS);
1172:   }

1174:   PetscOptionsHasName(((PetscObject)snes)->prefix,"-snes_mf_operator",&flg);
1175:   /*
1176:       This version replaces the user provided Jacobian matrix with a
1177:       matrix-free version but still employs the user-provided preconditioner matrix
1178:   */
1179:   if (flg) {
1180:     Mat J;
1181:     MatCreateSNESMF(snes,&J);
1182:     MatMFFDSetFromOptions(J);
1183:     PetscInfo(snes,"Setting default matrix-free operator routines\n");
1184:     SNESSetJacobian(snes,J,0,0,0);
1185:     MatDestroy(J);
1186:   }

1188: #if !defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_SINGLE) && !defined(PETSC_USE_MAT_SINGLE) && !defined(PETSC_USE_LONG_DOUBLE) && !defined(PETSC_USE_INT)
1189:   PetscOptionsHasName(((PetscObject)snes)->prefix,"-snes_mf_operator2",&flg);
1190:   if (flg) {
1191:     Mat J;
1192:     SNESDefaultMatrixFreeCreate2(snes,snes->vec_sol,&J);
1193:     PetscInfo(snes,"Setting default matrix-free operator routines (version 2)\n");
1194:     SNESSetJacobian(snes,J,0,0,0);
1195:     MatDestroy(J);
1196:   }
1197: #endif

1199:   PetscOptionsHasName(((PetscObject)snes)->prefix,"-snes_mf",&flg);
1200:   /*
1201:       This version replaces both the user-provided Jacobian and the user-
1202:       provided preconditioner matrix with the default matrix free version.
1203:    */
1204:   if (flg) {
1205:     Mat  J;
1206:     KSP ksp;
1207:     PC   pc;
1208:     /* create and set matrix-free operator */
1209:     MatCreateSNESMF(snes,&J);
1210:     MatMFFDSetFromOptions(J);
1211:     PetscInfo(snes,"Setting default matrix-free operator routines\n");
1212:     SNESSetJacobian(snes,J,J,MatMFFDComputeJacobian,snes->funP);
1213:     MatDestroy(J);
1214:     /* force no preconditioner */
1215:     SNESGetKSP(snes,&ksp);
1216:     KSPGetPC(ksp,&pc);
1217:     PetscTypeCompare((PetscObject)pc,PCSHELL,&flg);
1218:     if (!flg) {
1219:       PetscInfo(snes,"Setting default matrix-free preconditioner routines;\nThat is no preconditioner is being used\n");
1220:       PCSetType(pc,PCNONE);
1221:     }
1222:   }

1224:   if (!snes->vec_func && !snes->vec_rhs) {
1225:     SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetFunction() first");
1226:   }
1227:   if (!snes->ops->computefunction && !snes->vec_rhs) {
1228:     SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetFunction() first");
1229:   }
1230:   if (!snes->jacobian) {
1231:     SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetJacobian() first \n or use -snes_mf option");
1232:   }
1233:   if (snes->vec_func == snes->vec_sol) {
1234:     SETERRQ(PETSC_ERR_ARG_IDN,"Solution vector cannot be function vector");
1235:   }
1236: 
1237:   if (snes->ops->setup) {
1238:     (*snes->ops->setup)(snes);
1239:   }
1240:   snes->setupcalled = PETSC_TRUE;
1241:   return(0);
1242: }

1246: /*@
1247:    SNESDestroy - Destroys the nonlinear solver context that was created
1248:    with SNESCreate().

1250:    Collective on SNES

1252:    Input Parameter:
1253: .  snes - the SNES context

1255:    Level: beginner

1257: .keywords: SNES, nonlinear, destroy

1259: .seealso: SNESCreate(), SNESSolve()
1260: @*/
1261: PetscErrorCode  SNESDestroy(SNES snes)
1262: {

1267:   if (--((PetscObject)snes)->refct > 0) return(0);

1269:   /* if memory was published with AMS then destroy it */
1270:   PetscObjectDepublish(snes);
1271:   if (snes->ops->destroy) {(*(snes)->ops->destroy)(snes);}
1272: 
1273:   if (snes->vec_rhs) {VecDestroy(snes->vec_rhs);}
1274:   if (snes->vec_sol) {VecDestroy(snes->vec_sol);}
1275:   if (snes->vec_func) {VecDestroy(snes->vec_func);}
1276:   if (snes->jacobian) {MatDestroy(snes->jacobian);}
1277:   if (snes->jacobian_pre) {MatDestroy(snes->jacobian_pre);}
1278:   KSPDestroy(snes->ksp);
1279:   PetscFree(snes->kspconvctx);
1280:   if (snes->vwork) {VecDestroyVecs(snes->vwork,snes->nvwork);}
1281:   SNESMonitorCancel(snes);
1282:   PetscHeaderDestroy(snes);
1283:   return(0);
1284: }

1286: /* ----------- Routines to set solver parameters ---------- */

1290: /*@
1291:    SNESSetTolerances - Sets various parameters used in convergence tests.

1293:    Collective on SNES

1295:    Input Parameters:
1296: +  snes - the SNES context
1297: .  abstol - absolute convergence tolerance
1298: .  rtol - relative convergence tolerance
1299: .  stol -  convergence tolerance in terms of the norm
1300:            of the change in the solution between steps
1301: .  maxit - maximum number of iterations
1302: -  maxf - maximum number of function evaluations

1304:    Options Database Keys: 
1305: +    -snes_atol <abstol> - Sets abstol
1306: .    -snes_rtol <rtol> - Sets rtol
1307: .    -snes_stol <stol> - Sets stol
1308: .    -snes_max_it <maxit> - Sets maxit
1309: -    -snes_max_funcs <maxf> - Sets maxf

1311:    Notes:
1312:    The default maximum number of iterations is 50.
1313:    The default maximum number of function evaluations is 1000.

1315:    Level: intermediate

1317: .keywords: SNES, nonlinear, set, convergence, tolerances

1319: .seealso: SNESSetTrustRegionTolerance()
1320: @*/
1321: PetscErrorCode  SNESSetTolerances(SNES snes,PetscReal abstol,PetscReal rtol,PetscReal stol,PetscInt maxit,PetscInt maxf)
1322: {
1325:   if (abstol != PETSC_DEFAULT)  snes->abstol      = abstol;
1326:   if (rtol != PETSC_DEFAULT)  snes->rtol      = rtol;
1327:   if (stol != PETSC_DEFAULT)  snes->xtol      = stol;
1328:   if (maxit != PETSC_DEFAULT) snes->max_its   = maxit;
1329:   if (maxf != PETSC_DEFAULT)  snes->max_funcs = maxf;
1330:   return(0);
1331: }

1335: /*@
1336:    SNESGetTolerances - Gets various parameters used in convergence tests.

1338:    Not Collective

1340:    Input Parameters:
1341: +  snes - the SNES context
1342: .  atol - absolute convergence tolerance
1343: .  rtol - relative convergence tolerance
1344: .  stol -  convergence tolerance in terms of the norm
1345:            of the change in the solution between steps
1346: .  maxit - maximum number of iterations
1347: -  maxf - maximum number of function evaluations

1349:    Notes:
1350:    The user can specify PETSC_NULL for any parameter that is not needed.

1352:    Level: intermediate

1354: .keywords: SNES, nonlinear, get, convergence, tolerances

1356: .seealso: SNESSetTolerances()
1357: @*/
1358: PetscErrorCode  SNESGetTolerances(SNES snes,PetscReal *atol,PetscReal *rtol,PetscReal *stol,PetscInt *maxit,PetscInt *maxf)
1359: {
1362:   if (atol)  *atol  = snes->abstol;
1363:   if (rtol)  *rtol  = snes->rtol;
1364:   if (stol)  *stol  = snes->xtol;
1365:   if (maxit) *maxit = snes->max_its;
1366:   if (maxf)  *maxf  = snes->max_funcs;
1367:   return(0);
1368: }

1372: /*@
1373:    SNESSetTrustRegionTolerance - Sets the trust region parameter tolerance.  

1375:    Collective on SNES

1377:    Input Parameters:
1378: +  snes - the SNES context
1379: -  tol - tolerance
1380:    
1381:    Options Database Key: 
1382: .  -snes_trtol <tol> - Sets tol

1384:    Level: intermediate

1386: .keywords: SNES, nonlinear, set, trust region, tolerance

1388: .seealso: SNESSetTolerances()
1389: @*/
1390: PetscErrorCode  SNESSetTrustRegionTolerance(SNES snes,PetscReal tol)
1391: {
1394:   snes->deltatol = tol;
1395:   return(0);
1396: }

1398: /* 
1399:    Duplicate the lg monitors for SNES from KSP; for some reason with 
1400:    dynamic libraries things don't work under Sun4 if we just use 
1401:    macros instead of functions
1402: */
1405: PetscErrorCode  SNESMonitorLG(SNES snes,PetscInt it,PetscReal norm,void *ctx)
1406: {

1411:   KSPMonitorLG((KSP)snes,it,norm,ctx);
1412:   return(0);
1413: }

1417: PetscErrorCode  SNESMonitorLGCreate(const char host[],const char label[],int x,int y,int m,int n,PetscDrawLG *draw)
1418: {

1422:   KSPMonitorLGCreate(host,label,x,y,m,n,draw);
1423:   return(0);
1424: }

1428: PetscErrorCode  SNESMonitorLGDestroy(PetscDrawLG draw)
1429: {

1433:   KSPMonitorLGDestroy(draw);
1434:   return(0);
1435: }

1437: /* ------------ Routines to set performance monitoring options ----------- */

1441: /*@C
1442:    SNESMonitorSet - Sets an ADDITIONAL function that is to be used at every
1443:    iteration of the nonlinear solver to display the iteration's 
1444:    progress.   

1446:    Collective on SNES

1448:    Input Parameters:
1449: +  snes - the SNES context
1450: .  func - monitoring routine
1451: .  mctx - [optional] user-defined context for private data for the 
1452:           monitor routine (use PETSC_NULL if no context is desired)
1453: -  monitordestroy - [optional] routine that frees monitor context
1454:           (may be PETSC_NULL)

1456:    Calling sequence of func:
1457: $     int func(SNES snes,PetscInt its, PetscReal norm,void *mctx)

1459: +    snes - the SNES context
1460: .    its - iteration number
1461: .    norm - 2-norm function value (may be estimated)
1462: -    mctx - [optional] monitoring context

1464:    Options Database Keys:
1465: +    -snes_monitor        - sets SNESMonitorDefault()
1466: .    -snes_monitor_draw    - sets line graph monitor,
1467:                             uses SNESMonitorLGCreate()
1468: _    -snes_monitor_cancel - cancels all monitors that have
1469:                             been hardwired into a code by 
1470:                             calls to SNESMonitorSet(), but
1471:                             does not cancel those set via
1472:                             the options database.

1474:    Notes: 
1475:    Several different monitoring routines may be set by calling
1476:    SNESMonitorSet() multiple times; all will be called in the 
1477:    order in which they were set.

1479:    Level: intermediate

1481: .keywords: SNES, nonlinear, set, monitor

1483: .seealso: SNESMonitorDefault(), SNESMonitorCancel()
1484: @*/
1485: PetscErrorCode  SNESMonitorSet(SNES snes,PetscErrorCode (*monitor)(SNES,PetscInt,PetscReal,void*),void *mctx,PetscErrorCode (*monitordestroy)(void*))
1486: {
1487:   PetscInt i;

1491:   if (snes->numbermonitors >= MAXSNESMONITORS) {
1492:     SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Too many monitors set");
1493:   }
1494:   for (i=0; i<snes->numbermonitors;i++) {
1495:     if (monitor == snes->monitor[i] && monitordestroy == snes->monitordestroy[i] && mctx == snes->monitorcontext[i]) return(0);

1497:     /* check if both default monitors that share common ASCII viewer */
1498:     if (monitor == snes->monitor[i] && monitor == SNESMonitorDefault) {
1499:       if (mctx && snes->monitorcontext[i]) {
1500:         PetscErrorCode          ierr;
1501:         PetscViewerASCIIMonitor viewer1 = (PetscViewerASCIIMonitor) mctx;
1502:         PetscViewerASCIIMonitor viewer2 = (PetscViewerASCIIMonitor) snes->monitorcontext[i];
1503:         if (viewer1->viewer == viewer2->viewer) {
1504:           (*monitordestroy)(mctx);
1505:           return(0);
1506:         }
1507:       }
1508:     }
1509:   }
1510:   snes->monitor[snes->numbermonitors]           = monitor;
1511:   snes->monitordestroy[snes->numbermonitors]    = monitordestroy;
1512:   snes->monitorcontext[snes->numbermonitors++]  = (void*)mctx;
1513:   return(0);
1514: }

1518: /*@C
1519:    SNESMonitorCancel - Clears all the monitor functions for a SNES object.

1521:    Collective on SNES

1523:    Input Parameters:
1524: .  snes - the SNES context

1526:    Options Database Key:
1527: .  -snes_monitor_cancel - cancels all monitors that have been hardwired
1528:     into a code by calls to SNESMonitorSet(), but does not cancel those 
1529:     set via the options database

1531:    Notes: 
1532:    There is no way to clear one specific monitor from a SNES object.

1534:    Level: intermediate

1536: .keywords: SNES, nonlinear, set, monitor

1538: .seealso: SNESMonitorDefault(), SNESMonitorSet()
1539: @*/
1540: PetscErrorCode  SNESMonitorCancel(SNES snes)
1541: {
1543:   PetscInt       i;

1547:   for (i=0; i<snes->numbermonitors; i++) {
1548:     if (snes->monitordestroy[i]) {
1549:       (*snes->monitordestroy[i])(snes->monitorcontext[i]);
1550:     }
1551:   }
1552:   snes->numbermonitors = 0;
1553:   return(0);
1554: }

1558: /*@C
1559:    SNESSetConvergenceTest - Sets the function that is to be used 
1560:    to test for convergence of the nonlinear iterative solution.   

1562:    Collective on SNES

1564:    Input Parameters:
1565: +  snes - the SNES context
1566: .  func - routine to test for convergence
1567: -  cctx - [optional] context for private data for the convergence routine 
1568:           (may be PETSC_NULL)

1570:    Calling sequence of func:
1571: $     PetscErrorCode func (SNES snes,PetscInt it,PetscReal xnorm,PetscReal gnorm,PetscReal f,SNESConvergedReason *reason,void *cctx)

1573: +    snes - the SNES context
1574: .    it - current iteration (0 is the first and is before any Newton step)
1575: .    cctx - [optional] convergence context
1576: .    reason - reason for convergence/divergence
1577: .    xnorm - 2-norm of current iterate
1578: .    gnorm - 2-norm of current step
1579: -    f - 2-norm of function

1581:    Level: advanced

1583: .keywords: SNES, nonlinear, set, convergence, test

1585: .seealso: SNESDefaultConverged(), SNESSkipConverged()
1586: @*/
1587: PetscErrorCode  SNESSetConvergenceTest(SNES snes,PetscErrorCode (*func)(SNES,PetscInt,PetscReal,PetscReal,PetscReal,SNESConvergedReason*,void*),void *cctx)
1588: {
1591:   if (!func) func = SNESSkipConverged;
1592:   snes->ops->converged = func;
1593:   snes->cnvP           = cctx;
1594:   return(0);
1595: }

1599: /*@
1600:    SNESGetConvergedReason - Gets the reason the SNES iteration was stopped.

1602:    Not Collective

1604:    Input Parameter:
1605: .  snes - the SNES context

1607:    Output Parameter:
1608: .  reason - negative value indicates diverged, positive value converged, see petscsnes.h or the 
1609:             manual pages for the individual convergence tests for complete lists

1611:    Level: intermediate

1613:    Notes: Can only be called after the call the SNESSolve() is complete.

1615: .keywords: SNES, nonlinear, set, convergence, test

1617: .seealso: SNESSetConvergenceTest(), SNESConvergedReason
1618: @*/
1619: PetscErrorCode  SNESGetConvergedReason(SNES snes,SNESConvergedReason *reason)
1620: {
1624:   *reason = snes->reason;
1625:   return(0);
1626: }

1630: /*@
1631:    SNESSetConvergenceHistory - Sets the array used to hold the convergence history.

1633:    Collective on SNES

1635:    Input Parameters:
1636: +  snes - iterative context obtained from SNESCreate()
1637: .  a   - array to hold history
1638: .  its - integer array holds the number of linear iterations for each solve.
1639: .  na  - size of a and its
1640: -  reset - PETSC_TRUE indicates each new nonlinear solve resets the history counter to zero,
1641:            else it continues storing new values for new nonlinear solves after the old ones

1643:    Notes:
1644:    If set, this array will contain the function norms computed
1645:    at each step.

1647:    This routine is useful, e.g., when running a code for purposes
1648:    of accurate performance monitoring, when no I/O should be done
1649:    during the section of code that is being timed.

1651:    Level: intermediate

1653: .keywords: SNES, set, convergence, history

1655: .seealso: SNESGetConvergenceHistory()

1657: @*/
1658: PetscErrorCode  SNESSetConvergenceHistory(SNES snes,PetscReal a[],PetscInt its[],PetscInt na,PetscTruth reset)
1659: {
1664:   snes->conv_hist       = a;
1665:   snes->conv_hist_its   = its;
1666:   snes->conv_hist_max   = na;
1667:   snes->conv_hist_reset = reset;
1668:   return(0);
1669: }

1673: /*@C
1674:    SNESGetConvergenceHistory - Gets the array used to hold the convergence history.

1676:    Collective on SNES

1678:    Input Parameter:
1679: .  snes - iterative context obtained from SNESCreate()

1681:    Output Parameters:
1682: .  a   - array to hold history
1683: .  its - integer array holds the number of linear iterations (or
1684:          negative if not converged) for each solve.
1685: -  na  - size of a and its

1687:    Notes:
1688:     The calling sequence for this routine in Fortran is
1689: $   call SNESGetConvergenceHistory(SNES snes, integer na, integer ierr)

1691:    This routine is useful, e.g., when running a code for purposes
1692:    of accurate performance monitoring, when no I/O should be done
1693:    during the section of code that is being timed.

1695:    Level: intermediate

1697: .keywords: SNES, get, convergence, history

1699: .seealso: SNESSetConvergencHistory()

1701: @*/
1702: PetscErrorCode  SNESGetConvergenceHistory(SNES snes,PetscReal *a[],PetscInt *its[],PetscInt *na)
1703: {
1706:   if (a)   *a   = snes->conv_hist;
1707:   if (its) *its = snes->conv_hist_its;
1708:   if (na)  *na  = snes->conv_hist_len;
1709:   return(0);
1710: }

1714: /*@C
1715:   SNESSetUpdate - Sets the general-purpose update function called
1716:   at the beginning o every iteration of the nonlinear solve. Specifically
1717:   it is called just before the Jacobian is "evaluated".

1719:   Collective on SNES

1721:   Input Parameters:
1722: . snes - The nonlinear solver context
1723: . func - The function

1725:   Calling sequence of func:
1726: . func (SNES snes, PetscInt step);

1728: . step - The current step of the iteration

1730:   Level: intermediate

1732: .keywords: SNES, update

1734: .seealso SNESDefaultUpdate(), SNESSetJacobian(), SNESSolve()
1735: @*/
1736: PetscErrorCode  SNESSetUpdate(SNES snes, PetscErrorCode (*func)(SNES, PetscInt))
1737: {
1740:   snes->ops->update = func;
1741:   return(0);
1742: }

1746: /*@
1747:   SNESDefaultUpdate - The default update function which does nothing.

1749:   Not collective

1751:   Input Parameters:
1752: . snes - The nonlinear solver context
1753: . step - The current step of the iteration

1755:   Level: intermediate

1757: .keywords: SNES, update
1758: .seealso SNESSetUpdate(), SNESDefaultRhsBC(), SNESDefaultShortolutionBC()
1759: @*/
1760: PetscErrorCode  SNESDefaultUpdate(SNES snes, PetscInt step)
1761: {
1763:   return(0);
1764: }

1768: /*
1769:    SNESScaleStep_Private - Scales a step so that its length is less than the
1770:    positive parameter delta.

1772:     Input Parameters:
1773: +   snes - the SNES context
1774: .   y - approximate solution of linear system
1775: .   fnorm - 2-norm of current function
1776: -   delta - trust region size

1778:     Output Parameters:
1779: +   gpnorm - predicted function norm at the new point, assuming local 
1780:     linearization.  The value is zero if the step lies within the trust 
1781:     region, and exceeds zero otherwise.
1782: -   ynorm - 2-norm of the step

1784:     Note:
1785:     For non-trust region methods such as SNESLS, the parameter delta 
1786:     is set to be the maximum allowable step size.  

1788: .keywords: SNES, nonlinear, scale, step
1789: */
1790: PetscErrorCode SNESScaleStep_Private(SNES snes,Vec y,PetscReal *fnorm,PetscReal *delta,PetscReal *gpnorm,PetscReal *ynorm)
1791: {
1792:   PetscReal      nrm;
1793:   PetscScalar    cnorm;


1801:   VecNorm(y,NORM_2,&nrm);
1802:   if (nrm > *delta) {
1803:      nrm = *delta/nrm;
1804:      *gpnorm = (1.0 - nrm)*(*fnorm);
1805:      cnorm = nrm;
1806:      VecScale(y,cnorm);
1807:      *ynorm = *delta;
1808:   } else {
1809:      *gpnorm = 0.0;
1810:      *ynorm = nrm;
1811:   }
1812:   return(0);
1813: }

1817: /*@C
1818:    SNESSolve - Solves a nonlinear system F(x) = b.
1819:    Call SNESSolve() after calling SNESCreate() and optional routines of the form SNESSetXXX().

1821:    Collective on SNES

1823:    Input Parameters:
1824: +  snes - the SNES context
1825: .  b - the constant part of the equation, or PETSC_NULL to use zero.
1826: -  x - the solution vector.

1828:    Notes:
1829:    The user should initialize the vector,x, with the initial guess
1830:    for the nonlinear solve prior to calling SNESSolve.  In particular,
1831:    to employ an initial guess of zero, the user should explicitly set
1832:    this vector to zero by calling VecSet().

1834:    Level: beginner

1836: .keywords: SNES, nonlinear, solve

1838: .seealso: SNESCreate(), SNESDestroy(), SNESSetFunction(), SNESSetJacobian()
1839: @*/
1840: PetscErrorCode  SNESSolve(SNES snes,Vec b,Vec x)
1841: {
1843:   PetscTruth     flg;
1844:   char           filename[PETSC_MAX_PATH_LEN];
1845:   PetscViewer    viewer;


1854:   /* set solution vector */
1855:   PetscObjectReference((PetscObject)x);
1856:   if (snes->vec_sol) { VecDestroy(snes->vec_sol); }
1857:   snes->vec_sol = x;
1858:   /* set afine vector if provided */
1859:   if (b) { PetscObjectReference((PetscObject)b); }
1860:   if (snes->vec_rhs) { VecDestroy(snes->vec_rhs); }
1861:   snes->vec_rhs = b;
1862: 
1863:   if (!snes->vec_func && snes->vec_rhs) {
1864:     VecDuplicate(b, &snes->vec_func);
1865:   }

1867:   SNESSetUp(snes);

1869:   if (snes->conv_hist_reset) snes->conv_hist_len = 0;
1870:   snes->nfuncs = 0; snes->linear_its = 0; snes->numFailures = 0;

1873: 
1874:   PetscExceptionTry1((*(snes)->ops->solve)(snes),PETSC_ERR_ARG_DOMAIN);
1875:   if (PetscExceptionValue(ierr)) {
1876:     /* this means that a caller above me has also tryed this exception so I don't handle it here, pass it up */
1878:   } else if (PetscExceptionCaught(ierr,PETSC_ERR_ARG_DOMAIN)) {
1879:     /* translate exception into SNES not converged reason */
1880:     snes->reason = SNES_DIVERGED_FUNCTION_DOMAIN;
1881:     0;
1882:   }
1883: 

1886:   if (!snes->reason) {
1887:     SETERRQ(PETSC_ERR_PLIB,"Internal error, solver returned without setting converged reason");
1888:   }
1889: 
1890:   PetscOptionsGetString(((PetscObject)snes)->prefix,"-snes_view",filename,PETSC_MAX_PATH_LEN,&flg);
1891:   if (flg && !PetscPreLoadingOn) {
1892:     PetscViewerASCIIOpen(((PetscObject)snes)->comm,filename,&viewer);
1893:     SNESView(snes,viewer);
1894:     PetscViewerDestroy(viewer);
1895:   }

1897:   PetscOptionsHasName(((PetscObject)snes)->prefix,"-snes_test_local_min",&flg);
1898:   if (flg && !PetscPreLoadingOn) { SNESTestLocalMin(snes); }
1899:   if (snes->printreason) {
1900:     if (snes->reason > 0) {
1901:       PetscPrintf(((PetscObject)snes)->comm,"Nonlinear solve converged due to %s\n",SNESConvergedReasons[snes->reason]);
1902:     } else {
1903:       PetscPrintf(((PetscObject)snes)->comm,"Nonlinear solve did not converge due to %s\n",SNESConvergedReasons[snes->reason]);
1904:     }
1905:   }

1907:   return(0);
1908: }

1910: /* --------- Internal routines for SNES Package --------- */

1914: /*@C
1915:    SNESSetType - Sets the method for the nonlinear solver.  

1917:    Collective on SNES

1919:    Input Parameters:
1920: +  snes - the SNES context
1921: -  type - a known method

1923:    Options Database Key:
1924: .  -snes_type <type> - Sets the method; use -help for a list
1925:    of available methods (for instance, ls or tr)

1927:    Notes:
1928:    See "petsc/include/petscsnes.h" for available methods (for instance)
1929: +    SNESLS - Newton's method with line search
1930:      (systems of nonlinear equations)
1931: .    SNESTR - Newton's method with trust region
1932:      (systems of nonlinear equations)

1934:   Normally, it is best to use the SNESSetFromOptions() command and then
1935:   set the SNES solver type from the options database rather than by using
1936:   this routine.  Using the options database provides the user with
1937:   maximum flexibility in evaluating the many nonlinear solvers.
1938:   The SNESSetType() routine is provided for those situations where it
1939:   is necessary to set the nonlinear solver independently of the command
1940:   line or options database.  This might be the case, for example, when
1941:   the choice of solver changes during the execution of the program,
1942:   and the user's application is taking responsibility for choosing the
1943:   appropriate method.

1945:   Level: intermediate

1947: .keywords: SNES, set, type

1949: .seealso: SNESType, SNESCreate()

1951: @*/
1952: PetscErrorCode  SNESSetType(SNES snes,SNESType type)
1953: {
1954:   PetscErrorCode ierr,(*r)(SNES);
1955:   PetscTruth     match;


1961:   PetscTypeCompare((PetscObject)snes,type,&match);
1962:   if (match) return(0);

1964:    PetscFListFind(SNESList,((PetscObject)snes)->comm,type,(void (**)(void)) &r);
1965:   if (!r) SETERRQ1(PETSC_ERR_ARG_UNKNOWN_TYPE,"Unable to find requested SNES type %s",type);
1966:   /* Destroy the previous private SNES context */
1967:   if (snes->ops->destroy) { (*(snes)->ops->destroy)(snes); }
1968:   /* Reinitialize function pointers in SNESOps structure */
1969:   snes->ops->setup          = 0;
1970:   snes->ops->solve          = 0;
1971:   snes->ops->view           = 0;
1972:   snes->ops->setfromoptions = 0;
1973:   snes->ops->destroy        = 0;
1974:   /* Call the SNESCreate_XXX routine for this particular Nonlinear solver */
1975:   snes->setupcalled = PETSC_FALSE;
1976:   (*r)(snes);
1977:   PetscObjectChangeTypeName((PetscObject)snes,type);
1978:   return(0);
1979: }


1982: /* --------------------------------------------------------------------- */
1985: /*@
1986:    SNESRegisterDestroy - Frees the list of nonlinear solvers that were
1987:    registered by SNESRegisterDynamic().

1989:    Not Collective

1991:    Level: advanced

1993: .keywords: SNES, nonlinear, register, destroy

1995: .seealso: SNESRegisterAll(), SNESRegisterAll()
1996: @*/
1997: PetscErrorCode  SNESRegisterDestroy(void)
1998: {

2002:   PetscFListDestroy(&SNESList);
2003:   SNESRegisterAllCalled = PETSC_FALSE;
2004:   return(0);
2005: }

2009: /*@C
2010:    SNESGetType - Gets the SNES method type and name (as a string).

2012:    Not Collective

2014:    Input Parameter:
2015: .  snes - nonlinear solver context

2017:    Output Parameter:
2018: .  type - SNES method (a character string)

2020:    Level: intermediate

2022: .keywords: SNES, nonlinear, get, type, name
2023: @*/
2024: PetscErrorCode  SNESGetType(SNES snes,SNESType *type)
2025: {
2029:   *type = ((PetscObject)snes)->type_name;
2030:   return(0);
2031: }

2035: /*@
2036:    SNESGetSolution - Returns the vector where the approximate solution is
2037:    stored.

2039:    Not Collective, but Vec is parallel if SNES is parallel

2041:    Input Parameter:
2042: .  snes - the SNES context

2044:    Output Parameter:
2045: .  x - the solution

2047:    Level: intermediate

2049: .keywords: SNES, nonlinear, get, solution

2051: .seealso:  SNESGetSolutionUpdate(), SNESGetFunction()
2052: @*/
2053: PetscErrorCode  SNESGetSolution(SNES snes,Vec *x)
2054: {
2058:   *x = snes->vec_sol;
2059:   return(0);
2060: }

2064: /*@
2065:    SNESGetSolutionUpdate - Returns the vector where the solution update is
2066:    stored. 

2068:    Not Collective, but Vec is parallel if SNES is parallel

2070:    Input Parameter:
2071: .  snes - the SNES context

2073:    Output Parameter:
2074: .  x - the solution update

2076:    Level: advanced

2078: .keywords: SNES, nonlinear, get, solution, update

2080: .seealso: SNESGetSolution(), SNESGetFunction()
2081: @*/
2082: PetscErrorCode  SNESGetSolutionUpdate(SNES snes,Vec *x)
2083: {
2087:   *x = snes->vec_sol_update;
2088:   return(0);
2089: }

2093: /*@C
2094:    SNESGetFunction - Returns the vector where the function is stored.

2096:    Not Collective, but Vec is parallel if SNES is parallel

2098:    Input Parameter:
2099: .  snes - the SNES context

2101:    Output Parameter:
2102: +  r - the function (or PETSC_NULL)
2103: .  func - the function (or PETSC_NULL)
2104: -  ctx - the function context (or PETSC_NULL)

2106:    Level: advanced

2108: .keywords: SNES, nonlinear, get, function

2110: .seealso: SNESSetFunction(), SNESGetSolution()
2111: @*/
2112: PetscErrorCode  SNESGetFunction(SNES snes,Vec *r,PetscErrorCode (**func)(SNES,Vec,Vec,void*),void **ctx)
2113: {
2116:   if (r)    *r    = snes->vec_func;
2117:   if (func) *func = snes->ops->computefunction;
2118:   if (ctx)  *ctx  = snes->funP;
2119:   return(0);
2120: }

2124: /*@C
2125:    SNESSetOptionsPrefix - Sets the prefix used for searching for all 
2126:    SNES options in the database.

2128:    Collective on SNES

2130:    Input Parameter:
2131: +  snes - the SNES context
2132: -  prefix - the prefix to prepend to all option names

2134:    Notes:
2135:    A hyphen (-) must NOT be given at the beginning of the prefix name.
2136:    The first character of all runtime options is AUTOMATICALLY the hyphen.

2138:    Level: advanced

2140: .keywords: SNES, set, options, prefix, database

2142: .seealso: SNESSetFromOptions()
2143: @*/
2144: PetscErrorCode  SNESSetOptionsPrefix(SNES snes,const char prefix[])
2145: {

2150:   PetscObjectSetOptionsPrefix((PetscObject)snes,prefix);
2151:   KSPSetOptionsPrefix(snes->ksp,prefix);
2152:   return(0);
2153: }

2157: /*@C
2158:    SNESAppendOptionsPrefix - Appends to the prefix used for searching for all 
2159:    SNES options in the database.

2161:    Collective on SNES

2163:    Input Parameters:
2164: +  snes - the SNES context
2165: -  prefix - the prefix to prepend to all option names

2167:    Notes:
2168:    A hyphen (-) must NOT be given at the beginning of the prefix name.
2169:    The first character of all runtime options is AUTOMATICALLY the hyphen.

2171:    Level: advanced

2173: .keywords: SNES, append, options, prefix, database

2175: .seealso: SNESGetOptionsPrefix()
2176: @*/
2177: PetscErrorCode  SNESAppendOptionsPrefix(SNES snes,const char prefix[])
2178: {
2180: 
2183:   PetscObjectAppendOptionsPrefix((PetscObject)snes,prefix);
2184:   KSPAppendOptionsPrefix(snes->ksp,prefix);
2185:   return(0);
2186: }

2190: /*@C
2191:    SNESGetOptionsPrefix - Sets the prefix used for searching for all 
2192:    SNES options in the database.

2194:    Not Collective

2196:    Input Parameter:
2197: .  snes - the SNES context

2199:    Output Parameter:
2200: .  prefix - pointer to the prefix string used

2202:    Notes: On the fortran side, the user should pass in a string 'prifix' of
2203:    sufficient length to hold the prefix.

2205:    Level: advanced

2207: .keywords: SNES, get, options, prefix, database

2209: .seealso: SNESAppendOptionsPrefix()
2210: @*/
2211: PetscErrorCode  SNESGetOptionsPrefix(SNES snes,const char *prefix[])
2212: {

2217:   PetscObjectGetOptionsPrefix((PetscObject)snes,prefix);
2218:   return(0);
2219: }


2224: /*@C
2225:   SNESRegister - See SNESRegisterDynamic()

2227:   Level: advanced
2228: @*/
2229: PetscErrorCode  SNESRegister(const char sname[],const char path[],const char name[],PetscErrorCode (*function)(SNES))
2230: {
2231:   char           fullname[PETSC_MAX_PATH_LEN];

2235:   PetscFListConcat(path,name,fullname);
2236:   PetscFListAdd(&SNESList,sname,fullname,(void (*)(void))function);
2237:   return(0);
2238: }

2242: PetscErrorCode  SNESTestLocalMin(SNES snes)
2243: {
2245:   PetscInt       N,i,j;
2246:   Vec            u,uh,fh;
2247:   PetscScalar    value;
2248:   PetscReal      norm;

2251:   SNESGetSolution(snes,&u);
2252:   VecDuplicate(u,&uh);
2253:   VecDuplicate(u,&fh);

2255:   /* currently only works for sequential */
2256:   PetscPrintf(PETSC_COMM_WORLD,"Testing FormFunction() for local min\n");
2257:   VecGetSize(u,&N);
2258:   for (i=0; i<N; i++) {
2259:     VecCopy(u,uh);
2260:     PetscPrintf(PETSC_COMM_WORLD,"i = %D\n",i);
2261:     for (j=-10; j<11; j++) {
2262:       value = PetscSign(j)*exp(PetscAbs(j)-10.0);
2263:       VecSetValue(uh,i,value,ADD_VALUES);
2264:       SNESComputeFunction(snes,uh,fh);
2265:       VecNorm(fh,NORM_2,&norm);
2266:       PetscPrintf(PETSC_COMM_WORLD,"       j norm %D %18.16e\n",j,norm);
2267:       value = -value;
2268:       VecSetValue(uh,i,value,ADD_VALUES);
2269:     }
2270:   }
2271:   VecDestroy(uh);
2272:   VecDestroy(fh);
2273:   return(0);
2274: }

2278: /*@
2279:    SNESKSPSetUseEW - Sets SNES use Eisenstat-Walker method for
2280:    computing relative tolerance for linear solvers within an inexact
2281:    Newton method.

2283:    Collective on SNES

2285:    Input Parameters:
2286: +  snes - SNES context
2287: -  flag - PETSC_TRUE or PETSC_FALSE

2289:    Notes:
2290:    Currently, the default is to use a constant relative tolerance for 
2291:    the inner linear solvers.  Alternatively, one can use the 
2292:    Eisenstat-Walker method, where the relative convergence tolerance 
2293:    is reset at each Newton iteration according progress of the nonlinear 
2294:    solver. 

2296:    Level: advanced

2298:    Reference:
2299:    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an 
2300:    inexact Newton method", SISC 17 (1), pp.16-32, 1996.

2302: .keywords: SNES, KSP, Eisenstat, Walker, convergence, test, inexact, Newton

2304: .seealso: SNESKSPGetUseEW(), SNESKSPGetParametersEW(), SNESKSPSetParametersEW()
2305: @*/
2306: PetscErrorCode  SNESKSPSetUseEW(SNES snes,PetscTruth flag)
2307: {
2310:   snes->ksp_ewconv = flag;
2311:   return(0);
2312: }

2316: /*@
2317:    SNESKSPGetUseEW - Gets if SNES is using Eisenstat-Walker method
2318:    for computing relative tolerance for linear solvers within an
2319:    inexact Newton method.

2321:    Not Collective

2323:    Input Parameter:
2324: .  snes - SNES context

2326:    Output Parameter:
2327: .  flag - PETSC_TRUE or PETSC_FALSE

2329:    Notes:
2330:    Currently, the default is to use a constant relative tolerance for 
2331:    the inner linear solvers.  Alternatively, one can use the 
2332:    Eisenstat-Walker method, where the relative convergence tolerance 
2333:    is reset at each Newton iteration according progress of the nonlinear 
2334:    solver. 

2336:    Level: advanced

2338:    Reference:
2339:    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an 
2340:    inexact Newton method", SISC 17 (1), pp.16-32, 1996.

2342: .keywords: SNES, KSP, Eisenstat, Walker, convergence, test, inexact, Newton

2344: .seealso: SNESKSPSetUseEW(), SNESKSPGetParametersEW(), SNESKSPSetParametersEW()
2345: @*/
2346: PetscErrorCode  SNESKSPGetUseEW(SNES snes, PetscTruth *flag)
2347: {
2351:   *flag = snes->ksp_ewconv;
2352:   return(0);
2353: }

2357: /*@
2358:    SNESKSPSetParametersEW - Sets parameters for Eisenstat-Walker
2359:    convergence criteria for the linear solvers within an inexact
2360:    Newton method.

2362:    Collective on SNES
2363:  
2364:    Input Parameters:
2365: +    snes - SNES context
2366: .    version - version 1, 2 (default is 2) or 3
2367: .    rtol_0 - initial relative tolerance (0 <= rtol_0 < 1)
2368: .    rtol_max - maximum relative tolerance (0 <= rtol_max < 1)
2369: .    gamma - multiplicative factor for version 2 rtol computation
2370:              (0 <= gamma2 <= 1)
2371: .    alpha - power for version 2 rtol computation (1 < alpha <= 2)
2372: .    alpha2 - power for safeguard
2373: -    threshold - threshold for imposing safeguard (0 < threshold < 1)

2375:    Note:
2376:    Version 3 was contributed by Luis Chacon, June 2006.

2378:    Use PETSC_DEFAULT to retain the default for any of the parameters.

2380:    Level: advanced

2382:    Reference:
2383:    S. C. Eisenstat and H. F. Walker, "Choosing the forcing terms in an 
2384:    inexact Newton method", Utah State University Math. Stat. Dept. Res. 
2385:    Report 6/94/75, June, 1994, to appear in SIAM J. Sci. Comput. 

2387: .keywords: SNES, KSP, Eisenstat, Walker, set, parameters

2389: .seealso: SNESKSPSetUseEW(), SNESKSPGetUseEW(), SNESKSPGetParametersEW()
2390: @*/
2391: PetscErrorCode  SNESKSPSetParametersEW(SNES snes,PetscInt version,PetscReal rtol_0,PetscReal rtol_max,
2392:                                                             PetscReal gamma,PetscReal alpha,PetscReal alpha2,PetscReal threshold)
2393: {
2394:   SNESKSPEW *kctx;
2397:   kctx = (SNESKSPEW*)snes->kspconvctx;
2398:   if (!kctx) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context existing");

2400:   if (version != PETSC_DEFAULT)   kctx->version   = version;
2401:   if (rtol_0 != PETSC_DEFAULT)    kctx->rtol_0    = rtol_0;
2402:   if (rtol_max != PETSC_DEFAULT)  kctx->rtol_max  = rtol_max;
2403:   if (gamma != PETSC_DEFAULT)     kctx->gamma     = gamma;
2404:   if (alpha != PETSC_DEFAULT)     kctx->alpha     = alpha;
2405:   if (alpha2 != PETSC_DEFAULT)    kctx->alpha2    = alpha2;
2406:   if (threshold != PETSC_DEFAULT) kctx->threshold = threshold;
2407: 
2408:   if (kctx->version < 1 || kctx->version > 3) {
2409:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Only versions 1, 2 and 3 are supported: %D",kctx->version);
2410:   }
2411:   if (kctx->rtol_0 < 0.0 || kctx->rtol_0 >= 1.0) {
2412:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= rtol_0 < 1.0: %G",kctx->rtol_0);
2413:   }
2414:   if (kctx->rtol_max < 0.0 || kctx->rtol_max >= 1.0) {
2415:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= rtol_max (%G) < 1.0\n",kctx->rtol_max);
2416:   }
2417:   if (kctx->gamma < 0.0 || kctx->gamma > 1.0) {
2418:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"0.0 <= gamma (%G) <= 1.0\n",kctx->gamma);
2419:   }
2420:   if (kctx->alpha <= 1.0 || kctx->alpha > 2.0) {
2421:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"1.0 < alpha (%G) <= 2.0\n",kctx->alpha);
2422:   }
2423:   if (kctx->threshold <= 0.0 || kctx->threshold >= 1.0) {
2424:     SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"0.0 < threshold (%G) < 1.0\n",kctx->threshold);
2425:   }
2426:   return(0);
2427: }

2431: /*@
2432:    SNESKSPGetParametersEW - Gets parameters for Eisenstat-Walker
2433:    convergence criteria for the linear solvers within an inexact
2434:    Newton method.

2436:    Not Collective
2437:  
2438:    Input Parameters:
2439:      snes - SNES context

2441:    Output Parameters:
2442: +    version - version 1, 2 (default is 2) or 3
2443: .    rtol_0 - initial relative tolerance (0 <= rtol_0 < 1)
2444: .    rtol_max - maximum relative tolerance (0 <= rtol_max < 1)
2445: .    gamma - multiplicative factor for version 2 rtol computation
2446:              (0 <= gamma2 <= 1)
2447: .    alpha - power for version 2 rtol computation (1 < alpha <= 2)
2448: .    alpha2 - power for safeguard
2449: -    threshold - threshold for imposing safeguard (0 < threshold < 1)

2451:    Level: advanced

2453: .keywords: SNES, KSP, Eisenstat, Walker, get, parameters

2455: .seealso: SNESKSPSetUseEW(), SNESKSPGetUseEW(), SNESKSPSetParametersEW()
2456: @*/
2457: PetscErrorCode  SNESKSPGetParametersEW(SNES snes,PetscInt *version,PetscReal *rtol_0,PetscReal *rtol_max,
2458:                                                             PetscReal *gamma,PetscReal *alpha,PetscReal *alpha2,PetscReal *threshold)
2459: {
2460:   SNESKSPEW *kctx;
2463:   kctx = (SNESKSPEW*)snes->kspconvctx;
2464:   if (!kctx) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context existing");
2465:   if(version)   *version   = kctx->version;
2466:   if(rtol_0)    *rtol_0    = kctx->rtol_0;
2467:   if(rtol_max)  *rtol_max  = kctx->rtol_max;
2468:   if(gamma)     *gamma     = kctx->gamma;
2469:   if(alpha)     *alpha     = kctx->alpha;
2470:   if(alpha2)    *alpha2    = kctx->alpha2;
2471:   if(threshold) *threshold = kctx->threshold;
2472:   return(0);
2473: }

2477: static PetscErrorCode SNESKSPEW_PreSolve(SNES snes, KSP ksp, Vec b, Vec x)
2478: {
2480:   SNESKSPEW      *kctx = (SNESKSPEW*)snes->kspconvctx;
2481:   PetscReal      rtol=PETSC_DEFAULT,stol;

2484:   if (!kctx) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context exists");
2485:   if (!snes->iter) { /* first time in, so use the original user rtol */
2486:     rtol = kctx->rtol_0;
2487:   } else {
2488:     if (kctx->version == 1) {
2489:       rtol = (snes->norm - kctx->lresid_last)/kctx->norm_last;
2490:       if (rtol < 0.0) rtol = -rtol;
2491:       stol = pow(kctx->rtol_last,kctx->alpha2);
2492:       if (stol > kctx->threshold) rtol = PetscMax(rtol,stol);
2493:     } else if (kctx->version == 2) {
2494:       rtol = kctx->gamma * pow(snes->norm/kctx->norm_last,kctx->alpha);
2495:       stol = kctx->gamma * pow(kctx->rtol_last,kctx->alpha);
2496:       if (stol > kctx->threshold) rtol = PetscMax(rtol,stol);
2497:     } else if (kctx->version == 3) {/* contributed by Luis Chacon, June 2006. */
2498:       rtol = kctx->gamma * pow(snes->norm/kctx->norm_last,kctx->alpha);
2499:       /* safeguard: avoid sharp decrease of rtol */
2500:       stol = kctx->gamma*pow(kctx->rtol_last,kctx->alpha);
2501:       stol = PetscMax(rtol,stol);
2502:       rtol = PetscMin(kctx->rtol_0,stol);
2503:       /* safeguard: avoid oversolving */
2504:       stol = kctx->gamma*(snes->ttol)/snes->norm;
2505:       stol = PetscMax(rtol,stol);
2506:       rtol = PetscMin(kctx->rtol_0,stol);
2507:     } else SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Only versions 1, 2 or 3 are supported: %D",kctx->version);
2508:   }
2509:   /* safeguard: avoid rtol greater than one */
2510:   rtol = PetscMin(rtol,kctx->rtol_max);
2511:   KSPSetTolerances(ksp,rtol,PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT);
2512:   PetscInfo3(snes,"iter %D, Eisenstat-Walker (version %D) KSP rtol=%G\n",snes->iter,kctx->version,rtol);
2513:   return(0);
2514: }

2518: static PetscErrorCode SNESKSPEW_PostSolve(SNES snes, KSP ksp, Vec b, Vec x)
2519: {
2521:   SNESKSPEW      *kctx = (SNESKSPEW*)snes->kspconvctx;
2522:   PCSide         pcside;
2523:   Vec            lres;

2526:   if (!kctx) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"No Eisenstat-Walker context exists");
2527:   KSPGetTolerances(ksp,&kctx->rtol_last,0,0,0);
2528:   SNESGetFunctionNorm(snes,&kctx->norm_last);
2529:   if (kctx->version == 1) {
2530:     KSPGetPreconditionerSide(ksp,&pcside);
2531:     if (pcside == PC_RIGHT) { /* XXX Should we also test KSP_UNPRECONDITIONED_NORM ? */
2532:       /* KSP residual is true linear residual */
2533:       KSPGetResidualNorm(ksp,&kctx->lresid_last);
2534:     } else {
2535:       /* KSP residual is preconditioned residual */
2536:       /* compute true linear residual norm */
2537:       VecDuplicate(b,&lres);
2538:       MatMult(snes->jacobian,x,lres);
2539:       VecAYPX(lres,-1.0,b);
2540:       VecNorm(lres,NORM_2,&kctx->lresid_last);
2541:       VecDestroy(lres);
2542:     }
2543:   }
2544:   return(0);
2545: }

2549: PetscErrorCode SNES_KSPSolve(SNES snes, KSP ksp, Vec b, Vec x)
2550: {

2554:   if (snes->ksp_ewconv) { SNESKSPEW_PreSolve(snes,ksp,b,x);  }
2555:   KSPSolve(ksp,b,x);
2556:   if (snes->ksp_ewconv) { SNESKSPEW_PostSolve(snes,ksp,b,x); }
2557:   return(0);
2558: }