xref: /petsc/src/snes/impls/tr/tr.c (revision 9c49e667ad4da7e0d52938e36847e76419c5ab11)
14800dd8cSBarry Smith #ifndef lint
2*9c49e667SLois Curfman McInnes static char vcid[] = "$Id: tr.c,v 1.19 1995/07/27 03:00:58 curfman Exp curfman $";
34800dd8cSBarry Smith #endif
44800dd8cSBarry Smith 
54800dd8cSBarry Smith #include <math.h>
6fbe28522SBarry Smith #include "tr.h"
7a935fc98SLois Curfman McInnes #include "pviewer.h"
84800dd8cSBarry Smith 
9fbe28522SBarry Smith /*
10df60cc22SBarry Smith    This convergence test determines if the two norm of the
11df60cc22SBarry Smith    solution lies outside the trust region, if so it halts.
12df60cc22SBarry Smith */
13*9c49e667SLois Curfman McInnes int SNES_TR_KSPConverged_Private(KSP ksp,int n, double rnorm, void *ctx)
14df60cc22SBarry Smith {
15df60cc22SBarry Smith   SNES    snes = (SNES) ctx;
16df60cc22SBarry Smith   SNES_TR *neP = (SNES_TR*)snes->data;
17df60cc22SBarry Smith   double  rtol,atol,dtol,norm;
18df60cc22SBarry Smith   Vec     x;
1925c7317fSLois Curfman McInnes   int     ierr, mkit;
20df60cc22SBarry Smith 
2125c7317fSLois Curfman McInnes   KSPGetTolerances(ksp,&rtol,&atol,&dtol,&mkit);
22df60cc22SBarry Smith 
23df60cc22SBarry Smith   if ( n == 0 ) {
24*9c49e667SLois Curfman McInnes     neP->ttol   = PETSCMAX(rtol*rnorm,atol);
25df60cc22SBarry Smith     neP->rnorm0 = rnorm;
26df60cc22SBarry Smith   }
27df60cc22SBarry Smith   if ( rnorm <= neP->ttol )      return 1;
28df60cc22SBarry Smith   if ( rnorm >= dtol*neP->rnorm0 || rnorm != rnorm) return -1;
29df60cc22SBarry Smith 
30a935fc98SLois Curfman McInnes   /* Determine norm of solution */
3178b31e54SBarry Smith   ierr = KSPBuildSolution(ksp,0,&x); CHKERRQ(ierr);
3278b31e54SBarry Smith   ierr = VecNorm(x,&norm); CHKERRQ(ierr);
33df60cc22SBarry Smith   if (norm >= neP->delta) {
34a935fc98SLois Curfman McInnes     PLogInfo((PetscObject)snes,
35a935fc98SLois Curfman McInnes       "Ending linear iteration early, delta %g length %g\n",neP->delta,norm);
36df60cc22SBarry Smith     return 1;
37df60cc22SBarry Smith   }
38df60cc22SBarry Smith   return(0);
39df60cc22SBarry Smith }
40df60cc22SBarry Smith /*
41ddbbdb52SLois Curfman McInnes    SNESSolve_TR - Implements Newton's Method with a very simple trust
42ddbbdb52SLois Curfman McInnes    region approach for solving systems of nonlinear equations.
434800dd8cSBarry Smith 
444800dd8cSBarry Smith    The basic algorithm is taken from "The Minpack Project", by More',
454800dd8cSBarry Smith    Sorensen, Garbow, Hillstrom, pages 88-111 of "Sources and Development
46ddbbdb52SLois Curfman McInnes    of Mathematical Software", Wayne Cowell, editor.
47ddbbdb52SLois Curfman McInnes 
484800dd8cSBarry Smith    This is intended as a model implementation, since it does not
494800dd8cSBarry Smith    necessarily have many of the bells and whistles of other
504800dd8cSBarry Smith    implementations.
514800dd8cSBarry Smith */
52fbe28522SBarry Smith static int SNESSolve_TR(SNES snes,int *its)
534800dd8cSBarry Smith {
54fbe28522SBarry Smith   SNES_TR      *neP = (SNES_TR *) snes->data;
556b5873e3SBarry Smith   Vec          X, F, Y, G, TMP, Ytmp;
56ddbbdb52SLois Curfman McInnes   int          maxits, i, history_len, ierr, lits;
57df60cc22SBarry Smith   MatStructure flg = ALLMAT_DIFFERENT_NONZERO_PATTERN;
58fbe28522SBarry Smith   double       rho, fnorm, gnorm, gpnorm, xnorm, delta,norm;
594800dd8cSBarry Smith   double       *history, ynorm;
60eafb4bcbSBarry Smith   Scalar       one = 1.0,cnorm;
61df60cc22SBarry Smith   KSP          ksp;
62df60cc22SBarry Smith   SLES         sles;
634800dd8cSBarry Smith 
64fbe28522SBarry Smith   history	= snes->conv_hist;	/* convergence history */
65fbe28522SBarry Smith   history_len	= snes->conv_hist_len;	/* convergence history length */
66fbe28522SBarry Smith   maxits	= snes->max_its;	/* maximum number of iterations */
67fbe28522SBarry Smith   X		= snes->vec_sol;	/* solution vector */
6839e2f89bSBarry Smith   F		= snes->vec_func;	/* residual vector */
69fbe28522SBarry Smith   Y		= snes->work[0];	/* work vectors */
70fbe28522SBarry Smith   G		= snes->work[1];
716b5873e3SBarry Smith   Ytmp          = snes->work[2];
724800dd8cSBarry Smith 
7378b31e54SBarry Smith   ierr = SNESComputeInitialGuess(snes,X); CHKERRQ(ierr);  /* X <- X_0 */
74fbe28522SBarry Smith   VecNorm(X, &xnorm ); 		/* xnorm = || X || */
754800dd8cSBarry Smith 
7678b31e54SBarry Smith   ierr = SNESComputeFunction(snes,X,F); CHKERRQ(ierr); /* (+/-) F(X) */
77fbe28522SBarry Smith   VecNorm(F, &fnorm );		/* fnorm <- || F || */
78fbe28522SBarry Smith   snes->norm = fnorm;
794800dd8cSBarry Smith   if (history && history_len > 0) history[0] = fnorm;
804800dd8cSBarry Smith   delta = neP->delta0*fnorm;
814800dd8cSBarry Smith   neP->delta = delta;
82bbb6d6a8SBarry Smith   if (snes->monitor)
83bbb6d6a8SBarry Smith     {ierr = (*snes->monitor)(snes,0,fnorm,snes->monP); CHKERRQ(ierr);}
844800dd8cSBarry Smith 
85a935fc98SLois Curfman McInnes   /* Set the stopping criteria to use the More' trick. */
8678b31e54SBarry Smith   ierr = SNESGetSLES(snes,&sles); CHKERRQ(ierr);
8778b31e54SBarry Smith   ierr = SLESGetKSP(sles,&ksp); CHKERRQ(ierr);
88*9c49e667SLois Curfman McInnes   ierr = KSPSetConvergenceTest(ksp,SNES_TR_KSPConverged_Private,(void *)snes);
8978b31e54SBarry Smith   CHKERRQ(ierr);
90df60cc22SBarry Smith 
914800dd8cSBarry Smith   for ( i=0; i<maxits; i++ ) {
92fbe28522SBarry Smith      snes->iter = i+1;
93df60cc22SBarry Smith      ierr = SNESComputeJacobian(snes,X,&snes->jacobian,&snes->jacobian_pre,
94bbb6d6a8SBarry Smith                                              &flg); CHKERRQ(ierr);
95a935fc98SLois Curfman McInnes      ierr = SLESSetOperators(snes->sles,snes->jacobian,snes->jacobian_pre,
96a935fc98SLois Curfman McInnes                             flg); CHKERRQ(ierr);
9778b31e54SBarry Smith      ierr = SLESSolve(snes->sles,F,Ytmp,&lits); CHKERRQ(ierr);
986b5873e3SBarry Smith      VecNorm( Ytmp, &norm );
996b5873e3SBarry Smith      while(1) {
1006b5873e3SBarry Smith        VecCopy(Ytmp,Y);
101fbe28522SBarry Smith        /* Scale Y if need be and predict new value of F norm */
1026b5873e3SBarry Smith 
103eafb4bcbSBarry Smith        if (norm >= delta) {
104fbe28522SBarry Smith          norm = delta/norm;
105fbe28522SBarry Smith          gpnorm = (1.0 - norm)*fnorm;
106eafb4bcbSBarry Smith          cnorm = norm;
107df60cc22SBarry Smith          PLogInfo((PetscObject)snes, "Scaling direction by %g \n",norm );
108eafb4bcbSBarry Smith          VecScale( &cnorm, Y );
109eafb4bcbSBarry Smith          norm = gpnorm;
110fbe28522SBarry Smith          ynorm = delta;
111fbe28522SBarry Smith        } else {
112fbe28522SBarry Smith          gpnorm = 0.0;
113fbe28522SBarry Smith          PLogInfo((PetscObject)snes,"Direction is in Trust Region \n" );
114fbe28522SBarry Smith          ynorm = norm;
115fbe28522SBarry Smith        }
116fbe28522SBarry Smith        VecAXPY(&one, X, Y );	/* Y <- X + Y */
11781b6cf68SLois Curfman McInnes        ierr = VecCopy(X,snes->vec_sol_update_always); CHKERRQ(ierr);
11878b31e54SBarry Smith        ierr = SNESComputeFunction(snes,Y,G); CHKERRQ(ierr); /* (+/-) F(X) */
119fbe28522SBarry Smith        VecNorm( G, &gnorm );	/* gnorm <- || g || */
1204800dd8cSBarry Smith        if (fnorm == gpnorm) rho = 0.0;
121fbe28522SBarry Smith        else rho = (fnorm*fnorm - gnorm*gnorm)/(fnorm*fnorm - gpnorm*gpnorm);
1224800dd8cSBarry Smith 
1234800dd8cSBarry Smith        /* Update size of trust region */
1244800dd8cSBarry Smith        if      (rho < neP->mu)  delta *= neP->delta1;
1254800dd8cSBarry Smith        else if (rho < neP->eta) delta *= neP->delta2;
1264800dd8cSBarry Smith        else                     delta *= neP->delta3;
1274800dd8cSBarry Smith 
128fbe28522SBarry Smith        PLogInfo((PetscObject)snes,"%d:  f_norm=%g, g_norm=%g, ynorm=%g\n",
1294800dd8cSBarry Smith                                              i, fnorm, gnorm, ynorm );
130fbe28522SBarry Smith        PLogInfo((PetscObject)snes,"gpred=%g, rho=%g, delta=%g,iters=%d\n",
131fbe28522SBarry Smith                                                gpnorm, rho, delta, lits);
1324800dd8cSBarry Smith 
1334800dd8cSBarry Smith        neP->delta = delta;
1344800dd8cSBarry Smith        if (rho > neP->sigma) break;
135eafb4bcbSBarry Smith        PLogInfo((PetscObject)snes,"Trying again in smaller region\n");
1366b5873e3SBarry Smith        /* check to see if progress is hopeless */
13752392280SLois Curfman McInnes        neP->itflag = 0;
13852392280SLois Curfman McInnes        if ((*snes->converged)(snes,xnorm,ynorm,fnorm,snes->cnvP)) {
13952392280SLois Curfman McInnes          /* We're not progressing, so return with the current iterate */
14052392280SLois Curfman McInnes          if (X != snes->vec_sol) {
14152392280SLois Curfman McInnes            VecCopy(X,snes->vec_sol);
14252392280SLois Curfman McInnes            snes->vec_sol_always = snes->vec_sol;
14352392280SLois Curfman McInnes            snes->vec_func_always = snes->vec_func;
14452392280SLois Curfman McInnes          }
14552392280SLois Curfman McInnes        }
14652392280SLois Curfman McInnes        snes->nfailures++;
1474800dd8cSBarry Smith      }
1484800dd8cSBarry Smith      fnorm = gnorm;
149fbe28522SBarry Smith      snes->norm = fnorm;
1504800dd8cSBarry Smith      if (history && history_len > i+1) history[i+1] = fnorm;
15139e2f89bSBarry Smith      TMP = F; F = G; snes->vec_func_always = F; G = TMP;
15239e2f89bSBarry Smith      TMP = X; X = Y; snes->vec_sol_always = X; Y = TMP;
153fbe28522SBarry Smith      VecNorm(X, &xnorm );		/* xnorm = || X || */
154bbb6d6a8SBarry Smith      if (snes->monitor)
155bbb6d6a8SBarry Smith        {(*snes->monitor)(snes,i+1,fnorm,snes->monP); CHKERRQ(ierr);}
1564800dd8cSBarry Smith 
1574800dd8cSBarry Smith      /* Test for convergence */
15852392280SLois Curfman McInnes      neP->itflag = 1;
159bbb6d6a8SBarry Smith      if ((*snes->converged)( snes, xnorm, ynorm, fnorm,snes->cnvP )) {
1604800dd8cSBarry Smith        /* Verify solution is in corect location */
16139e2f89bSBarry Smith        if (X != snes->vec_sol) {
16239e2f89bSBarry Smith          VecCopy(X,snes->vec_sol);
16339e2f89bSBarry Smith          snes->vec_sol_always = snes->vec_sol;
16439e2f89bSBarry Smith          snes->vec_func_always = snes->vec_func;
16539e2f89bSBarry Smith        }
1664800dd8cSBarry Smith        break;
1674800dd8cSBarry Smith      }
1684800dd8cSBarry Smith    }
16952392280SLois Curfman McInnes   if (i == maxits) {
17052392280SLois Curfman McInnes     PLogInfo((PetscObject)snes,
17152392280SLois Curfman McInnes       "Maximum number of iterations has been reached: %d\n",maxits);
17252392280SLois Curfman McInnes     i--;
17352392280SLois Curfman McInnes   }
17452392280SLois Curfman McInnes   *its = i+1;
175fbe28522SBarry Smith   return 0;
1764800dd8cSBarry Smith }
1774800dd8cSBarry Smith /*------------------------------------------------------------*/
178fbe28522SBarry Smith static int SNESSetUp_TR( SNES snes )
1794800dd8cSBarry Smith {
180fbe28522SBarry Smith   int ierr;
18181b6cf68SLois Curfman McInnes   snes->nwork = 4;
18278b31e54SBarry Smith   ierr = VecGetVecs(snes->vec_sol,snes->nwork,&snes->work ); CHKERRQ(ierr);
18381b6cf68SLois Curfman McInnes   snes->vec_sol_update_always = snes->work[3];
184fbe28522SBarry Smith   return 0;
1854800dd8cSBarry Smith }
1864800dd8cSBarry Smith /*------------------------------------------------------------*/
187fbe28522SBarry Smith static int SNESDestroy_TR(PetscObject obj )
1884800dd8cSBarry Smith {
189fbe28522SBarry Smith   SNES snes = (SNES) obj;
190fbe28522SBarry Smith   VecFreeVecs(snes->work, snes->nwork );
19178b31e54SBarry Smith   PETSCFREE(snes->data);
192fbe28522SBarry Smith   return 0;
1934800dd8cSBarry Smith }
1944800dd8cSBarry Smith /*------------------------------------------------------------*/
1954800dd8cSBarry Smith 
196fbe28522SBarry Smith static int SNESSetFromOptions_TR(SNES snes)
1974800dd8cSBarry Smith {
198fbe28522SBarry Smith   SNES_TR *ctx = (SNES_TR *)snes->data;
199fbe28522SBarry Smith   double  tmp;
2004800dd8cSBarry Smith 
201df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-mu",&tmp)) {ctx->mu = tmp;}
202df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-eta",&tmp)) {ctx->eta = tmp;}
203df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-sigma",&tmp)) {ctx->sigma = tmp;}
204df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-delta0",&tmp)) {ctx->delta0 = tmp;}
205df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-delta1",&tmp)) {ctx->delta1 = tmp;}
206df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-delta2",&tmp)) {ctx->delta2 = tmp;}
207df60cc22SBarry Smith   if (OptionsGetDouble(snes->prefix,"-delta3",&tmp)) {ctx->delta3 = tmp;}
208fbe28522SBarry Smith   return 0;
2094800dd8cSBarry Smith }
2104800dd8cSBarry Smith 
211fbe28522SBarry Smith static int SNESPrintHelp_TR(SNES snes)
2124800dd8cSBarry Smith {
213fbe28522SBarry Smith   SNES_TR *ctx = (SNES_TR *)snes->data;
21452392280SLois Curfman McInnes   char    *p;
21552392280SLois Curfman McInnes   if (snes->prefix) p = snes->prefix; else p = "-";
21652392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout," method tr (system of nonlinear equations):\n");
21752392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_mu mu (default %g)\n",p,ctx->mu);
21852392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_eta eta (default %g)\n",p,ctx->eta);
21952392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_sigma sigma (default %g)\n",p,ctx->sigma);
22052392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_delta0 delta0 (default %g)\n",p,ctx->delta0);
22152392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_delta1 delta1 (default %g)\n",p,ctx->delta1);
22252392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_delta2 delta2 (default %g)\n",p,ctx->delta2);
22352392280SLois Curfman McInnes   MPIU_fprintf(snes->comm,stdout,"   %ssnes_trust_region_delta3 delta3 (default %g)\n",p,ctx->delta3);
224fbe28522SBarry Smith   return 0;
2254800dd8cSBarry Smith }
2264800dd8cSBarry Smith 
227a935fc98SLois Curfman McInnes static int SNESView_TR(PetscObject obj,Viewer viewer)
228a935fc98SLois Curfman McInnes {
229a935fc98SLois Curfman McInnes   SNES    snes = (SNES)obj;
230a935fc98SLois Curfman McInnes   SNES_TR *tr = (SNES_TR *)snes->data;
231a935fc98SLois Curfman McInnes   FILE    *fd = ViewerFileGetPointer_Private(viewer);
232a935fc98SLois Curfman McInnes 
233a935fc98SLois Curfman McInnes   MPIU_fprintf(snes->comm,fd,"    mu=%g, eta=%g, sigma=%g\n",
234a935fc98SLois Curfman McInnes     tr->mu,tr->eta,tr->sigma);
235a935fc98SLois Curfman McInnes   MPIU_fprintf(snes->comm,fd,
236a935fc98SLois Curfman McInnes     "    delta0=%g, delta1=%g, delta2=%g, delta3=%g\n",
237a935fc98SLois Curfman McInnes     tr->delta0,tr->delta1,tr->delta2,tr->delta3);
238a935fc98SLois Curfman McInnes   return 0;
239a935fc98SLois Curfman McInnes }
240a935fc98SLois Curfman McInnes 
24152392280SLois Curfman McInnes /* ---------------------------------------------------------------- */
24252392280SLois Curfman McInnes /*@
24352392280SLois Curfman McInnes    SNESTrustRegionDefaultConverged - Default test for monitoring the
24452392280SLois Curfman McInnes    convergence of the trust region method SNES_EQ_TR for solving systems
24552392280SLois Curfman McInnes    of nonlinear equations.
24652392280SLois Curfman McInnes 
24752392280SLois Curfman McInnes    Input Parameters:
24852392280SLois Curfman McInnes .  snes - the SNES context
24952392280SLois Curfman McInnes .  xnorm - 2-norm of current iterate
25052392280SLois Curfman McInnes .  pnorm - 2-norm of current step
25152392280SLois Curfman McInnes .  fnorm - 2-norm of function
25252392280SLois Curfman McInnes .  dummy - unused context
25352392280SLois Curfman McInnes 
25452392280SLois Curfman McInnes    Returns:
25552392280SLois Curfman McInnes $  1  if  ( delta < xnorm*deltatol ),
25652392280SLois Curfman McInnes $  2  if  ( fnorm < atol ),
25752392280SLois Curfman McInnes $  3  if  ( pnorm < xtol*xnorm ),
25852392280SLois Curfman McInnes $ -2  if  ( nfct > maxf ),
25952392280SLois Curfman McInnes $ -1  if  ( delta < xnorm*epsmch ),
26052392280SLois Curfman McInnes $  0  otherwise,
26152392280SLois Curfman McInnes 
26252392280SLois Curfman McInnes    where
26352392280SLois Curfman McInnes $    delta    - trust region paramenter
26452392280SLois Curfman McInnes $    deltatol - trust region size tolerance,
26552392280SLois Curfman McInnes $               set with SNESSetTrustRegionTolerance()
26652392280SLois Curfman McInnes $    maxf - maximum number of function evaluations,
26752392280SLois Curfman McInnes $           set with SNESSetMaxFunctionEvaluations()
26852392280SLois Curfman McInnes $    nfct - number of function evaluations,
26952392280SLois Curfman McInnes $    atol - absolute function norm tolerance,
27052392280SLois Curfman McInnes $           set with SNESSetAbsoluteTolerance()
27152392280SLois Curfman McInnes $    xtol - relative function norm tolerance,
27252392280SLois Curfman McInnes $           set with SNESSetRelativeTolerance()
27352392280SLois Curfman McInnes 
27452392280SLois Curfman McInnes .keywords: SNES, nonlinear, default, converged, convergence
27552392280SLois Curfman McInnes 
27652392280SLois Curfman McInnes .seealso: SNESSetConvergenceTest(), SNESEisenstatWalkerConverged()
27752392280SLois Curfman McInnes @*/
27852392280SLois Curfman McInnes int SNESTrustRegionDefaultConverged(SNES snes,double xnorm,double pnorm,
27952392280SLois Curfman McInnes                          double fnorm,void *dummy)
28052392280SLois Curfman McInnes {
28152392280SLois Curfman McInnes   SNES_TR *neP = (SNES_TR *)snes->data;
28252392280SLois Curfman McInnes   double  epsmch = 1.0e-14;   /* This must be fixed */
28352392280SLois Curfman McInnes   int     info;
28452392280SLois Curfman McInnes   if (snes->method_class != SNES_NONLINEAR_EQUATIONS) SETERRQ(1,
28552392280SLois Curfman McInnes     "SNESDefaultConverged:For SNES_NONLINEAR_EQUATIONS method only");
28652392280SLois Curfman McInnes 
28752392280SLois Curfman McInnes   if (neP->delta < xnorm * snes->deltatol) {
28852392280SLois Curfman McInnes     PLogInfo((PetscObject)snes,
28952392280SLois Curfman McInnes       "SNES: Converged due to trust region param %g < %g * %g\n",neP->delta,
29052392280SLois Curfman McInnes        xnorm, snes->deltatol);
29152392280SLois Curfman McInnes     return 1;
29252392280SLois Curfman McInnes   }
29352392280SLois Curfman McInnes   if (neP->itflag) {
29452392280SLois Curfman McInnes     info = SNESDefaultConverged(snes,xnorm,pnorm,fnorm,dummy);
29552392280SLois Curfman McInnes     if (info) return info;
29652392280SLois Curfman McInnes   }
29752392280SLois Curfman McInnes   if (neP->delta < xnorm * epsmch) {
29852392280SLois Curfman McInnes     PLogInfo((PetscObject)snes,
29952392280SLois Curfman McInnes       "SNES: Converged due to trust region param %g < %g * %g\n",neP->delta,
30052392280SLois Curfman McInnes        xnorm, epsmch);
30152392280SLois Curfman McInnes     return -1;
30252392280SLois Curfman McInnes   }
30352392280SLois Curfman McInnes   return 0;
30452392280SLois Curfman McInnes }
30552392280SLois Curfman McInnes /* ------------------------------------------------------------ */
306fbe28522SBarry Smith int SNESCreate_TR(SNES snes )
3074800dd8cSBarry Smith {
308fbe28522SBarry Smith   SNES_TR *neP;
3094800dd8cSBarry Smith 
310369a4401SLois Curfman McInnes   if (snes->method_class != SNES_NONLINEAR_EQUATIONS) SETERRQ(1,
311369a4401SLois Curfman McInnes     "SNESCreate_TR: Valid for SNES_NONLINEAR_EQUATIONS problems only");
31225c7317fSLois Curfman McInnes   snes->type 		= SNES_EQ_NTR;
31306be10caSBarry Smith   snes->setup		= SNESSetUp_TR;
31406be10caSBarry Smith   snes->solve		= SNESSolve_TR;
315fbe28522SBarry Smith   snes->destroy		= SNESDestroy_TR;
31652392280SLois Curfman McInnes   snes->converged	= SNESTrustRegionDefaultConverged;
31706be10caSBarry Smith   snes->printhelp       = SNESPrintHelp_TR;
31806be10caSBarry Smith   snes->setfromoptions  = SNESSetFromOptions_TR;
319a935fc98SLois Curfman McInnes   snes->view            = SNESView_TR;
320fbe28522SBarry Smith 
32178b31e54SBarry Smith   neP			= PETSCNEW(SNES_TR); CHKPTRQ(neP);
322fbe28522SBarry Smith   snes->data	        = (void *) neP;
323fbe28522SBarry Smith   neP->mu		= 0.25;
324fbe28522SBarry Smith   neP->eta		= 0.75;
325fbe28522SBarry Smith   neP->delta		= 0.0;
326fbe28522SBarry Smith   neP->delta0		= 0.2;
327fbe28522SBarry Smith   neP->delta1		= 0.3;
328fbe28522SBarry Smith   neP->delta2		= 0.75;
329fbe28522SBarry Smith   neP->delta3		= 2.0;
330fbe28522SBarry Smith   neP->sigma		= 0.0001;
331fbe28522SBarry Smith   neP->itflag		= 0;
33252392280SLois Curfman McInnes   neP->rnorm0		= 0;
33352392280SLois Curfman McInnes   neP->ttol		= 0;
3346b5873e3SBarry Smith   return 0;
3354800dd8cSBarry Smith }
336