1 #define PETSCSNES_DLL 2 3 #include "src/snes/snesimpl.h" /*I "petscsnes.h" I*/ 4 5 PetscTruth SNESRegisterAllCalled = PETSC_FALSE; 6 PetscFList SNESList = PETSC_NULL; 7 8 /* Logging support */ 9 PetscCookie PETSCSNES_DLLEXPORT SNES_COOKIE = 0; 10 PetscEvent SNES_Solve = 0, SNES_LineSearch = 0, SNES_FunctionEval = 0, SNES_JacobianEval = 0; 11 12 #undef __FUNCT__ 13 #define __FUNCT__ "SNESView" 14 /*@C 15 SNESView - Prints the SNES data structure. 16 17 Collective on SNES 18 19 Input Parameters: 20 + SNES - the SNES context 21 - viewer - visualization context 22 23 Options Database Key: 24 . -snes_view - Calls SNESView() at end of SNESSolve() 25 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. 33 34 The user can open an alternative visualization context with 35 PetscViewerASCIIOpen() - output to a specified file. 36 37 Level: beginner 38 39 .keywords: SNES, view 40 41 .seealso: PetscViewerASCIIOpen() 42 @*/ 43 PetscErrorCode PETSCSNES_DLLEXPORT SNESView(SNES snes,PetscViewer viewer) 44 { 45 SNES_KSP_EW_ConvCtx *kctx; 46 PetscErrorCode ierr; 47 KSP ksp; 48 SNESType type; 49 PetscTruth iascii,isstring; 50 51 PetscFunctionBegin; 52 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 53 if (!viewer) viewer = PETSC_VIEWER_STDOUT_(snes->comm); 54 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_COOKIE,2); 55 PetscCheckSameComm(snes,1,viewer,2); 56 57 ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);CHKERRQ(ierr); 58 ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_STRING,&isstring);CHKERRQ(ierr); 59 if (iascii) { 60 if (snes->prefix) { 61 ierr = PetscViewerASCIIPrintf(viewer,"SNES Object:(%s)\n",snes->prefix);CHKERRQ(ierr); 62 } else { 63 ierr = PetscViewerASCIIPrintf(viewer,"SNES Object:\n");CHKERRQ(ierr); 64 } 65 ierr = SNESGetType(snes,&type);CHKERRQ(ierr); 66 if (type) { 67 ierr = PetscViewerASCIIPrintf(viewer," type: %s\n",type);CHKERRQ(ierr); 68 } else { 69 ierr = PetscViewerASCIIPrintf(viewer," type: not set yet\n");CHKERRQ(ierr); 70 } 71 if (snes->view) { 72 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 73 ierr = (*snes->view)(snes,viewer);CHKERRQ(ierr); 74 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 75 } 76 ierr = PetscViewerASCIIPrintf(viewer," maximum iterations=%D, maximum function evaluations=%D\n",snes->max_its,snes->max_funcs);CHKERRQ(ierr); 77 ierr = PetscViewerASCIIPrintf(viewer," tolerances: relative=%G, absolute=%G, solution=%G\n", 78 snes->rtol,snes->abstol,snes->xtol);CHKERRQ(ierr); 79 ierr = PetscViewerASCIIPrintf(viewer," total number of linear solver iterations=%D\n",snes->linear_its);CHKERRQ(ierr); 80 ierr = PetscViewerASCIIPrintf(viewer," total number of function evaluations=%D\n",snes->nfuncs);CHKERRQ(ierr); 81 if (snes->ksp_ewconv) { 82 kctx = (SNES_KSP_EW_ConvCtx *)snes->kspconvctx; 83 if (kctx) { 84 ierr = PetscViewerASCIIPrintf(viewer," Eisenstat-Walker computation of KSP relative tolerance (version %D)\n",kctx->version);CHKERRQ(ierr); 85 ierr = PetscViewerASCIIPrintf(viewer," rtol_0=%G, rtol_max=%G, threshold=%G\n",kctx->rtol_0,kctx->rtol_max,kctx->threshold);CHKERRQ(ierr); 86 ierr = PetscViewerASCIIPrintf(viewer," gamma=%G, alpha=%G, alpha2=%G\n",kctx->gamma,kctx->alpha,kctx->alpha2);CHKERRQ(ierr); 87 } 88 } 89 } else if (isstring) { 90 ierr = SNESGetType(snes,&type);CHKERRQ(ierr); 91 ierr = PetscViewerStringSPrintf(viewer," %-3.3s",type);CHKERRQ(ierr); 92 } 93 ierr = SNESGetKSP(snes,&ksp);CHKERRQ(ierr); 94 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 95 ierr = KSPView(ksp,viewer);CHKERRQ(ierr); 96 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 97 PetscFunctionReturn(0); 98 } 99 100 /* 101 We retain a list of functions that also take SNES command 102 line options. These are called at the end SNESSetFromOptions() 103 */ 104 #define MAXSETFROMOPTIONS 5 105 static PetscInt numberofsetfromoptions; 106 static PetscErrorCode (*othersetfromoptions[MAXSETFROMOPTIONS])(SNES); 107 108 #undef __FUNCT__ 109 #define __FUNCT__ "SNESAddOptionsChecker" 110 /*@C 111 SNESAddOptionsChecker - Adds an additional function to check for SNES options. 112 113 Not Collective 114 115 Input Parameter: 116 . snescheck - function that checks for options 117 118 Level: developer 119 120 .seealso: SNESSetFromOptions() 121 @*/ 122 PetscErrorCode PETSCSNES_DLLEXPORT SNESAddOptionsChecker(PetscErrorCode (*snescheck)(SNES)) 123 { 124 PetscFunctionBegin; 125 if (numberofsetfromoptions >= MAXSETFROMOPTIONS) { 126 SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE, "Too many options checkers, only %D allowed", MAXSETFROMOPTIONS); 127 } 128 othersetfromoptions[numberofsetfromoptions++] = snescheck; 129 PetscFunctionReturn(0); 130 } 131 132 #undef __FUNCT__ 133 #define __FUNCT__ "SNESSetFromOptions" 134 /*@ 135 SNESSetFromOptions - Sets various SNES and KSP parameters from user options. 136 137 Collective on SNES 138 139 Input Parameter: 140 . snes - the SNES context 141 142 Options Database Keys: 143 + -snes_type <type> - ls, tr, umls, umtr, test 144 . -snes_stol - convergence tolerance in terms of the norm 145 of the change in the solution between steps 146 . -snes_atol <abstol> - absolute tolerance of residual norm 147 . -snes_rtol <rtol> - relative decrease in tolerance norm from initial 148 . -snes_max_it <max_it> - maximum number of iterations 149 . -snes_max_funcs <max_funcs> - maximum number of function evaluations 150 . -snes_max_fail <max_fail> - maximum number of failures 151 . -snes_trtol <trtol> - trust region tolerance 152 . -snes_no_convergence_test - skip convergence test in nonlinear 153 solver; hence iterations will continue until max_it 154 or some other criterion is reached. Saves expense 155 of convergence test 156 . -snes_monitor <optional filename> - prints residual norm at each iteration. if no 157 filename given prints to stdout 158 . -snes_vecmonitor - plots solution at each iteration 159 . -snes_vecmonitor_update - plots update to solution at each iteration 160 . -snes_xmonitor - plots residual norm at each iteration 161 . -snes_fd - use finite differences to compute Jacobian; very slow, only for testing 162 . -snes_mf_ksp_monitor - if using matrix-free multiply then print h at each KSP iteration 163 - -snes_print_converged_reason - print the reason for convergence/divergence after each solve 164 165 Options Database for Eisenstat-Walker method: 166 + -snes_ksp_ew_conv - use Eisenstat-Walker method for determining linear system convergence 167 . -snes_ksp_ew_version ver - version of Eisenstat-Walker method 168 . -snes_ksp_ew_rtol0 <rtol0> - Sets rtol0 169 . -snes_ksp_ew_rtolmax <rtolmax> - Sets rtolmax 170 . -snes_ksp_ew_gamma <gamma> - Sets gamma 171 . -snes_ksp_ew_alpha <alpha> - Sets alpha 172 . -snes_ksp_ew_alpha2 <alpha2> - Sets alpha2 173 - -snes_ksp_ew_threshold <threshold> - Sets threshold 174 175 Notes: 176 To see all options, run your program with the -help option or consult 177 the users manual. 178 179 Level: beginner 180 181 .keywords: SNES, nonlinear, set, options, database 182 183 .seealso: SNESSetOptionsPrefix() 184 @*/ 185 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetFromOptions(SNES snes) 186 { 187 KSP ksp; 188 SNES_KSP_EW_ConvCtx *kctx = (SNES_KSP_EW_ConvCtx *)snes->kspconvctx; 189 PetscTruth flg; 190 PetscErrorCode ierr; 191 PetscInt i; 192 const char *deft; 193 char type[256], monfilename[PETSC_MAX_PATH_LEN]; 194 PetscViewer monviewer; 195 196 PetscFunctionBegin; 197 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 198 199 ierr = PetscOptionsBegin(snes->comm,snes->prefix,"Nonlinear solver (SNES) options","SNES");CHKERRQ(ierr); 200 if (snes->type_name) { 201 deft = snes->type_name; 202 } else { 203 deft = SNESLS; 204 } 205 206 if (!SNESRegisterAllCalled) {ierr = SNESRegisterAll(PETSC_NULL);CHKERRQ(ierr);} 207 ierr = PetscOptionsList("-snes_type","Nonlinear solver method","SNESSetType",SNESList,deft,type,256,&flg);CHKERRQ(ierr); 208 if (flg) { 209 ierr = SNESSetType(snes,type);CHKERRQ(ierr); 210 } else if (!snes->type_name) { 211 ierr = SNESSetType(snes,deft);CHKERRQ(ierr); 212 } 213 ierr = PetscOptionsName("-snes_view","Print detailed information on solver used","SNESView",0);CHKERRQ(ierr); 214 215 ierr = PetscOptionsReal("-snes_stol","Stop if step length less then","SNESSetTolerances",snes->xtol,&snes->xtol,0);CHKERRQ(ierr); 216 ierr = PetscOptionsReal("-snes_atol","Stop if function norm less then","SNESSetTolerances",snes->abstol,&snes->abstol,0);CHKERRQ(ierr); 217 218 ierr = PetscOptionsReal("-snes_rtol","Stop if decrease in function norm less then","SNESSetTolerances",snes->rtol,&snes->rtol,0);CHKERRQ(ierr); 219 ierr = PetscOptionsInt("-snes_max_it","Maximum iterations","SNESSetTolerances",snes->max_its,&snes->max_its,PETSC_NULL);CHKERRQ(ierr); 220 ierr = PetscOptionsInt("-snes_max_funcs","Maximum function evaluations","SNESSetTolerances",snes->max_funcs,&snes->max_funcs,PETSC_NULL);CHKERRQ(ierr); 221 ierr = PetscOptionsInt("-snes_max_fail","Maximum failures","SNESSetTolerances",snes->maxFailures,&snes->maxFailures,PETSC_NULL);CHKERRQ(ierr); 222 ierr = PetscOptionsName("-snes_converged_reason","Print reason for converged or diverged","SNESSolve",&flg);CHKERRQ(ierr); 223 if (flg) { 224 snes->printreason = PETSC_TRUE; 225 } 226 227 ierr = PetscOptionsTruth("-snes_ksp_ew_conv","Use Eisentat-Walker linear system convergence test","SNES_KSP_SetParametersEW",snes->ksp_ewconv,&snes->ksp_ewconv,PETSC_NULL);CHKERRQ(ierr); 228 229 ierr = PetscOptionsInt("-snes_ksp_ew_version","Version 1, 2 or 3","SNES_KSP_SetParametersEW",kctx->version,&kctx->version,0);CHKERRQ(ierr); 230 ierr = PetscOptionsReal("-snes_ksp_ew_rtol0","0 <= rtol0 < 1","SNES_KSP_SetParametersEW",kctx->rtol_0,&kctx->rtol_0,0);CHKERRQ(ierr); 231 ierr = PetscOptionsReal("-snes_ksp_ew_rtolmax","0 <= rtolmax < 1","SNES_KSP_SetParametersEW",kctx->rtol_max,&kctx->rtol_max,0);CHKERRQ(ierr); 232 ierr = PetscOptionsReal("-snes_ksp_ew_gamma","0 <= gamma <= 1","SNES_KSP_SetParametersEW",kctx->gamma,&kctx->gamma,0);CHKERRQ(ierr); 233 ierr = PetscOptionsReal("-snes_ksp_ew_alpha","1 < alpha <= 2","SNES_KSP_SetParametersEW",kctx->alpha,&kctx->alpha,0);CHKERRQ(ierr); 234 ierr = PetscOptionsReal("-snes_ksp_ew_alpha2","alpha2","SNES_KSP_SetParametersEW",kctx->alpha2,&kctx->alpha2,0);CHKERRQ(ierr); 235 ierr = PetscOptionsReal("-snes_ksp_ew_threshold","0 < threshold < 1","SNES_KSP_SetParametersEW",kctx->threshold,&kctx->threshold,0);CHKERRQ(ierr); 236 237 ierr = PetscOptionsName("-snes_no_convergence_test","Don't test for convergence","None",&flg);CHKERRQ(ierr); 238 if (flg) {snes->converged = 0;} 239 ierr = PetscOptionsName("-snes_cancelmonitors","Remove all monitors","SNESClearMonitor",&flg);CHKERRQ(ierr); 240 if (flg) {ierr = SNESClearMonitor(snes);CHKERRQ(ierr);} 241 242 ierr = PetscOptionsString("-snes_monitor","Monitor norm of function","SNESSetMonitor","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); 243 if (flg) { 244 ierr = PetscViewerASCIIOpen(snes->comm,monfilename,&monviewer);CHKERRQ(ierr); 245 ierr = SNESSetMonitor(snes,SNESDefaultMonitor,monviewer,(PetscErrorCode (*)(void*))PetscViewerDestroy);CHKERRQ(ierr); 246 } 247 248 ierr = PetscOptionsString("-snes_ratiomonitor","Monitor ratios of norms of function","SNESSetRatioMonitor","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); 249 if (flg) { 250 ierr = PetscViewerASCIIOpen(snes->comm,monfilename,&monviewer);CHKERRQ(ierr); 251 ierr = SNESSetRatioMonitor(snes,monviewer);CHKERRQ(ierr); 252 } 253 254 ierr = PetscOptionsString("-snes_smonitor","Monitor norm of function (fewer digits)","SNESSetMonitor","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); 255 if (flg) { 256 ierr = PetscViewerASCIIOpen(snes->comm,monfilename,&monviewer);CHKERRQ(ierr); 257 ierr = SNESSetMonitor(snes,SNESDefaultSMonitor,monviewer,(PetscErrorCode (*)(void*))PetscViewerDestroy);CHKERRQ(ierr); 258 } 259 260 ierr = PetscOptionsName("-snes_vecmonitor","Plot solution at each iteration","SNESVecViewMonitor",&flg);CHKERRQ(ierr); 261 if (flg) {ierr = SNESSetMonitor(snes,SNESVecViewMonitor,0,0);CHKERRQ(ierr);} 262 ierr = PetscOptionsName("-snes_vecmonitor_update","Plot correction at each iteration","SNESVecViewUpdateMonitor",&flg);CHKERRQ(ierr); 263 if (flg) {ierr = SNESSetMonitor(snes,SNESVecViewUpdateMonitor,0,0);CHKERRQ(ierr);} 264 ierr = PetscOptionsName("-snes_vecmonitor_residual","Plot residual at each iteration","SNESVecViewResidualMonitor",&flg);CHKERRQ(ierr); 265 if (flg) {ierr = SNESSetMonitor(snes,SNESVecViewResidualMonitor,0,0);CHKERRQ(ierr);} 266 ierr = PetscOptionsName("-snes_xmonitor","Plot function norm at each iteration","SNESLGMonitor",&flg);CHKERRQ(ierr); 267 if (flg) {ierr = SNESSetMonitor(snes,SNESLGMonitor,PETSC_NULL,PETSC_NULL);CHKERRQ(ierr);} 268 269 ierr = PetscOptionsName("-snes_fd","Use finite differences (slow) to compute Jacobian","SNESDefaultComputeJacobian",&flg);CHKERRQ(ierr); 270 if (flg) { 271 ierr = SNESSetJacobian(snes,snes->jacobian,snes->jacobian_pre,SNESDefaultComputeJacobian,snes->funP);CHKERRQ(ierr); 272 ierr = PetscInfo(snes,"Setting default finite difference Jacobian matrix\n");CHKERRQ(ierr); 273 } 274 275 for(i = 0; i < numberofsetfromoptions; i++) { 276 ierr = (*othersetfromoptions[i])(snes);CHKERRQ(ierr); 277 } 278 279 if (snes->setfromoptions) { 280 ierr = (*snes->setfromoptions)(snes);CHKERRQ(ierr); 281 } 282 ierr = PetscOptionsEnd();CHKERRQ(ierr); 283 284 ierr = SNESGetKSP(snes,&ksp);CHKERRQ(ierr); 285 ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr); 286 287 PetscFunctionReturn(0); 288 } 289 290 291 #undef __FUNCT__ 292 #define __FUNCT__ "SNESSetApplicationContext" 293 /*@ 294 SNESSetApplicationContext - Sets the optional user-defined context for 295 the nonlinear solvers. 296 297 Collective on SNES 298 299 Input Parameters: 300 + snes - the SNES context 301 - usrP - optional user context 302 303 Level: intermediate 304 305 .keywords: SNES, nonlinear, set, application, context 306 307 .seealso: SNESGetApplicationContext() 308 @*/ 309 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetApplicationContext(SNES snes,void *usrP) 310 { 311 PetscFunctionBegin; 312 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 313 snes->user = usrP; 314 PetscFunctionReturn(0); 315 } 316 317 #undef __FUNCT__ 318 #define __FUNCT__ "SNESGetApplicationContext" 319 /*@C 320 SNESGetApplicationContext - Gets the user-defined context for the 321 nonlinear solvers. 322 323 Not Collective 324 325 Input Parameter: 326 . snes - SNES context 327 328 Output Parameter: 329 . usrP - user context 330 331 Level: intermediate 332 333 .keywords: SNES, nonlinear, get, application, context 334 335 .seealso: SNESSetApplicationContext() 336 @*/ 337 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetApplicationContext(SNES snes,void **usrP) 338 { 339 PetscFunctionBegin; 340 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 341 *usrP = snes->user; 342 PetscFunctionReturn(0); 343 } 344 345 #undef __FUNCT__ 346 #define __FUNCT__ "SNESGetIterationNumber" 347 /*@ 348 SNESGetIterationNumber - Gets the number of nonlinear iterations completed 349 at this time. 350 351 Not Collective 352 353 Input Parameter: 354 . snes - SNES context 355 356 Output Parameter: 357 . iter - iteration number 358 359 Notes: 360 For example, during the computation of iteration 2 this would return 1. 361 362 This is useful for using lagged Jacobians (where one does not recompute the 363 Jacobian at each SNES iteration). For example, the code 364 .vb 365 ierr = SNESGetIterationNumber(snes,&it); 366 if (!(it % 2)) { 367 [compute Jacobian here] 368 } 369 .ve 370 can be used in your ComputeJacobian() function to cause the Jacobian to be 371 recomputed every second SNES iteration. 372 373 Level: intermediate 374 375 .keywords: SNES, nonlinear, get, iteration, number, 376 377 .seealso: SNESGetFunctionNorm(), SNESGetNumberLinearIterations() 378 @*/ 379 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetIterationNumber(SNES snes,PetscInt* iter) 380 { 381 PetscFunctionBegin; 382 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 383 PetscValidIntPointer(iter,2); 384 *iter = snes->iter; 385 PetscFunctionReturn(0); 386 } 387 388 #undef __FUNCT__ 389 #define __FUNCT__ "SNESGetFunctionNorm" 390 /*@ 391 SNESGetFunctionNorm - Gets the norm of the current function that was set 392 with SNESSSetFunction(). 393 394 Collective on SNES 395 396 Input Parameter: 397 . snes - SNES context 398 399 Output Parameter: 400 . fnorm - 2-norm of function 401 402 Level: intermediate 403 404 .keywords: SNES, nonlinear, get, function, norm 405 406 .seealso: SNESGetFunction(), SNESGetIterationNumber(), SNESGetNumberLinearIterations() 407 @*/ 408 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetFunctionNorm(SNES snes,PetscScalar *fnorm) 409 { 410 PetscFunctionBegin; 411 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 412 PetscValidScalarPointer(fnorm,2); 413 *fnorm = snes->norm; 414 PetscFunctionReturn(0); 415 } 416 417 #undef __FUNCT__ 418 #define __FUNCT__ "SNESGetNumberUnsuccessfulSteps" 419 /*@ 420 SNESGetNumberUnsuccessfulSteps - Gets the number of unsuccessful steps 421 attempted by the nonlinear solver. 422 423 Not Collective 424 425 Input Parameter: 426 . snes - SNES context 427 428 Output Parameter: 429 . nfails - number of unsuccessful steps attempted 430 431 Notes: 432 This counter is reset to zero for each successive call to SNESSolve(). 433 434 Level: intermediate 435 436 .keywords: SNES, nonlinear, get, number, unsuccessful, steps 437 @*/ 438 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetNumberUnsuccessfulSteps(SNES snes,PetscInt* nfails) 439 { 440 PetscFunctionBegin; 441 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 442 PetscValidIntPointer(nfails,2); 443 *nfails = snes->numFailures; 444 PetscFunctionReturn(0); 445 } 446 447 #undef __FUNCT__ 448 #define __FUNCT__ "SNESSetMaximumUnsuccessfulSteps" 449 /*@ 450 SNESSetMaximumUnsuccessfulSteps - Sets the maximum number of unsuccessful steps 451 attempted by the nonlinear solver before it gives up. 452 453 Not Collective 454 455 Input Parameters: 456 + snes - SNES context 457 - maxFails - maximum of unsuccessful steps 458 459 Level: intermediate 460 461 .keywords: SNES, nonlinear, set, maximum, unsuccessful, steps 462 @*/ 463 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetMaximumUnsuccessfulSteps(SNES snes, PetscInt maxFails) 464 { 465 PetscFunctionBegin; 466 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 467 snes->maxFailures = maxFails; 468 PetscFunctionReturn(0); 469 } 470 471 #undef __FUNCT__ 472 #define __FUNCT__ "SNESGetMaximumUnsuccessfulSteps" 473 /*@ 474 SNESGetMaximumUnsuccessfulSteps - Gets the maximum number of unsuccessful steps 475 attempted by the nonlinear solver before it gives up. 476 477 Not Collective 478 479 Input Parameter: 480 . snes - SNES context 481 482 Output Parameter: 483 . maxFails - maximum of unsuccessful steps 484 485 Level: intermediate 486 487 .keywords: SNES, nonlinear, get, maximum, unsuccessful, steps 488 @*/ 489 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetMaximumUnsuccessfulSteps(SNES snes, PetscInt *maxFails) 490 { 491 PetscFunctionBegin; 492 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 493 PetscValidIntPointer(maxFails,2); 494 *maxFails = snes->maxFailures; 495 PetscFunctionReturn(0); 496 } 497 498 #undef __FUNCT__ 499 #define __FUNCT__ "SNESGetLinearSolveFailures" 500 /*@ 501 SNESGetLinearSolveFailures - Gets the number of failed (non-converged) 502 linear solvers. 503 504 Not Collective 505 506 Input Parameter: 507 . snes - SNES context 508 509 Output Parameter: 510 . nfails - number of failed solves 511 512 Notes: 513 This counter is reset to zero for each successive call to SNESSolve(). 514 515 Level: intermediate 516 517 .keywords: SNES, nonlinear, get, number, unsuccessful, steps 518 @*/ 519 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetLinearSolveFailures(SNES snes,PetscInt* nfails) 520 { 521 PetscFunctionBegin; 522 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 523 PetscValidIntPointer(nfails,2); 524 *nfails = snes->numLinearSolveFailures; 525 PetscFunctionReturn(0); 526 } 527 528 #undef __FUNCT__ 529 #define __FUNCT__ "SNESSetMaxLinearSolveFailures" 530 /*@ 531 SNESSetMaxLinearSolveFailures - the number of failed linear solve attempts 532 allowed before SNES returns with a diverged reason of SNES_DIVERGED_LINEAR_SOLVE 533 534 Collective on SNES 535 536 Input Parameters: 537 + snes - SNES context 538 - maxFails - maximum allowed linear solve failures 539 540 Level: intermediate 541 542 Notes: By default this is 1; that is SNES returns on the first failed linear solve 543 544 .keywords: SNES, nonlinear, set, maximum, unsuccessful, steps 545 546 .seealso: SNESGetLinearSolveFailures(), SNESGetMaxLinearSolveFailures() 547 @*/ 548 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetMaxLinearSolveFailures(SNES snes, PetscInt maxFails) 549 { 550 PetscFunctionBegin; 551 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 552 snes->maxLinearSolveFailures = maxFails; 553 PetscFunctionReturn(0); 554 } 555 556 #undef __FUNCT__ 557 #define __FUNCT__ "SNESGetMaxLinearSolveFailures" 558 /*@ 559 SNESGetMaxLinearSolveFailures - gets the maximum number of linear solve failures that 560 are allowed before SNES terminates 561 562 Not Collective 563 564 Input Parameter: 565 . snes - SNES context 566 567 Output Parameter: 568 . maxFails - maximum of unsuccessful solves allowed 569 570 Level: intermediate 571 572 Notes: By default this is 1; that is SNES returns on the first failed linear solve 573 574 .keywords: SNES, nonlinear, get, maximum, unsuccessful, steps 575 576 .seealso: SNESGetLinearSolveFailures(), SNESGetMaxLinearSolveFailures() 577 @*/ 578 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetMaxLinearSolveFailures(SNES snes, PetscInt *maxFails) 579 { 580 PetscFunctionBegin; 581 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 582 PetscValidIntPointer(maxFails,2); 583 *maxFails = snes->maxLinearSolveFailures; 584 PetscFunctionReturn(0); 585 } 586 587 #undef __FUNCT__ 588 #define __FUNCT__ "SNESGetNumberLinearIterations" 589 /*@ 590 SNESGetNumberLinearIterations - Gets the total number of linear iterations 591 used by the nonlinear solver. 592 593 Not Collective 594 595 Input Parameter: 596 . snes - SNES context 597 598 Output Parameter: 599 . lits - number of linear iterations 600 601 Notes: 602 This counter is reset to zero for each successive call to SNESSolve(). 603 604 Level: intermediate 605 606 .keywords: SNES, nonlinear, get, number, linear, iterations 607 608 .seealso: SNESGetIterationNumber(), SNESGetFunctionNorm() 609 @*/ 610 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetNumberLinearIterations(SNES snes,PetscInt* lits) 611 { 612 PetscFunctionBegin; 613 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 614 PetscValidIntPointer(lits,2); 615 *lits = snes->linear_its; 616 PetscFunctionReturn(0); 617 } 618 619 #undef __FUNCT__ 620 #define __FUNCT__ "SNESGetKSP" 621 /*@ 622 SNESGetKSP - Returns the KSP context for a SNES solver. 623 624 Not Collective, but if SNES object is parallel, then KSP object is parallel 625 626 Input Parameter: 627 . snes - the SNES context 628 629 Output Parameter: 630 . ksp - the KSP context 631 632 Notes: 633 The user can then directly manipulate the KSP context to set various 634 options, etc. Likewise, the user can then extract and manipulate the 635 KSP and PC contexts as well. 636 637 Level: beginner 638 639 .keywords: SNES, nonlinear, get, KSP, context 640 641 .seealso: KSPGetPC() 642 @*/ 643 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetKSP(SNES snes,KSP *ksp) 644 { 645 PetscFunctionBegin; 646 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 647 PetscValidPointer(ksp,2); 648 *ksp = snes->ksp; 649 PetscFunctionReturn(0); 650 } 651 652 #undef __FUNCT__ 653 #define __FUNCT__ "SNESPublish_Petsc" 654 static PetscErrorCode SNESPublish_Petsc(PetscObject obj) 655 { 656 PetscFunctionBegin; 657 PetscFunctionReturn(0); 658 } 659 660 /* -----------------------------------------------------------*/ 661 #undef __FUNCT__ 662 #define __FUNCT__ "SNESCreate" 663 /*@ 664 SNESCreate - Creates a nonlinear solver context. 665 666 Collective on MPI_Comm 667 668 Input Parameters: 669 + comm - MPI communicator 670 671 Output Parameter: 672 . outsnes - the new SNES context 673 674 Options Database Keys: 675 + -snes_mf - Activates default matrix-free Jacobian-vector products, 676 and no preconditioning matrix 677 . -snes_mf_operator - Activates default matrix-free Jacobian-vector 678 products, and a user-provided preconditioning matrix 679 as set by SNESSetJacobian() 680 - -snes_fd - Uses (slow!) finite differences to compute Jacobian 681 682 Level: beginner 683 684 .keywords: SNES, nonlinear, create, context 685 686 .seealso: SNESSolve(), SNESDestroy(), SNES 687 @*/ 688 PetscErrorCode PETSCSNES_DLLEXPORT SNESCreate(MPI_Comm comm,SNES *outsnes) 689 { 690 PetscErrorCode ierr; 691 SNES snes; 692 SNES_KSP_EW_ConvCtx *kctx; 693 694 PetscFunctionBegin; 695 PetscValidPointer(outsnes,2); 696 *outsnes = PETSC_NULL; 697 #ifndef PETSC_USE_DYNAMIC_LIBRARIES 698 ierr = SNESInitializePackage(PETSC_NULL);CHKERRQ(ierr); 699 #endif 700 701 ierr = PetscHeaderCreate(snes,_p_SNES,PetscInt,SNES_COOKIE,0,"SNES",comm,SNESDestroy,SNESView);CHKERRQ(ierr); 702 snes->bops->publish = SNESPublish_Petsc; 703 snes->max_its = 50; 704 snes->max_funcs = 10000; 705 snes->norm = 0.0; 706 snes->rtol = 1.e-8; 707 snes->ttol = 0.0; 708 snes->abstol = 1.e-50; 709 snes->xtol = 1.e-8; 710 snes->deltatol = 1.e-12; 711 snes->nfuncs = 0; 712 snes->numFailures = 0; 713 snes->maxFailures = 1; 714 snes->linear_its = 0; 715 snes->numbermonitors = 0; 716 snes->data = 0; 717 snes->view = 0; 718 snes->setupcalled = PETSC_FALSE; 719 snes->ksp_ewconv = PETSC_FALSE; 720 snes->vwork = 0; 721 snes->nwork = 0; 722 snes->conv_hist_len = 0; 723 snes->conv_hist_max = 0; 724 snes->conv_hist = PETSC_NULL; 725 snes->conv_hist_its = PETSC_NULL; 726 snes->conv_hist_reset = PETSC_TRUE; 727 snes->reason = SNES_CONVERGED_ITERATING; 728 729 snes->numLinearSolveFailures = 0; 730 snes->maxLinearSolveFailures = 1; 731 732 /* Create context to compute Eisenstat-Walker relative tolerance for KSP */ 733 ierr = PetscNew(SNES_KSP_EW_ConvCtx,&kctx);CHKERRQ(ierr); 734 ierr = PetscLogObjectMemory(snes,sizeof(SNES_KSP_EW_ConvCtx));CHKERRQ(ierr); 735 snes->kspconvctx = (void*)kctx; 736 kctx->version = 2; 737 kctx->rtol_0 = .3; /* Eisenstat and Walker suggest rtol_0=.5, but 738 this was too large for some test cases */ 739 kctx->rtol_last = 0; 740 kctx->rtol_max = .9; 741 kctx->gamma = 1.0; 742 kctx->alpha2 = .5*(1.0 + sqrt(5.0)); 743 kctx->alpha = kctx->alpha2; 744 kctx->threshold = .1; 745 kctx->lresid_last = 0; 746 kctx->norm_last = 0; 747 748 ierr = KSPCreate(comm,&snes->ksp);CHKERRQ(ierr); 749 ierr = PetscLogObjectParent(snes,snes->ksp);CHKERRQ(ierr); 750 751 *outsnes = snes; 752 ierr = PetscPublishAll(snes);CHKERRQ(ierr); 753 PetscFunctionReturn(0); 754 } 755 756 #undef __FUNCT__ 757 #define __FUNCT__ "SNESSetFunction" 758 /*@C 759 SNESSetFunction - Sets the function evaluation routine and function 760 vector for use by the SNES routines in solving systems of nonlinear 761 equations. 762 763 Collective on SNES 764 765 Input Parameters: 766 + snes - the SNES context 767 . func - function evaluation routine 768 . r - vector to store function value 769 - ctx - [optional] user-defined context for private data for the 770 function evaluation routine (may be PETSC_NULL) 771 772 Calling sequence of func: 773 $ func (SNES snes,Vec x,Vec f,void *ctx); 774 775 . f - function vector 776 - ctx - optional user-defined function context 777 778 Notes: 779 The Newton-like methods typically solve linear systems of the form 780 $ f'(x) x = -f(x), 781 where f'(x) denotes the Jacobian matrix and f(x) is the function. 782 783 Level: beginner 784 785 .keywords: SNES, nonlinear, set, function 786 787 .seealso: SNESGetFunction(), SNESComputeFunction(), SNESSetJacobian() 788 @*/ 789 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetFunction(SNES snes,Vec r,PetscErrorCode (*func)(SNES,Vec,Vec,void*),void *ctx) 790 { 791 PetscFunctionBegin; 792 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 793 PetscValidHeaderSpecific(r,VEC_COOKIE,2); 794 PetscCheckSameComm(snes,1,r,2); 795 796 snes->computefunction = func; 797 snes->vec_func = snes->vec_func_always = r; 798 snes->funP = ctx; 799 PetscFunctionReturn(0); 800 } 801 802 /* --------------------------------------------------------------- */ 803 #undef __FUNCT__ 804 #define __FUNCT__ "SNESSetRhs" 805 /*@C 806 SNESSetRhs - Sets the vector for solving F(x) = rhs. If rhs is not set 807 it assumes a zero right hand side. 808 809 Collective on SNES 810 811 Input Parameters: 812 + snes - the SNES context 813 - rhs - the right hand side vector or PETSC_NULL for a zero right hand side 814 815 Level: intermediate 816 817 .keywords: SNES, nonlinear, set, function, right hand side 818 819 .seealso: SNESGetRhs(), SNESGetFunction(), SNESComputeFunction(), SNESSetJacobian(), SNESSetFunction() 820 @*/ 821 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetRhs(SNES snes,Vec rhs) 822 { 823 PetscErrorCode ierr; 824 825 PetscFunctionBegin; 826 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 827 if (rhs) { 828 PetscValidHeaderSpecific(rhs,VEC_COOKIE,2); 829 PetscCheckSameComm(snes,1,rhs,2); 830 ierr = PetscObjectReference((PetscObject)rhs);CHKERRQ(ierr); 831 } 832 if (snes->afine) { 833 ierr = VecDestroy(snes->afine);CHKERRQ(ierr); 834 } 835 snes->afine = rhs; 836 PetscFunctionReturn(0); 837 } 838 839 #undef __FUNCT__ 840 #define __FUNCT__ "SNESGetRhs" 841 /*@C 842 SNESGetRhs - Gets the vector for solving F(x) = rhs. If rhs is not set 843 it assumes a zero right hand side. 844 845 Collective on SNES 846 847 Input Parameter: 848 . snes - the SNES context 849 850 Output Parameter: 851 . rhs - the right hand side vector or PETSC_NULL for a zero right hand side 852 853 Level: intermediate 854 855 .keywords: SNES, nonlinear, get, function, right hand side 856 857 .seealso: SNESSetRhs(), SNESGetFunction(), SNESComputeFunction(), SNESSetJacobian(), SNESSetFunction() 858 @*/ 859 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetRhs(SNES snes,Vec *rhs) 860 { 861 PetscFunctionBegin; 862 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 863 PetscValidPointer(rhs,2); 864 *rhs = snes->afine; 865 PetscFunctionReturn(0); 866 } 867 868 #undef __FUNCT__ 869 #define __FUNCT__ "SNESComputeFunction" 870 /*@ 871 SNESComputeFunction - Calls the function that has been set with 872 SNESSetFunction(). 873 874 Collective on SNES 875 876 Input Parameters: 877 + snes - the SNES context 878 - x - input vector 879 880 Output Parameter: 881 . y - function vector, as set by SNESSetFunction() 882 883 Notes: 884 SNESComputeFunction() is typically used within nonlinear solvers 885 implementations, so most users would not generally call this routine 886 themselves. 887 888 Level: developer 889 890 .keywords: SNES, nonlinear, compute, function 891 892 .seealso: SNESSetFunction(), SNESGetFunction() 893 @*/ 894 PetscErrorCode PETSCSNES_DLLEXPORT SNESComputeFunction(SNES snes,Vec x,Vec y) 895 { 896 PetscErrorCode ierr; 897 898 PetscFunctionBegin; 899 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 900 PetscValidHeaderSpecific(x,VEC_COOKIE,2); 901 PetscValidHeaderSpecific(y,VEC_COOKIE,3); 902 PetscCheckSameComm(snes,1,x,2); 903 PetscCheckSameComm(snes,1,y,3); 904 905 ierr = PetscLogEventBegin(SNES_FunctionEval,snes,x,y,0);CHKERRQ(ierr); 906 if (snes->computefunction) { 907 PetscStackPush("SNES user function"); 908 CHKMEMQ; 909 ierr = (*snes->computefunction)(snes,x,y,snes->funP); 910 CHKMEMQ; 911 PetscStackPop; 912 if (PetscExceptionValue(ierr)) { 913 PetscErrorCode pierr = PetscLogEventEnd(SNES_FunctionEval,snes,x,y,0);CHKERRQ(pierr); 914 } 915 CHKERRQ(ierr); 916 } else if (snes->afine) { 917 ierr = MatMult(snes->jacobian, x, y);CHKERRQ(ierr); 918 } else { 919 SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Must call SNESSetFunction() before SNESComputeFunction(), likely called from SNESSolve()."); 920 } 921 if (snes->afine) { 922 ierr = VecAXPY(y,-1.0,snes->afine);CHKERRQ(ierr); 923 } 924 snes->nfuncs++; 925 ierr = PetscLogEventEnd(SNES_FunctionEval,snes,x,y,0);CHKERRQ(ierr); 926 PetscFunctionReturn(0); 927 } 928 929 #undef __FUNCT__ 930 #define __FUNCT__ "SNESComputeJacobian" 931 /*@ 932 SNESComputeJacobian - Computes the Jacobian matrix that has been 933 set with SNESSetJacobian(). 934 935 Collective on SNES and Mat 936 937 Input Parameters: 938 + snes - the SNES context 939 - x - input vector 940 941 Output Parameters: 942 + A - Jacobian matrix 943 . B - optional preconditioning matrix 944 - flag - flag indicating matrix structure (one of, SAME_NONZERO_PATTERN,DIFFERENT_NONZERO_PATTERN,SAME_PRECONDITIONER) 945 946 Notes: 947 Most users should not need to explicitly call this routine, as it 948 is used internally within the nonlinear solvers. 949 950 See KSPSetOperators() for important information about setting the 951 flag parameter. 952 953 Level: developer 954 955 .keywords: SNES, compute, Jacobian, matrix 956 957 .seealso: SNESSetJacobian(), KSPSetOperators(), MatStructure 958 @*/ 959 PetscErrorCode PETSCSNES_DLLEXPORT SNESComputeJacobian(SNES snes,Vec X,Mat *A,Mat *B,MatStructure *flg) 960 { 961 PetscErrorCode ierr; 962 963 PetscFunctionBegin; 964 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 965 PetscValidHeaderSpecific(X,VEC_COOKIE,2); 966 PetscValidPointer(flg,5); 967 PetscCheckSameComm(snes,1,X,2); 968 if (!snes->computejacobian) PetscFunctionReturn(0); 969 ierr = PetscLogEventBegin(SNES_JacobianEval,snes,X,*A,*B);CHKERRQ(ierr); 970 *flg = DIFFERENT_NONZERO_PATTERN; 971 PetscStackPush("SNES user Jacobian function"); 972 CHKMEMQ; 973 ierr = (*snes->computejacobian)(snes,X,A,B,flg,snes->jacP);CHKERRQ(ierr); 974 CHKMEMQ; 975 PetscStackPop; 976 ierr = PetscLogEventEnd(SNES_JacobianEval,snes,X,*A,*B);CHKERRQ(ierr); 977 /* make sure user returned a correct Jacobian and preconditioner */ 978 /* PetscValidHeaderSpecific(*A,MAT_COOKIE,3); 979 PetscValidHeaderSpecific(*B,MAT_COOKIE,4); */ 980 PetscFunctionReturn(0); 981 } 982 983 #undef __FUNCT__ 984 #define __FUNCT__ "SNESSetJacobian" 985 /*@C 986 SNESSetJacobian - Sets the function to compute Jacobian as well as the 987 location to store the matrix. 988 989 Collective on SNES and Mat 990 991 Input Parameters: 992 + snes - the SNES context 993 . A - Jacobian matrix 994 . B - preconditioner matrix (usually same as the Jacobian) 995 . func - Jacobian evaluation routine 996 - ctx - [optional] user-defined context for private data for the 997 Jacobian evaluation routine (may be PETSC_NULL) 998 999 Calling sequence of func: 1000 $ func (SNES snes,Vec x,Mat *A,Mat *B,int *flag,void *ctx); 1001 1002 + x - input vector 1003 . A - Jacobian matrix 1004 . B - preconditioner matrix, usually the same as A 1005 . flag - flag indicating information about the preconditioner matrix 1006 structure (same as flag in KSPSetOperators()), one of SAME_NONZERO_PATTERN,DIFFERENT_NONZERO_PATTERN,SAME_PRECONDITIONER 1007 - ctx - [optional] user-defined Jacobian context 1008 1009 Notes: 1010 See KSPSetOperators() for important information about setting the flag 1011 output parameter in the routine func(). Be sure to read this information! 1012 1013 The routine func() takes Mat * as the matrix arguments rather than Mat. 1014 This allows the Jacobian evaluation routine to replace A and/or B with a 1015 completely new new matrix structure (not just different matrix elements) 1016 when appropriate, for instance, if the nonzero structure is changing 1017 throughout the global iterations. 1018 1019 Level: beginner 1020 1021 .keywords: SNES, nonlinear, set, Jacobian, matrix 1022 1023 .seealso: KSPSetOperators(), SNESSetFunction(), MatSNESMFComputeJacobian(), SNESDefaultComputeJacobianColor(), MatStructure 1024 @*/ 1025 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetJacobian(SNES snes,Mat A,Mat B,PetscErrorCode (*func)(SNES,Vec,Mat*,Mat*,MatStructure*,void*),void *ctx) 1026 { 1027 PetscErrorCode ierr; 1028 1029 PetscFunctionBegin; 1030 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1031 if (A) PetscValidHeaderSpecific(A,MAT_COOKIE,2); 1032 if (B) PetscValidHeaderSpecific(B,MAT_COOKIE,3); 1033 if (A) PetscCheckSameComm(snes,1,A,2); 1034 if (B) PetscCheckSameComm(snes,1,B,2); 1035 if (func) snes->computejacobian = func; 1036 if (ctx) snes->jacP = ctx; 1037 if (A) { 1038 if (snes->jacobian) {ierr = MatDestroy(snes->jacobian);CHKERRQ(ierr);} 1039 snes->jacobian = A; 1040 ierr = PetscObjectReference((PetscObject)A);CHKERRQ(ierr); 1041 } 1042 if (B) { 1043 if (snes->jacobian_pre) {ierr = MatDestroy(snes->jacobian_pre);CHKERRQ(ierr);} 1044 snes->jacobian_pre = B; 1045 ierr = PetscObjectReference((PetscObject)B);CHKERRQ(ierr); 1046 } 1047 ierr = KSPSetOperators(snes->ksp,A,B,SAME_NONZERO_PATTERN);CHKERRQ(ierr); 1048 PetscFunctionReturn(0); 1049 } 1050 1051 #undef __FUNCT__ 1052 #define __FUNCT__ "SNESGetJacobian" 1053 /*@C 1054 SNESGetJacobian - Returns the Jacobian matrix and optionally the user 1055 provided context for evaluating the Jacobian. 1056 1057 Not Collective, but Mat object will be parallel if SNES object is 1058 1059 Input Parameter: 1060 . snes - the nonlinear solver context 1061 1062 Output Parameters: 1063 + A - location to stash Jacobian matrix (or PETSC_NULL) 1064 . B - location to stash preconditioner matrix (or PETSC_NULL) 1065 . func - location to put Jacobian function (or PETSC_NULL) 1066 - ctx - location to stash Jacobian ctx (or PETSC_NULL) 1067 1068 Level: advanced 1069 1070 .seealso: SNESSetJacobian(), SNESComputeJacobian() 1071 @*/ 1072 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetJacobian(SNES snes,Mat *A,Mat *B,PetscErrorCode (**func)(SNES,Vec,Mat*,Mat*,MatStructure*,void*),void **ctx) 1073 { 1074 PetscFunctionBegin; 1075 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1076 if (A) *A = snes->jacobian; 1077 if (B) *B = snes->jacobian_pre; 1078 if (func) *func = snes->computejacobian; 1079 if (ctx) *ctx = snes->jacP; 1080 PetscFunctionReturn(0); 1081 } 1082 1083 /* ----- Routines to initialize and destroy a nonlinear solver ---- */ 1084 EXTERN PetscErrorCode PETSCSNES_DLLEXPORT SNESDefaultMatrixFreeCreate2(SNES,Vec,Mat*); 1085 1086 #undef __FUNCT__ 1087 #define __FUNCT__ "SNESSetUp" 1088 /*@ 1089 SNESSetUp - Sets up the internal data structures for the later use 1090 of a nonlinear solver. 1091 1092 Collective on SNES 1093 1094 Input Parameters: 1095 . snes - the SNES context 1096 1097 Notes: 1098 For basic use of the SNES solvers the user need not explicitly call 1099 SNESSetUp(), since these actions will automatically occur during 1100 the call to SNESSolve(). However, if one wishes to control this 1101 phase separately, SNESSetUp() should be called after SNESCreate() 1102 and optional routines of the form SNESSetXXX(), but before SNESSolve(). 1103 1104 Level: advanced 1105 1106 .keywords: SNES, nonlinear, setup 1107 1108 .seealso: SNESCreate(), SNESSolve(), SNESDestroy() 1109 @*/ 1110 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetUp(SNES snes) 1111 { 1112 PetscErrorCode ierr; 1113 PetscTruth flg, iseqtr; 1114 1115 PetscFunctionBegin; 1116 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1117 if (snes->setupcalled) PetscFunctionReturn(0); 1118 1119 ierr = PetscOptionsHasName(snes->prefix,"-snes_mf_operator",&flg);CHKERRQ(ierr); 1120 /* 1121 This version replaces the user provided Jacobian matrix with a 1122 matrix-free version but still employs the user-provided preconditioner matrix 1123 */ 1124 if (flg) { 1125 Mat J; 1126 ierr = MatCreateSNESMF(snes,snes->vec_sol,&J);CHKERRQ(ierr); 1127 ierr = MatSNESMFSetFromOptions(J);CHKERRQ(ierr); 1128 ierr = PetscInfo(snes,"Setting default matrix-free operator routines\n");CHKERRQ(ierr); 1129 ierr = SNESSetJacobian(snes,J,0,0,0);CHKERRQ(ierr); 1130 ierr = MatDestroy(J);CHKERRQ(ierr); 1131 } 1132 1133 #if !defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_SINGLE) && !defined(PETSC_USE_MAT_SINGLE) && !defined(PETSC_USE_LONG_DOUBLE) && !defined(PETSC_USE_INT) 1134 ierr = PetscOptionsHasName(snes->prefix,"-snes_mf_operator2",&flg);CHKERRQ(ierr); 1135 if (flg) { 1136 Mat J; 1137 ierr = SNESDefaultMatrixFreeCreate2(snes,snes->vec_sol,&J);CHKERRQ(ierr); 1138 ierr = SNESSetJacobian(snes,J,0,0,0);CHKERRQ(ierr); 1139 ierr = MatDestroy(J);CHKERRQ(ierr); 1140 } 1141 #endif 1142 1143 ierr = PetscOptionsHasName(snes->prefix,"-snes_mf",&flg);CHKERRQ(ierr); 1144 /* 1145 This version replaces both the user-provided Jacobian and the user- 1146 provided preconditioner matrix with the default matrix free version. 1147 */ 1148 if (flg) { 1149 Mat J; 1150 KSP ksp; 1151 PC pc; 1152 1153 ierr = MatCreateSNESMF(snes,snes->vec_sol,&J);CHKERRQ(ierr); 1154 ierr = MatSNESMFSetFromOptions(J);CHKERRQ(ierr); 1155 ierr = PetscInfo(snes,"Setting default matrix-free operator and preconditioner routines;\nThat is no preconditioner is being used.\n");CHKERRQ(ierr); 1156 ierr = SNESSetJacobian(snes,J,J,MatSNESMFComputeJacobian,snes->funP);CHKERRQ(ierr); 1157 ierr = MatDestroy(J);CHKERRQ(ierr); 1158 1159 /* force no preconditioner */ 1160 ierr = SNESGetKSP(snes,&ksp);CHKERRQ(ierr); 1161 ierr = KSPGetPC(ksp,&pc);CHKERRQ(ierr); 1162 ierr = PetscTypeCompare((PetscObject)pc,PCSHELL,&flg);CHKERRQ(ierr); 1163 if (!flg) { 1164 ierr = PCSetType(pc,PCNONE);CHKERRQ(ierr); 1165 } 1166 } 1167 1168 if (!snes->vec_func && !snes->afine) { 1169 SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetFunction() first"); 1170 } 1171 if (!snes->computefunction && !snes->afine) { 1172 SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetFunction() first"); 1173 } 1174 if (!snes->jacobian) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Must call SNESSetJacobian() first \n or use -snes_mf option"); 1175 if (snes->vec_func == snes->vec_sol) { 1176 SETERRQ(PETSC_ERR_ARG_IDN,"Solution vector cannot be function vector"); 1177 } 1178 1179 /* Set the KSP stopping criterion to use the Eisenstat-Walker method */ 1180 ierr = PetscTypeCompare((PetscObject)snes,SNESTR,&iseqtr);CHKERRQ(ierr); 1181 if (snes->ksp_ewconv && !iseqtr) { 1182 KSP ksp; 1183 ierr = SNESGetKSP(snes,&ksp);CHKERRQ(ierr); 1184 ierr = KSPSetConvergenceTest(ksp,SNES_KSP_EW_Converged_Private,snes);CHKERRQ(ierr); 1185 } 1186 1187 if (snes->setup) {ierr = (*snes->setup)(snes);CHKERRQ(ierr);} 1188 snes->setupcalled = PETSC_TRUE; 1189 PetscFunctionReturn(0); 1190 } 1191 1192 #undef __FUNCT__ 1193 #define __FUNCT__ "SNESDestroy" 1194 /*@ 1195 SNESDestroy - Destroys the nonlinear solver context that was created 1196 with SNESCreate(). 1197 1198 Collective on SNES 1199 1200 Input Parameter: 1201 . snes - the SNES context 1202 1203 Level: beginner 1204 1205 .keywords: SNES, nonlinear, destroy 1206 1207 .seealso: SNESCreate(), SNESSolve() 1208 @*/ 1209 PetscErrorCode PETSCSNES_DLLEXPORT SNESDestroy(SNES snes) 1210 { 1211 PetscErrorCode ierr; 1212 1213 PetscFunctionBegin; 1214 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1215 if (--snes->refct > 0) PetscFunctionReturn(0); 1216 1217 /* if memory was published with AMS then destroy it */ 1218 ierr = PetscObjectDepublish(snes);CHKERRQ(ierr); 1219 1220 if (snes->destroy) {ierr = (*(snes)->destroy)(snes);CHKERRQ(ierr);} 1221 ierr = PetscFree(snes->kspconvctx);CHKERRQ(ierr); 1222 if (snes->jacobian) {ierr = MatDestroy(snes->jacobian);CHKERRQ(ierr);} 1223 if (snes->jacobian_pre) {ierr = MatDestroy(snes->jacobian_pre);CHKERRQ(ierr);} 1224 if (snes->afine) {ierr = VecDestroy(snes->afine);CHKERRQ(ierr);} 1225 ierr = KSPDestroy(snes->ksp);CHKERRQ(ierr); 1226 if (snes->vwork) {ierr = VecDestroyVecs(snes->vwork,snes->nvwork);CHKERRQ(ierr);} 1227 ierr = SNESClearMonitor(snes);CHKERRQ(ierr); 1228 ierr = PetscHeaderDestroy(snes);CHKERRQ(ierr); 1229 PetscFunctionReturn(0); 1230 } 1231 1232 /* ----------- Routines to set solver parameters ---------- */ 1233 1234 #undef __FUNCT__ 1235 #define __FUNCT__ "SNESSetTolerances" 1236 /*@ 1237 SNESSetTolerances - Sets various parameters used in convergence tests. 1238 1239 Collective on SNES 1240 1241 Input Parameters: 1242 + snes - the SNES context 1243 . abstol - absolute convergence tolerance 1244 . rtol - relative convergence tolerance 1245 . stol - convergence tolerance in terms of the norm 1246 of the change in the solution between steps 1247 . maxit - maximum number of iterations 1248 - maxf - maximum number of function evaluations 1249 1250 Options Database Keys: 1251 + -snes_atol <abstol> - Sets abstol 1252 . -snes_rtol <rtol> - Sets rtol 1253 . -snes_stol <stol> - Sets stol 1254 . -snes_max_it <maxit> - Sets maxit 1255 - -snes_max_funcs <maxf> - Sets maxf 1256 1257 Notes: 1258 The default maximum number of iterations is 50. 1259 The default maximum number of function evaluations is 1000. 1260 1261 Level: intermediate 1262 1263 .keywords: SNES, nonlinear, set, convergence, tolerances 1264 1265 .seealso: SNESSetTrustRegionTolerance() 1266 @*/ 1267 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetTolerances(SNES snes,PetscReal abstol,PetscReal rtol,PetscReal stol,PetscInt maxit,PetscInt maxf) 1268 { 1269 PetscFunctionBegin; 1270 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1271 if (abstol != PETSC_DEFAULT) snes->abstol = abstol; 1272 if (rtol != PETSC_DEFAULT) snes->rtol = rtol; 1273 if (stol != PETSC_DEFAULT) snes->xtol = stol; 1274 if (maxit != PETSC_DEFAULT) snes->max_its = maxit; 1275 if (maxf != PETSC_DEFAULT) snes->max_funcs = maxf; 1276 PetscFunctionReturn(0); 1277 } 1278 1279 #undef __FUNCT__ 1280 #define __FUNCT__ "SNESGetTolerances" 1281 /*@ 1282 SNESGetTolerances - Gets various parameters used in convergence tests. 1283 1284 Not Collective 1285 1286 Input Parameters: 1287 + snes - the SNES context 1288 . abstol - absolute convergence tolerance 1289 . rtol - relative convergence tolerance 1290 . stol - convergence tolerance in terms of the norm 1291 of the change in the solution between steps 1292 . maxit - maximum number of iterations 1293 - maxf - maximum number of function evaluations 1294 1295 Notes: 1296 The user can specify PETSC_NULL for any parameter that is not needed. 1297 1298 Level: intermediate 1299 1300 .keywords: SNES, nonlinear, get, convergence, tolerances 1301 1302 .seealso: SNESSetTolerances() 1303 @*/ 1304 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetTolerances(SNES snes,PetscReal *abstol,PetscReal *rtol,PetscReal *stol,PetscInt *maxit,PetscInt *maxf) 1305 { 1306 PetscFunctionBegin; 1307 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1308 if (abstol) *abstol = snes->abstol; 1309 if (rtol) *rtol = snes->rtol; 1310 if (stol) *stol = snes->xtol; 1311 if (maxit) *maxit = snes->max_its; 1312 if (maxf) *maxf = snes->max_funcs; 1313 PetscFunctionReturn(0); 1314 } 1315 1316 #undef __FUNCT__ 1317 #define __FUNCT__ "SNESSetTrustRegionTolerance" 1318 /*@ 1319 SNESSetTrustRegionTolerance - Sets the trust region parameter tolerance. 1320 1321 Collective on SNES 1322 1323 Input Parameters: 1324 + snes - the SNES context 1325 - tol - tolerance 1326 1327 Options Database Key: 1328 . -snes_trtol <tol> - Sets tol 1329 1330 Level: intermediate 1331 1332 .keywords: SNES, nonlinear, set, trust region, tolerance 1333 1334 .seealso: SNESSetTolerances() 1335 @*/ 1336 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetTrustRegionTolerance(SNES snes,PetscReal tol) 1337 { 1338 PetscFunctionBegin; 1339 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1340 snes->deltatol = tol; 1341 PetscFunctionReturn(0); 1342 } 1343 1344 /* 1345 Duplicate the lg monitors for SNES from KSP; for some reason with 1346 dynamic libraries things don't work under Sun4 if we just use 1347 macros instead of functions 1348 */ 1349 #undef __FUNCT__ 1350 #define __FUNCT__ "SNESLGMonitor" 1351 PetscErrorCode PETSCSNES_DLLEXPORT SNESLGMonitor(SNES snes,PetscInt it,PetscReal norm,void *ctx) 1352 { 1353 PetscErrorCode ierr; 1354 1355 PetscFunctionBegin; 1356 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1357 ierr = KSPLGMonitor((KSP)snes,it,norm,ctx);CHKERRQ(ierr); 1358 PetscFunctionReturn(0); 1359 } 1360 1361 #undef __FUNCT__ 1362 #define __FUNCT__ "SNESLGMonitorCreate" 1363 PetscErrorCode PETSCSNES_DLLEXPORT SNESLGMonitorCreate(const char host[],const char label[],int x,int y,int m,int n,PetscDrawLG *draw) 1364 { 1365 PetscErrorCode ierr; 1366 1367 PetscFunctionBegin; 1368 ierr = KSPLGMonitorCreate(host,label,x,y,m,n,draw);CHKERRQ(ierr); 1369 PetscFunctionReturn(0); 1370 } 1371 1372 #undef __FUNCT__ 1373 #define __FUNCT__ "SNESLGMonitorDestroy" 1374 PetscErrorCode PETSCSNES_DLLEXPORT SNESLGMonitorDestroy(PetscDrawLG draw) 1375 { 1376 PetscErrorCode ierr; 1377 1378 PetscFunctionBegin; 1379 ierr = KSPLGMonitorDestroy(draw);CHKERRQ(ierr); 1380 PetscFunctionReturn(0); 1381 } 1382 1383 /* ------------ Routines to set performance monitoring options ----------- */ 1384 1385 #undef __FUNCT__ 1386 #define __FUNCT__ "SNESSetMonitor" 1387 /*@C 1388 SNESSetMonitor - Sets an ADDITIONAL function that is to be used at every 1389 iteration of the nonlinear solver to display the iteration's 1390 progress. 1391 1392 Collective on SNES 1393 1394 Input Parameters: 1395 + snes - the SNES context 1396 . func - monitoring routine 1397 . mctx - [optional] user-defined context for private data for the 1398 monitor routine (use PETSC_NULL if no context is desired) 1399 - monitordestroy - [optional] routine that frees monitor context 1400 (may be PETSC_NULL) 1401 1402 Calling sequence of func: 1403 $ int func(SNES snes,PetscInt its, PetscReal norm,void *mctx) 1404 1405 + snes - the SNES context 1406 . its - iteration number 1407 . norm - 2-norm function value (may be estimated) 1408 - mctx - [optional] monitoring context 1409 1410 Options Database Keys: 1411 + -snes_monitor - sets SNESDefaultMonitor() 1412 . -snes_xmonitor - sets line graph monitor, 1413 uses SNESLGMonitorCreate() 1414 _ -snes_cancelmonitors - cancels all monitors that have 1415 been hardwired into a code by 1416 calls to SNESSetMonitor(), but 1417 does not cancel those set via 1418 the options database. 1419 1420 Notes: 1421 Several different monitoring routines may be set by calling 1422 SNESSetMonitor() multiple times; all will be called in the 1423 order in which they were set. 1424 1425 Level: intermediate 1426 1427 .keywords: SNES, nonlinear, set, monitor 1428 1429 .seealso: SNESDefaultMonitor(), SNESClearMonitor() 1430 @*/ 1431 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetMonitor(SNES snes,PetscErrorCode (*func)(SNES,PetscInt,PetscReal,void*),void *mctx,PetscErrorCode (*monitordestroy)(void*)) 1432 { 1433 PetscFunctionBegin; 1434 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1435 if (snes->numbermonitors >= MAXSNESMONITORS) { 1436 SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Too many monitors set"); 1437 } 1438 snes->monitor[snes->numbermonitors] = func; 1439 snes->monitordestroy[snes->numbermonitors] = monitordestroy; 1440 snes->monitorcontext[snes->numbermonitors++] = (void*)mctx; 1441 PetscFunctionReturn(0); 1442 } 1443 1444 #undef __FUNCT__ 1445 #define __FUNCT__ "SNESClearMonitor" 1446 /*@C 1447 SNESClearMonitor - Clears all the monitor functions for a SNES object. 1448 1449 Collective on SNES 1450 1451 Input Parameters: 1452 . snes - the SNES context 1453 1454 Options Database Key: 1455 . -snes_cancelmonitors - cancels all monitors that have been hardwired 1456 into a code by calls to SNESSetMonitor(), but does not cancel those 1457 set via the options database 1458 1459 Notes: 1460 There is no way to clear one specific monitor from a SNES object. 1461 1462 Level: intermediate 1463 1464 .keywords: SNES, nonlinear, set, monitor 1465 1466 .seealso: SNESDefaultMonitor(), SNESSetMonitor() 1467 @*/ 1468 PetscErrorCode PETSCSNES_DLLEXPORT SNESClearMonitor(SNES snes) 1469 { 1470 PetscErrorCode ierr; 1471 PetscInt i; 1472 1473 PetscFunctionBegin; 1474 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1475 for (i=0; i<snes->numbermonitors; i++) { 1476 if (snes->monitordestroy[i]) { 1477 ierr = (*snes->monitordestroy[i])(snes->monitorcontext[i]);CHKERRQ(ierr); 1478 } 1479 } 1480 snes->numbermonitors = 0; 1481 PetscFunctionReturn(0); 1482 } 1483 1484 #undef __FUNCT__ 1485 #define __FUNCT__ "SNESSetConvergenceTest" 1486 /*@C 1487 SNESSetConvergenceTest - Sets the function that is to be used 1488 to test for convergence of the nonlinear iterative solution. 1489 1490 Collective on SNES 1491 1492 Input Parameters: 1493 + snes - the SNES context 1494 . func - routine to test for convergence 1495 - cctx - [optional] context for private data for the convergence routine 1496 (may be PETSC_NULL) 1497 1498 Calling sequence of func: 1499 $ PetscErrorCode func (SNES snes,PetscInt it,PetscReal xnorm,PetscReal gnorm,PetscReal f,SNESConvergedReason *reason,void *cctx) 1500 1501 + snes - the SNES context 1502 . it - current iteration (0 is the first and is before any Newton step) 1503 . cctx - [optional] convergence context 1504 . reason - reason for convergence/divergence 1505 . xnorm - 2-norm of current iterate 1506 . gnorm - 2-norm of current step 1507 - f - 2-norm of function 1508 1509 Level: advanced 1510 1511 .keywords: SNES, nonlinear, set, convergence, test 1512 1513 .seealso: SNESConverged_LS(), SNESConverged_TR() 1514 @*/ 1515 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetConvergenceTest(SNES snes,PetscErrorCode (*func)(SNES,PetscInt,PetscReal,PetscReal,PetscReal,SNESConvergedReason*,void*),void *cctx) 1516 { 1517 PetscFunctionBegin; 1518 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1519 (snes)->converged = func; 1520 (snes)->cnvP = cctx; 1521 PetscFunctionReturn(0); 1522 } 1523 1524 #undef __FUNCT__ 1525 #define __FUNCT__ "SNESGetConvergedReason" 1526 /*@ 1527 SNESGetConvergedReason - Gets the reason the SNES iteration was stopped. 1528 1529 Not Collective 1530 1531 Input Parameter: 1532 . snes - the SNES context 1533 1534 Output Parameter: 1535 . reason - negative value indicates diverged, positive value converged, see petscsnes.h or the 1536 manual pages for the individual convergence tests for complete lists 1537 1538 Level: intermediate 1539 1540 Notes: Can only be called after the call the SNESSolve() is complete. 1541 1542 .keywords: SNES, nonlinear, set, convergence, test 1543 1544 .seealso: SNESSetConvergenceTest(), SNESConverged_LS(), SNESConverged_TR(), SNESConvergedReason 1545 @*/ 1546 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetConvergedReason(SNES snes,SNESConvergedReason *reason) 1547 { 1548 PetscFunctionBegin; 1549 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1550 PetscValidPointer(reason,2); 1551 *reason = snes->reason; 1552 PetscFunctionReturn(0); 1553 } 1554 1555 #undef __FUNCT__ 1556 #define __FUNCT__ "SNESSetConvergenceHistory" 1557 /*@ 1558 SNESSetConvergenceHistory - Sets the array used to hold the convergence history. 1559 1560 Collective on SNES 1561 1562 Input Parameters: 1563 + snes - iterative context obtained from SNESCreate() 1564 . a - array to hold history 1565 . its - integer array holds the number of linear iterations for each solve. 1566 . na - size of a and its 1567 - reset - PETSC_TRUE indicates each new nonlinear solve resets the history counter to zero, 1568 else it continues storing new values for new nonlinear solves after the old ones 1569 1570 Notes: 1571 If set, this array will contain the function norms computed 1572 at each step. 1573 1574 This routine is useful, e.g., when running a code for purposes 1575 of accurate performance monitoring, when no I/O should be done 1576 during the section of code that is being timed. 1577 1578 Level: intermediate 1579 1580 .keywords: SNES, set, convergence, history 1581 1582 .seealso: SNESGetConvergenceHistory() 1583 1584 @*/ 1585 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetConvergenceHistory(SNES snes,PetscReal a[],PetscInt *its,PetscInt na,PetscTruth reset) 1586 { 1587 PetscFunctionBegin; 1588 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1589 if (na) PetscValidScalarPointer(a,2); 1590 snes->conv_hist = a; 1591 snes->conv_hist_its = its; 1592 snes->conv_hist_max = na; 1593 snes->conv_hist_reset = reset; 1594 PetscFunctionReturn(0); 1595 } 1596 1597 #undef __FUNCT__ 1598 #define __FUNCT__ "SNESGetConvergenceHistory" 1599 /*@C 1600 SNESGetConvergenceHistory - Gets the array used to hold the convergence history. 1601 1602 Collective on SNES 1603 1604 Input Parameter: 1605 . snes - iterative context obtained from SNESCreate() 1606 1607 Output Parameters: 1608 . a - array to hold history 1609 . its - integer array holds the number of linear iterations (or 1610 negative if not converged) for each solve. 1611 - na - size of a and its 1612 1613 Notes: 1614 The calling sequence for this routine in Fortran is 1615 $ call SNESGetConvergenceHistory(SNES snes, integer na, integer ierr) 1616 1617 This routine is useful, e.g., when running a code for purposes 1618 of accurate performance monitoring, when no I/O should be done 1619 during the section of code that is being timed. 1620 1621 Level: intermediate 1622 1623 .keywords: SNES, get, convergence, history 1624 1625 .seealso: SNESSetConvergencHistory() 1626 1627 @*/ 1628 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetConvergenceHistory(SNES snes,PetscReal *a[],PetscInt *its[],PetscInt *na) 1629 { 1630 PetscFunctionBegin; 1631 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1632 if (a) *a = snes->conv_hist; 1633 if (its) *its = snes->conv_hist_its; 1634 if (na) *na = snes->conv_hist_len; 1635 PetscFunctionReturn(0); 1636 } 1637 1638 #undef __FUNCT__ 1639 #define __FUNCT__ "SNESSetUpdate" 1640 /*@C 1641 SNESSetUpdate - Sets the general-purpose update function called 1642 at the beginning o every iteration of the nonlinear solve. Specifically 1643 it is called just before the Jacobian is "evaluated". 1644 1645 Collective on SNES 1646 1647 Input Parameters: 1648 . snes - The nonlinear solver context 1649 . func - The function 1650 1651 Calling sequence of func: 1652 . func (SNES snes, PetscInt step); 1653 1654 . step - The current step of the iteration 1655 1656 Level: intermediate 1657 1658 .keywords: SNES, update 1659 1660 .seealso SNESDefaultUpdate(), SNESSetRhsBC(), SNESSetSolutionBC() 1661 @*/ 1662 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetUpdate(SNES snes, PetscErrorCode (*func)(SNES, PetscInt)) 1663 { 1664 PetscFunctionBegin; 1665 PetscValidHeaderSpecific(snes, SNES_COOKIE,1); 1666 snes->update = func; 1667 PetscFunctionReturn(0); 1668 } 1669 1670 #undef __FUNCT__ 1671 #define __FUNCT__ "SNESDefaultUpdate" 1672 /*@ 1673 SNESDefaultUpdate - The default update function which does nothing. 1674 1675 Not collective 1676 1677 Input Parameters: 1678 . snes - The nonlinear solver context 1679 . step - The current step of the iteration 1680 1681 Level: intermediate 1682 1683 .keywords: SNES, update 1684 .seealso SNESSetUpdate(), SNESDefaultRhsBC(), SNESDefaultSolutionBC() 1685 @*/ 1686 PetscErrorCode PETSCSNES_DLLEXPORT SNESDefaultUpdate(SNES snes, PetscInt step) 1687 { 1688 PetscFunctionBegin; 1689 PetscFunctionReturn(0); 1690 } 1691 1692 #undef __FUNCT__ 1693 #define __FUNCT__ "SNESScaleStep_Private" 1694 /* 1695 SNESScaleStep_Private - Scales a step so that its length is less than the 1696 positive parameter delta. 1697 1698 Input Parameters: 1699 + snes - the SNES context 1700 . y - approximate solution of linear system 1701 . fnorm - 2-norm of current function 1702 - delta - trust region size 1703 1704 Output Parameters: 1705 + gpnorm - predicted function norm at the new point, assuming local 1706 linearization. The value is zero if the step lies within the trust 1707 region, and exceeds zero otherwise. 1708 - ynorm - 2-norm of the step 1709 1710 Note: 1711 For non-trust region methods such as SNESLS, the parameter delta 1712 is set to be the maximum allowable step size. 1713 1714 .keywords: SNES, nonlinear, scale, step 1715 */ 1716 PetscErrorCode SNESScaleStep_Private(SNES snes,Vec y,PetscReal *fnorm,PetscReal *delta,PetscReal *gpnorm,PetscReal *ynorm) 1717 { 1718 PetscReal nrm; 1719 PetscScalar cnorm; 1720 PetscErrorCode ierr; 1721 1722 PetscFunctionBegin; 1723 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1724 PetscValidHeaderSpecific(y,VEC_COOKIE,2); 1725 PetscCheckSameComm(snes,1,y,2); 1726 1727 ierr = VecNorm(y,NORM_2,&nrm);CHKERRQ(ierr); 1728 if (nrm > *delta) { 1729 nrm = *delta/nrm; 1730 *gpnorm = (1.0 - nrm)*(*fnorm); 1731 cnorm = nrm; 1732 ierr = VecScale(y,cnorm);CHKERRQ(ierr); 1733 *ynorm = *delta; 1734 } else { 1735 *gpnorm = 0.0; 1736 *ynorm = nrm; 1737 } 1738 PetscFunctionReturn(0); 1739 } 1740 1741 #undef __FUNCT__ 1742 #define __FUNCT__ "SNESSolve" 1743 /*@C 1744 SNESSolve - Solves a nonlinear system F(x) = b. 1745 Call SNESSolve() after calling SNESCreate() and optional routines of the form SNESSetXXX(). 1746 1747 Collective on SNES 1748 1749 Input Parameters: 1750 + snes - the SNES context 1751 . b - the constant part of the equation, or PETSC_NULL to use zero. 1752 - x - the solution vector, or PETSC_NULL if it was set with SNESSetSolution() 1753 1754 Notes: 1755 The user should initialize the vector,x, with the initial guess 1756 for the nonlinear solve prior to calling SNESSolve. In particular, 1757 to employ an initial guess of zero, the user should explicitly set 1758 this vector to zero by calling VecSet(). 1759 1760 Level: beginner 1761 1762 .keywords: SNES, nonlinear, solve 1763 1764 .seealso: SNESCreate(), SNESDestroy(), SNESSetFunction(), SNESSetJacobian(), SNESSetRhs(), SNESSetSolution() 1765 @*/ 1766 PetscErrorCode PETSCSNES_DLLEXPORT SNESSolve(SNES snes,Vec b,Vec x) 1767 { 1768 PetscErrorCode ierr; 1769 PetscTruth flg; 1770 char filename[PETSC_MAX_PATH_LEN]; 1771 PetscViewer viewer; 1772 1773 PetscFunctionBegin; 1774 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1775 if (!snes->solve) SETERRQ(PETSC_ERR_ORDER,"SNESSetType() or SNESSetFromOptions() must be called before SNESSolve()"); 1776 1777 if (b) { 1778 ierr = SNESSetRhs(snes, b); CHKERRQ(ierr); 1779 if (!snes->vec_func) { 1780 Vec r; 1781 1782 ierr = VecDuplicate(b, &r); CHKERRQ(ierr); 1783 ierr = SNESSetFunction(snes, r, PETSC_NULL, PETSC_NULL); CHKERRQ(ierr); 1784 } 1785 } 1786 if (x) { 1787 PetscValidHeaderSpecific(x,VEC_COOKIE,3); 1788 PetscCheckSameComm(snes,1,x,3); 1789 } else { 1790 ierr = SNESGetSolution(snes, &x); CHKERRQ(ierr); 1791 if (!x) { 1792 ierr = VecDuplicate(snes->vec_func_always, &x); CHKERRQ(ierr); 1793 } 1794 } 1795 snes->vec_sol = snes->vec_sol_always = x; 1796 if (!snes->setupcalled) { 1797 ierr = SNESSetUp(snes);CHKERRQ(ierr); 1798 } 1799 if (snes->conv_hist_reset) snes->conv_hist_len = 0; 1800 ierr = PetscLogEventBegin(SNES_Solve,snes,0,0,0);CHKERRQ(ierr); 1801 snes->nfuncs = 0; snes->linear_its = 0; snes->numFailures = 0; 1802 1803 ierr = PetscExceptionTry1((*(snes)->solve)(snes),PETSC_ERR_ARG_DOMAIN); 1804 if (PetscExceptionValue(ierr)) { 1805 /* this means that a caller above me has also tryed this exception so I don't handle it here, pass it up */ 1806 PetscErrorCode pierr = PetscLogEventEnd(SNES_Solve,snes,0,0,0);CHKERRQ(pierr); 1807 } else if (PetscExceptionCaught(ierr,PETSC_ERR_ARG_DOMAIN)) { 1808 /* translate exception into SNES not converged reason */ 1809 snes->reason = SNES_DIVERGED_FUNCTION_DOMAIN; 1810 ierr = 0; 1811 } 1812 CHKERRQ(ierr); 1813 1814 ierr = PetscLogEventEnd(SNES_Solve,snes,0,0,0);CHKERRQ(ierr); 1815 ierr = PetscOptionsGetString(snes->prefix,"-snes_view",filename,PETSC_MAX_PATH_LEN,&flg);CHKERRQ(ierr); 1816 if (flg && !PetscPreLoadingOn) { 1817 ierr = PetscViewerASCIIOpen(snes->comm,filename,&viewer);CHKERRQ(ierr); 1818 ierr = SNESView(snes,viewer);CHKERRQ(ierr); 1819 ierr = PetscViewerDestroy(viewer);CHKERRQ(ierr); 1820 } 1821 1822 ierr = PetscOptionsHasName(snes->prefix,"-snes_test_local_min",&flg);CHKERRQ(ierr); 1823 if (flg && !PetscPreLoadingOn) { ierr = SNESTestLocalMin(snes);CHKERRQ(ierr); } 1824 if (snes->printreason) { 1825 if (snes->reason > 0) { 1826 ierr = PetscPrintf(snes->comm,"Nonlinear solve converged due to %s\n",SNESConvergedReasons[snes->reason]);CHKERRQ(ierr); 1827 } else { 1828 ierr = PetscPrintf(snes->comm,"Nonlinear solve did not converge due to %s\n",SNESConvergedReasons[snes->reason]);CHKERRQ(ierr); 1829 } 1830 } 1831 1832 PetscFunctionReturn(0); 1833 } 1834 1835 /* --------- Internal routines for SNES Package --------- */ 1836 1837 #undef __FUNCT__ 1838 #define __FUNCT__ "SNESSetType" 1839 /*@C 1840 SNESSetType - Sets the method for the nonlinear solver. 1841 1842 Collective on SNES 1843 1844 Input Parameters: 1845 + snes - the SNES context 1846 - type - a known method 1847 1848 Options Database Key: 1849 . -snes_type <type> - Sets the method; use -help for a list 1850 of available methods (for instance, ls or tr) 1851 1852 Notes: 1853 See "petsc/include/petscsnes.h" for available methods (for instance) 1854 + SNESLS - Newton's method with line search 1855 (systems of nonlinear equations) 1856 . SNESTR - Newton's method with trust region 1857 (systems of nonlinear equations) 1858 1859 Normally, it is best to use the SNESSetFromOptions() command and then 1860 set the SNES solver type from the options database rather than by using 1861 this routine. Using the options database provides the user with 1862 maximum flexibility in evaluating the many nonlinear solvers. 1863 The SNESSetType() routine is provided for those situations where it 1864 is necessary to set the nonlinear solver independently of the command 1865 line or options database. This might be the case, for example, when 1866 the choice of solver changes during the execution of the program, 1867 and the user's application is taking responsibility for choosing the 1868 appropriate method. 1869 1870 Level: intermediate 1871 1872 .keywords: SNES, set, type 1873 1874 .seealso: SNESType, SNESCreate() 1875 1876 @*/ 1877 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetType(SNES snes,SNESType type) 1878 { 1879 PetscErrorCode ierr,(*r)(SNES); 1880 PetscTruth match; 1881 1882 PetscFunctionBegin; 1883 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1884 PetscValidCharPointer(type,2); 1885 1886 ierr = PetscTypeCompare((PetscObject)snes,type,&match);CHKERRQ(ierr); 1887 if (match) PetscFunctionReturn(0); 1888 1889 if (snes->setupcalled) { 1890 snes->setupcalled = PETSC_FALSE; 1891 ierr = (*(snes)->destroy)(snes);CHKERRQ(ierr); 1892 snes->data = 0; 1893 } 1894 1895 /* Get the function pointers for the iterative method requested */ 1896 if (!SNESRegisterAllCalled) {ierr = SNESRegisterAll(PETSC_NULL);CHKERRQ(ierr);} 1897 ierr = PetscFListFind(snes->comm,SNESList,type,(void (**)(void)) &r);CHKERRQ(ierr); 1898 if (!r) SETERRQ1(PETSC_ERR_ARG_UNKNOWN_TYPE,"Unable to find requested SNES type %s",type); 1899 ierr = PetscFree(snes->data);CHKERRQ(ierr); 1900 snes->data = 0; 1901 ierr = (*r)(snes);CHKERRQ(ierr); 1902 ierr = PetscObjectChangeTypeName((PetscObject)snes,type);CHKERRQ(ierr); 1903 PetscFunctionReturn(0); 1904 } 1905 1906 1907 /* --------------------------------------------------------------------- */ 1908 #undef __FUNCT__ 1909 #define __FUNCT__ "SNESRegisterDestroy" 1910 /*@ 1911 SNESRegisterDestroy - Frees the list of nonlinear solvers that were 1912 registered by SNESRegisterDynamic(). 1913 1914 Not Collective 1915 1916 Level: advanced 1917 1918 .keywords: SNES, nonlinear, register, destroy 1919 1920 .seealso: SNESRegisterAll(), SNESRegisterAll() 1921 @*/ 1922 PetscErrorCode PETSCSNES_DLLEXPORT SNESRegisterDestroy(void) 1923 { 1924 PetscErrorCode ierr; 1925 1926 PetscFunctionBegin; 1927 if (SNESList) { 1928 ierr = PetscFListDestroy(&SNESList);CHKERRQ(ierr); 1929 SNESList = 0; 1930 } 1931 SNESRegisterAllCalled = PETSC_FALSE; 1932 PetscFunctionReturn(0); 1933 } 1934 1935 #undef __FUNCT__ 1936 #define __FUNCT__ "SNESGetType" 1937 /*@C 1938 SNESGetType - Gets the SNES method type and name (as a string). 1939 1940 Not Collective 1941 1942 Input Parameter: 1943 . snes - nonlinear solver context 1944 1945 Output Parameter: 1946 . type - SNES method (a character string) 1947 1948 Level: intermediate 1949 1950 .keywords: SNES, nonlinear, get, type, name 1951 @*/ 1952 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetType(SNES snes,SNESType *type) 1953 { 1954 PetscFunctionBegin; 1955 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1956 PetscValidPointer(type,2); 1957 *type = snes->type_name; 1958 PetscFunctionReturn(0); 1959 } 1960 1961 #undef __FUNCT__ 1962 #define __FUNCT__ "SNESGetSolution" 1963 /*@ 1964 SNESGetSolution - Returns the vector where the approximate solution is 1965 stored. 1966 1967 Not Collective, but Vec is parallel if SNES is parallel 1968 1969 Input Parameter: 1970 . snes - the SNES context 1971 1972 Output Parameter: 1973 . x - the solution 1974 1975 Level: intermediate 1976 1977 .keywords: SNES, nonlinear, get, solution 1978 1979 .seealso: SNESSetSolution(), SNESGetFunction(), SNESGetSolutionUpdate() 1980 @*/ 1981 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetSolution(SNES snes,Vec *x) 1982 { 1983 PetscFunctionBegin; 1984 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 1985 PetscValidPointer(x,2); 1986 *x = snes->vec_sol_always; 1987 PetscFunctionReturn(0); 1988 } 1989 1990 #undef __FUNCT__ 1991 #define __FUNCT__ "SNESSetSolution" 1992 /*@ 1993 SNESSetSolution - Sets the vector where the approximate solution is stored. 1994 1995 Not Collective, but Vec is parallel if SNES is parallel 1996 1997 Input Parameters: 1998 + snes - the SNES context 1999 - x - the solution 2000 2001 Output Parameter: 2002 2003 Level: intermediate 2004 2005 Notes: this is not normally used, rather one simply calls SNESSolve() with 2006 the appropriate solution vector. 2007 2008 .keywords: SNES, nonlinear, set, solution 2009 2010 .seealso: SNESGetSolution(), SNESGetFunction(), SNESGetSolutionUpdate() 2011 @*/ 2012 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetSolution(SNES snes,Vec x) 2013 { 2014 PetscFunctionBegin; 2015 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2016 PetscValidHeaderSpecific(x,VEC_COOKIE,2); 2017 PetscCheckSameComm(snes,1,x,2); 2018 snes->vec_sol_always = x; 2019 PetscFunctionReturn(0); 2020 } 2021 2022 #undef __FUNCT__ 2023 #define __FUNCT__ "SNESGetSolutionUpdate" 2024 /*@ 2025 SNESGetSolutionUpdate - Returns the vector where the solution update is 2026 stored. 2027 2028 Not Collective, but Vec is parallel if SNES is parallel 2029 2030 Input Parameter: 2031 . snes - the SNES context 2032 2033 Output Parameter: 2034 . x - the solution update 2035 2036 Level: advanced 2037 2038 .keywords: SNES, nonlinear, get, solution, update 2039 2040 .seealso: SNESGetSolution(), SNESGetFunction 2041 @*/ 2042 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetSolutionUpdate(SNES snes,Vec *x) 2043 { 2044 PetscFunctionBegin; 2045 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2046 PetscValidPointer(x,2); 2047 *x = snes->vec_sol_update_always; 2048 PetscFunctionReturn(0); 2049 } 2050 2051 #undef __FUNCT__ 2052 #define __FUNCT__ "SNESGetFunction" 2053 /*@C 2054 SNESGetFunction - Returns the vector where the function is stored. 2055 2056 Not Collective, but Vec is parallel if SNES is parallel 2057 2058 Input Parameter: 2059 . snes - the SNES context 2060 2061 Output Parameter: 2062 + r - the function (or PETSC_NULL) 2063 . func - the function (or PETSC_NULL) 2064 - ctx - the function context (or PETSC_NULL) 2065 2066 Level: advanced 2067 2068 .keywords: SNES, nonlinear, get, function 2069 2070 .seealso: SNESSetFunction(), SNESGetSolution() 2071 @*/ 2072 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetFunction(SNES snes,Vec *r,PetscErrorCode (**func)(SNES,Vec,Vec,void*),void **ctx) 2073 { 2074 PetscFunctionBegin; 2075 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2076 if (r) *r = snes->vec_func_always; 2077 if (func) *func = snes->computefunction; 2078 if (ctx) *ctx = snes->funP; 2079 PetscFunctionReturn(0); 2080 } 2081 2082 #undef __FUNCT__ 2083 #define __FUNCT__ "SNESSetOptionsPrefix" 2084 /*@C 2085 SNESSetOptionsPrefix - Sets the prefix used for searching for all 2086 SNES options in the database. 2087 2088 Collective on SNES 2089 2090 Input Parameter: 2091 + snes - the SNES context 2092 - prefix - the prefix to prepend to all option names 2093 2094 Notes: 2095 A hyphen (-) must NOT be given at the beginning of the prefix name. 2096 The first character of all runtime options is AUTOMATICALLY the hyphen. 2097 2098 Level: advanced 2099 2100 .keywords: SNES, set, options, prefix, database 2101 2102 .seealso: SNESSetFromOptions() 2103 @*/ 2104 PetscErrorCode PETSCSNES_DLLEXPORT SNESSetOptionsPrefix(SNES snes,const char prefix[]) 2105 { 2106 PetscErrorCode ierr; 2107 2108 PetscFunctionBegin; 2109 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2110 ierr = PetscObjectSetOptionsPrefix((PetscObject)snes,prefix);CHKERRQ(ierr); 2111 ierr = KSPSetOptionsPrefix(snes->ksp,prefix);CHKERRQ(ierr); 2112 PetscFunctionReturn(0); 2113 } 2114 2115 #undef __FUNCT__ 2116 #define __FUNCT__ "SNESAppendOptionsPrefix" 2117 /*@C 2118 SNESAppendOptionsPrefix - Appends to the prefix used for searching for all 2119 SNES options in the database. 2120 2121 Collective on SNES 2122 2123 Input Parameters: 2124 + snes - the SNES context 2125 - prefix - the prefix to prepend to all option names 2126 2127 Notes: 2128 A hyphen (-) must NOT be given at the beginning of the prefix name. 2129 The first character of all runtime options is AUTOMATICALLY the hyphen. 2130 2131 Level: advanced 2132 2133 .keywords: SNES, append, options, prefix, database 2134 2135 .seealso: SNESGetOptionsPrefix() 2136 @*/ 2137 PetscErrorCode PETSCSNES_DLLEXPORT SNESAppendOptionsPrefix(SNES snes,const char prefix[]) 2138 { 2139 PetscErrorCode ierr; 2140 2141 PetscFunctionBegin; 2142 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2143 ierr = PetscObjectAppendOptionsPrefix((PetscObject)snes,prefix);CHKERRQ(ierr); 2144 ierr = KSPAppendOptionsPrefix(snes->ksp,prefix);CHKERRQ(ierr); 2145 PetscFunctionReturn(0); 2146 } 2147 2148 #undef __FUNCT__ 2149 #define __FUNCT__ "SNESGetOptionsPrefix" 2150 /*@C 2151 SNESGetOptionsPrefix - Sets the prefix used for searching for all 2152 SNES options in the database. 2153 2154 Not Collective 2155 2156 Input Parameter: 2157 . snes - the SNES context 2158 2159 Output Parameter: 2160 . prefix - pointer to the prefix string used 2161 2162 Notes: On the fortran side, the user should pass in a string 'prifix' of 2163 sufficient length to hold the prefix. 2164 2165 Level: advanced 2166 2167 .keywords: SNES, get, options, prefix, database 2168 2169 .seealso: SNESAppendOptionsPrefix() 2170 @*/ 2171 PetscErrorCode PETSCSNES_DLLEXPORT SNESGetOptionsPrefix(SNES snes,const char *prefix[]) 2172 { 2173 PetscErrorCode ierr; 2174 2175 PetscFunctionBegin; 2176 PetscValidHeaderSpecific(snes,SNES_COOKIE,1); 2177 ierr = PetscObjectGetOptionsPrefix((PetscObject)snes,prefix);CHKERRQ(ierr); 2178 PetscFunctionReturn(0); 2179 } 2180 2181 2182 #undef __FUNCT__ 2183 #define __FUNCT__ "SNESRegister" 2184 /*@C 2185 SNESRegister - See SNESRegisterDynamic() 2186 2187 Level: advanced 2188 @*/ 2189 PetscErrorCode PETSCSNES_DLLEXPORT SNESRegister(const char sname[],const char path[],const char name[],PetscErrorCode (*function)(SNES)) 2190 { 2191 char fullname[PETSC_MAX_PATH_LEN]; 2192 PetscErrorCode ierr; 2193 2194 PetscFunctionBegin; 2195 ierr = PetscFListConcat(path,name,fullname);CHKERRQ(ierr); 2196 ierr = PetscFListAdd(&SNESList,sname,fullname,(void (*)(void))function);CHKERRQ(ierr); 2197 PetscFunctionReturn(0); 2198 } 2199 2200 #undef __FUNCT__ 2201 #define __FUNCT__ "SNESTestLocalMin" 2202 PetscErrorCode PETSCSNES_DLLEXPORT SNESTestLocalMin(SNES snes) 2203 { 2204 PetscErrorCode ierr; 2205 PetscInt N,i,j; 2206 Vec u,uh,fh; 2207 PetscScalar value; 2208 PetscReal norm; 2209 2210 PetscFunctionBegin; 2211 ierr = SNESGetSolution(snes,&u);CHKERRQ(ierr); 2212 ierr = VecDuplicate(u,&uh);CHKERRQ(ierr); 2213 ierr = VecDuplicate(u,&fh);CHKERRQ(ierr); 2214 2215 /* currently only works for sequential */ 2216 ierr = PetscPrintf(PETSC_COMM_WORLD,"Testing FormFunction() for local min\n"); 2217 ierr = VecGetSize(u,&N);CHKERRQ(ierr); 2218 for (i=0; i<N; i++) { 2219 ierr = VecCopy(u,uh);CHKERRQ(ierr); 2220 ierr = PetscPrintf(PETSC_COMM_WORLD,"i = %D\n",i);CHKERRQ(ierr); 2221 for (j=-10; j<11; j++) { 2222 value = PetscSign(j)*exp(PetscAbs(j)-10.0); 2223 ierr = VecSetValue(uh,i,value,ADD_VALUES);CHKERRQ(ierr); 2224 ierr = SNESComputeFunction(snes,uh,fh);CHKERRQ(ierr); 2225 ierr = VecNorm(fh,NORM_2,&norm);CHKERRQ(ierr); 2226 ierr = PetscPrintf(PETSC_COMM_WORLD," j norm %D %18.16e\n",j,norm);CHKERRQ(ierr); 2227 value = -value; 2228 ierr = VecSetValue(uh,i,value,ADD_VALUES);CHKERRQ(ierr); 2229 } 2230 } 2231 ierr = VecDestroy(uh);CHKERRQ(ierr); 2232 ierr = VecDestroy(fh);CHKERRQ(ierr); 2233 PetscFunctionReturn(0); 2234 } 2235