1 #define PETSCKSP_DLL 2 3 /* 4 This provides a simple shell for Fortran (and C programmers) to 5 create their own preconditioner without writing much interface code. 6 */ 7 8 #include "src/ksp/pc/pcimpl.h" /*I "petscpc.h" I*/ 9 #include "private/vecimpl.h" 10 11 EXTERN_C_BEGIN 12 typedef struct { 13 void *ctx; /* user provided contexts for preconditioner */ 14 PetscErrorCode (*setup)(void*); 15 PetscErrorCode (*apply)(void*,Vec,Vec); 16 PetscErrorCode (*presolve)(void*,KSP,Vec,Vec); 17 PetscErrorCode (*postsolve)(void*,KSP,Vec,Vec); 18 PetscErrorCode (*view)(void*,PetscViewer); 19 PetscErrorCode (*applytranspose)(void*,Vec,Vec); 20 PetscErrorCode (*applyrich)(void*,Vec,Vec,Vec,PetscReal,PetscReal,PetscReal,PetscInt); 21 char *name; 22 } PC_Shell; 23 EXTERN_C_END 24 25 #undef __FUNCT__ 26 #define __FUNCT__ "PCShellGetContext" 27 /*@ 28 PCShellGetContext - Returns the user-provided context associated with a shell PC 29 30 Not Collective 31 32 Input Parameter: 33 . pc - should have been created with PCCreateShell() 34 35 Output Parameter: 36 . ctx - the user provided context 37 38 Level: advanced 39 40 Notes: 41 This routine is intended for use within various shell routines 42 43 .keywords: PC, shell, get, context 44 45 .seealso: PCCreateShell(), PCShellSetContext() 46 @*/ 47 PetscErrorCode PETSCKSP_DLLEXPORT PCShellGetContext(PC pc,void **ctx) 48 { 49 PetscErrorCode ierr; 50 PetscTruth flg; 51 52 PetscFunctionBegin; 53 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 54 PetscValidPointer(ctx,2); 55 ierr = PetscTypeCompare((PetscObject)pc,PCSHELL,&flg);CHKERRQ(ierr); 56 if (!flg) *ctx = 0; 57 else *ctx = ((PC_Shell*)(pc->data))->ctx; 58 PetscFunctionReturn(0); 59 } 60 61 #undef __FUNCT__ 62 #define __FUNCT__ "PCShellSetContext" 63 /*@C 64 PCShellSetContext - sets the context for a shell PC 65 66 Collective on PC 67 68 Input Parameters: 69 + pc - the shell PC 70 - ctx - the context 71 72 Level: advanced 73 74 Fortran Notes: The context can only be an integer or a PetscObject 75 unfortunately it cannot be a Fortran array or derived type. 76 77 .seealso: PCCreateShell(), PCShellGetContext() 78 @*/ 79 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetContext(PC pc,void *ctx) 80 { 81 PC_Shell *shell = (PC_Shell*)pc->data; 82 PetscErrorCode ierr; 83 PetscTruth flg; 84 85 PetscFunctionBegin; 86 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 87 ierr = PetscTypeCompare((PetscObject)pc,PCSHELL,&flg);CHKERRQ(ierr); 88 if (flg) { 89 shell->ctx = ctx; 90 } 91 PetscFunctionReturn(0); 92 } 93 94 #undef __FUNCT__ 95 #define __FUNCT__ "PCApply_SetUp" 96 static PetscErrorCode PCSetUp_Shell(PC pc) 97 { 98 PC_Shell *shell; 99 PetscErrorCode ierr; 100 101 PetscFunctionBegin; 102 shell = (PC_Shell*)pc->data; 103 if (shell->setup) { 104 CHKMEMQ; 105 ierr = (*shell->setup)(shell->ctx);CHKERRQ(ierr); 106 CHKMEMQ; 107 } 108 PetscFunctionReturn(0); 109 } 110 111 #undef __FUNCT__ 112 #define __FUNCT__ "PCApply_Shell" 113 static PetscErrorCode PCApply_Shell(PC pc,Vec x,Vec y) 114 { 115 PC_Shell *shell; 116 PetscErrorCode ierr; 117 118 PetscFunctionBegin; 119 shell = (PC_Shell*)pc->data; 120 if (!shell->apply) SETERRQ(PETSC_ERR_USER,"No apply() routine provided to Shell PC"); 121 PetscStackPush("PCSHELL user function"); 122 CHKMEMQ; 123 ierr = (*shell->apply)(shell->ctx,x,y);CHKERRQ(ierr); 124 CHKMEMQ; 125 PetscStackPop; 126 PetscFunctionReturn(0); 127 } 128 129 #undef __FUNCT__ 130 #define __FUNCT__ "PCPreSolve_Shell" 131 static PetscErrorCode PCPreSolve_Shell(PC pc,KSP ksp,Vec b,Vec x) 132 { 133 PC_Shell *shell; 134 PetscErrorCode ierr; 135 136 PetscFunctionBegin; 137 shell = (PC_Shell*)pc->data; 138 if (!shell->presolve) SETERRQ(PETSC_ERR_USER,"No presolve() routine provided to Shell PC"); 139 ierr = (*shell->presolve)(shell->ctx,ksp,b,x);CHKERRQ(ierr); 140 PetscFunctionReturn(0); 141 } 142 143 #undef __FUNCT__ 144 #define __FUNCT__ "PCPostSolve_Shell" 145 static PetscErrorCode PCPostSolve_Shell(PC pc,KSP ksp,Vec b,Vec x) 146 { 147 PC_Shell *shell; 148 PetscErrorCode ierr; 149 150 PetscFunctionBegin; 151 shell = (PC_Shell*)pc->data; 152 if (!shell->postsolve) SETERRQ(PETSC_ERR_USER,"No postsolve() routine provided to Shell PC"); 153 ierr = (*shell->postsolve)(shell->ctx,ksp,b,x);CHKERRQ(ierr); 154 PetscFunctionReturn(0); 155 } 156 157 #undef __FUNCT__ 158 #define __FUNCT__ "PCApplyTranspose_Shell" 159 static PetscErrorCode PCApplyTranspose_Shell(PC pc,Vec x,Vec y) 160 { 161 PC_Shell *shell; 162 PetscErrorCode ierr; 163 164 PetscFunctionBegin; 165 shell = (PC_Shell*)pc->data; 166 if (!shell->applytranspose) SETERRQ(PETSC_ERR_USER,"No applytranspose() routine provided to Shell PC"); 167 ierr = (*shell->applytranspose)(shell->ctx,x,y);CHKERRQ(ierr); 168 PetscFunctionReturn(0); 169 } 170 171 #undef __FUNCT__ 172 #define __FUNCT__ "PCApplyRichardson_Shell" 173 static PetscErrorCode PCApplyRichardson_Shell(PC pc,Vec x,Vec y,Vec w,PetscReal rtol,PetscReal abstol, PetscReal dtol,PetscInt it) 174 { 175 PetscErrorCode ierr; 176 PC_Shell *shell; 177 178 PetscFunctionBegin; 179 shell = (PC_Shell*)pc->data; 180 ierr = (*shell->applyrich)(shell->ctx,x,y,w,rtol,abstol,dtol,it);CHKERRQ(ierr); 181 PetscFunctionReturn(0); 182 } 183 184 #undef __FUNCT__ 185 #define __FUNCT__ "PCDestroy_Shell" 186 static PetscErrorCode PCDestroy_Shell(PC pc) 187 { 188 PC_Shell *shell = (PC_Shell*)pc->data; 189 PetscErrorCode ierr; 190 191 PetscFunctionBegin; 192 if (shell->name) {ierr = PetscFree(shell->name);} 193 ierr = PetscFree(shell);CHKERRQ(ierr); 194 PetscFunctionReturn(0); 195 } 196 197 #undef __FUNCT__ 198 #define __FUNCT__ "PCView_Shell" 199 static PetscErrorCode PCView_Shell(PC pc,PetscViewer viewer) 200 { 201 PC_Shell *shell = (PC_Shell*)pc->data; 202 PetscErrorCode ierr; 203 PetscTruth iascii; 204 205 PetscFunctionBegin; 206 ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);CHKERRQ(ierr); 207 if (iascii) { 208 if (shell->name) {ierr = PetscViewerASCIIPrintf(viewer," Shell: %s\n",shell->name);CHKERRQ(ierr);} 209 else {ierr = PetscViewerASCIIPrintf(viewer," Shell: no name\n");CHKERRQ(ierr);} 210 } 211 if (shell->view) { 212 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 213 ierr = (*shell->view)(shell->ctx,viewer);CHKERRQ(ierr); 214 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 215 } 216 PetscFunctionReturn(0); 217 } 218 219 /* ------------------------------------------------------------------------------*/ 220 EXTERN_C_BEGIN 221 #undef __FUNCT__ 222 #define __FUNCT__ "PCShellSetSetUp_Shell" 223 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetSetUp_Shell(PC pc, PetscErrorCode (*setup)(void*)) 224 { 225 PC_Shell *shell; 226 227 PetscFunctionBegin; 228 shell = (PC_Shell*)pc->data; 229 shell->setup = setup; 230 PetscFunctionReturn(0); 231 } 232 EXTERN_C_END 233 234 EXTERN_C_BEGIN 235 #undef __FUNCT__ 236 #define __FUNCT__ "PCShellSetApply_Shell" 237 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApply_Shell(PC pc,PetscErrorCode (*apply)(void*,Vec,Vec)) 238 { 239 PC_Shell *shell; 240 241 PetscFunctionBegin; 242 shell = (PC_Shell*)pc->data; 243 shell->apply = apply; 244 PetscFunctionReturn(0); 245 } 246 EXTERN_C_END 247 248 EXTERN_C_BEGIN 249 #undef __FUNCT__ 250 #define __FUNCT__ "PCShellSetPreSolve_Shell" 251 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetPreSolve_Shell(PC pc,PetscErrorCode (*presolve)(void*,KSP,Vec,Vec)) 252 { 253 PC_Shell *shell; 254 255 PetscFunctionBegin; 256 shell = (PC_Shell*)pc->data; 257 shell->presolve = presolve; 258 if (presolve) { 259 pc->ops->presolve = PCPreSolve_Shell; 260 } else { 261 pc->ops->presolve = 0; 262 } 263 PetscFunctionReturn(0); 264 } 265 EXTERN_C_END 266 267 EXTERN_C_BEGIN 268 #undef __FUNCT__ 269 #define __FUNCT__ "PCShellSetPostSolve_Shell" 270 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetPostSolve_Shell(PC pc,PetscErrorCode (*postsolve)(void*,KSP,Vec,Vec)) 271 { 272 PC_Shell *shell; 273 274 PetscFunctionBegin; 275 shell = (PC_Shell*)pc->data; 276 shell->postsolve = postsolve; 277 if (postsolve) { 278 pc->ops->postsolve = PCPostSolve_Shell; 279 } else { 280 pc->ops->postsolve = 0; 281 } 282 PetscFunctionReturn(0); 283 } 284 EXTERN_C_END 285 286 EXTERN_C_BEGIN 287 #undef __FUNCT__ 288 #define __FUNCT__ "PCShellSetView_Shell" 289 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetView_Shell(PC pc,PetscErrorCode (*view)(void*,PetscViewer)) 290 { 291 PC_Shell *shell; 292 293 PetscFunctionBegin; 294 shell = (PC_Shell*)pc->data; 295 shell->view = view; 296 PetscFunctionReturn(0); 297 } 298 EXTERN_C_END 299 300 EXTERN_C_BEGIN 301 #undef __FUNCT__ 302 #define __FUNCT__ "PCShellSetApplyTranspose_Shell" 303 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApplyTranspose_Shell(PC pc,PetscErrorCode (*applytranspose)(void*,Vec,Vec)) 304 { 305 PC_Shell *shell; 306 307 PetscFunctionBegin; 308 shell = (PC_Shell*)pc->data; 309 shell->applytranspose = applytranspose; 310 PetscFunctionReturn(0); 311 } 312 EXTERN_C_END 313 314 EXTERN_C_BEGIN 315 #undef __FUNCT__ 316 #define __FUNCT__ "PCShellSetName_Shell" 317 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetName_Shell(PC pc,const char name[]) 318 { 319 PC_Shell *shell; 320 PetscErrorCode ierr; 321 322 PetscFunctionBegin; 323 shell = (PC_Shell*)pc->data; 324 ierr = PetscStrallocpy(name,&shell->name);CHKERRQ(ierr); 325 PetscFunctionReturn(0); 326 } 327 EXTERN_C_END 328 329 EXTERN_C_BEGIN 330 #undef __FUNCT__ 331 #define __FUNCT__ "PCShellGetName_Shell" 332 PetscErrorCode PETSCKSP_DLLEXPORT PCShellGetName_Shell(PC pc,char *name[]) 333 { 334 PC_Shell *shell; 335 336 PetscFunctionBegin; 337 shell = (PC_Shell*)pc->data; 338 *name = shell->name; 339 PetscFunctionReturn(0); 340 } 341 EXTERN_C_END 342 343 EXTERN_C_BEGIN 344 #undef __FUNCT__ 345 #define __FUNCT__ "PCShellSetApplyRichardson_Shell" 346 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApplyRichardson_Shell(PC pc,PetscErrorCode (*apply)(void*,Vec,Vec,Vec,PetscReal,PetscReal,PetscReal,PetscInt)) 347 { 348 PC_Shell *shell; 349 350 PetscFunctionBegin; 351 shell = (PC_Shell*)pc->data; 352 pc->ops->applyrichardson = PCApplyRichardson_Shell; 353 shell->applyrich = apply; 354 PetscFunctionReturn(0); 355 } 356 EXTERN_C_END 357 358 /* -------------------------------------------------------------------------------*/ 359 360 #undef __FUNCT__ 361 #define __FUNCT__ "PCShellSetSetUp" 362 /*@C 363 PCShellSetSetUp - Sets routine to use to "setup" the preconditioner whenever the 364 matrix operator is changed. 365 366 Collective on PC 367 368 Input Parameters: 369 + pc - the preconditioner context 370 . setup - the application-provided setup routine 371 372 Calling sequence of setup: 373 .vb 374 PetscErrorCode setup (void *ptr) 375 .ve 376 377 . ptr - the application context 378 379 Level: developer 380 381 .keywords: PC, shell, set, setup, user-provided 382 383 .seealso: PCShellSetApplyRichardson(), PCShellSetApply(), PCShellSetContext() 384 @*/ 385 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetSetUp(PC pc,PetscErrorCode (*setup)(void*)) 386 { 387 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*)); 388 389 PetscFunctionBegin; 390 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 391 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetSetUp_C",(void (**)(void))&f);CHKERRQ(ierr); 392 if (f) { 393 ierr = (*f)(pc,setup);CHKERRQ(ierr); 394 } 395 PetscFunctionReturn(0); 396 } 397 398 399 #undef __FUNCT__ 400 #define __FUNCT__ "PCShellSetView" 401 /*@C 402 PCShellSetView - Sets routine to use as viewer of shell preconditioner 403 404 Collective on PC 405 406 Input Parameters: 407 + pc - the preconditioner context 408 - view - the application-provided view routine 409 410 Calling sequence of apply: 411 .vb 412 PetscErrorCode view(void *ptr,PetscViewer v) 413 .ve 414 415 + ptr - the application context 416 - v - viewer 417 418 Level: developer 419 420 .keywords: PC, shell, set, apply, user-provided 421 422 .seealso: PCShellSetApplyRichardson(), PCShellSetSetUp(), PCShellSetApplyTranspose() 423 @*/ 424 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetView(PC pc,PetscErrorCode (*view)(void*,PetscViewer)) 425 { 426 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,PetscViewer)); 427 428 PetscFunctionBegin; 429 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 430 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetView_C",(void (**)(void))&f);CHKERRQ(ierr); 431 if (f) { 432 ierr = (*f)(pc,view);CHKERRQ(ierr); 433 } 434 PetscFunctionReturn(0); 435 } 436 437 #undef __FUNCT__ 438 #define __FUNCT__ "PCShellSetApply" 439 /*@C 440 PCShellSetApply - Sets routine to use as preconditioner. 441 442 Collective on PC 443 444 Input Parameters: 445 + pc - the preconditioner context 446 - apply - the application-provided preconditioning routine 447 448 Calling sequence of apply: 449 .vb 450 PetscErrorCode apply (void *ptr,Vec xin,Vec xout) 451 .ve 452 453 + ptr - the application context 454 . xin - input vector 455 - xout - output vector 456 457 Level: developer 458 459 .keywords: PC, shell, set, apply, user-provided 460 461 .seealso: PCShellSetApplyRichardson(), PCShellSetSetUp(), PCShellSetApplyTranspose(), PCShellSetContext() 462 @*/ 463 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApply(PC pc,PetscErrorCode (*apply)(void*,Vec,Vec)) 464 { 465 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,Vec,Vec)); 466 467 PetscFunctionBegin; 468 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 469 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetApply_C",(void (**)(void))&f);CHKERRQ(ierr); 470 if (f) { 471 ierr = (*f)(pc,apply);CHKERRQ(ierr); 472 } 473 PetscFunctionReturn(0); 474 } 475 476 #undef __FUNCT__ 477 #define __FUNCT__ "PCShellSetApplyTranspose" 478 /*@C 479 PCShellSetApplyTranspose - Sets routine to use as preconditioner transpose. 480 481 Collective on PC 482 483 Input Parameters: 484 + pc - the preconditioner context 485 - apply - the application-provided preconditioning transpose routine 486 487 Calling sequence of apply: 488 .vb 489 PetscErrorCode applytranspose (void *ptr,Vec xin,Vec xout) 490 .ve 491 492 + ptr - the application context 493 . xin - input vector 494 - xout - output vector 495 496 Level: developer 497 498 Notes: 499 Uses the same context variable as PCShellSetApply(). 500 501 .keywords: PC, shell, set, apply, user-provided 502 503 .seealso: PCShellSetApplyRichardson(), PCShellSetSetUp(), PCShellSetApply(), PCSetContext() 504 @*/ 505 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApplyTranspose(PC pc,PetscErrorCode (*applytranspose)(void*,Vec,Vec)) 506 { 507 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,Vec,Vec)); 508 509 PetscFunctionBegin; 510 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 511 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetApplyTranspose_C",(void (**)(void))&f);CHKERRQ(ierr); 512 if (f) { 513 ierr = (*f)(pc,applytranspose);CHKERRQ(ierr); 514 } 515 PetscFunctionReturn(0); 516 } 517 518 #undef __FUNCT__ 519 #define __FUNCT__ "PCShellSetPreSolve" 520 /*@C 521 PCShellSetPreSolve - Sets routine to apply to the operators/vectors before a KSPSolve() is 522 applied. This usually does something like scale the linear system in some application 523 specific way. 524 525 Collective on PC 526 527 Input Parameters: 528 + pc - the preconditioner context 529 - presolve - the application-provided presolve routine 530 531 Calling sequence of presolve: 532 .vb 533 PetscErrorCode presolve (void *ptr,KSP ksp,Vec b,Vec x) 534 .ve 535 536 + ptr - the application context 537 . xin - input vector 538 - xout - output vector 539 540 Level: developer 541 542 .keywords: PC, shell, set, apply, user-provided 543 544 .seealso: PCShellSetApplyRichardson(), PCShellSetSetUp(), PCShellSetApplyTranspose(), PCShellSetPostSolve(), PCShellSetContext() 545 @*/ 546 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetPreSolve(PC pc,PetscErrorCode (*presolve)(void*,KSP,Vec,Vec)) 547 { 548 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,KSP,Vec,Vec)); 549 550 PetscFunctionBegin; 551 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 552 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetPreSolve_C",(void (**)(void))&f);CHKERRQ(ierr); 553 if (f) { 554 ierr = (*f)(pc,presolve);CHKERRQ(ierr); 555 } 556 PetscFunctionReturn(0); 557 } 558 559 #undef __FUNCT__ 560 #define __FUNCT__ "PCShellSetPostSolve" 561 /*@C 562 PCShellSetPostSolve - Sets routine to apply to the operators/vectors before a KSPSolve() is 563 applied. This usually does something like scale the linear system in some application 564 specific way. 565 566 Collective on PC 567 568 Input Parameters: 569 + pc - the preconditioner context 570 - postsolve - the application-provided presolve routine 571 572 Calling sequence of postsolve: 573 .vb 574 PetscErrorCode postsolve(void *ptr,KSP ksp,Vec b,Vec x) 575 .ve 576 577 + ptr - the application context 578 . xin - input vector 579 - xout - output vector 580 581 Level: developer 582 583 .keywords: PC, shell, set, apply, user-provided 584 585 .seealso: PCShellSetApplyRichardson(), PCShellSetSetUp(), PCShellSetApplyTranspose(), PCShellSetPreSolve(), PCShellSetContext() 586 @*/ 587 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetPostSolve(PC pc,PetscErrorCode (*postsolve)(void*,KSP,Vec,Vec)) 588 { 589 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,KSP,Vec,Vec)); 590 591 PetscFunctionBegin; 592 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 593 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetPostSolve_C",(void (**)(void))&f);CHKERRQ(ierr); 594 if (f) { 595 ierr = (*f)(pc,postsolve);CHKERRQ(ierr); 596 } 597 PetscFunctionReturn(0); 598 } 599 600 #undef __FUNCT__ 601 #define __FUNCT__ "PCShellSetName" 602 /*@C 603 PCShellSetName - Sets an optional name to associate with a shell 604 preconditioner. 605 606 Not Collective 607 608 Input Parameters: 609 + pc - the preconditioner context 610 - name - character string describing shell preconditioner 611 612 Level: developer 613 614 .keywords: PC, shell, set, name, user-provided 615 616 .seealso: PCShellGetName() 617 @*/ 618 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetName(PC pc,const char name[]) 619 { 620 PetscErrorCode ierr,(*f)(PC,const char []); 621 622 PetscFunctionBegin; 623 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 624 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetName_C",(void (**)(void))&f);CHKERRQ(ierr); 625 if (f) { 626 ierr = (*f)(pc,name);CHKERRQ(ierr); 627 } 628 PetscFunctionReturn(0); 629 } 630 631 #undef __FUNCT__ 632 #define __FUNCT__ "PCShellGetName" 633 /*@C 634 PCShellGetName - Gets an optional name that the user has set for a shell 635 preconditioner. 636 637 Not Collective 638 639 Input Parameter: 640 . pc - the preconditioner context 641 642 Output Parameter: 643 . name - character string describing shell preconditioner (you should not free this) 644 645 Level: developer 646 647 .keywords: PC, shell, get, name, user-provided 648 649 .seealso: PCShellSetName() 650 @*/ 651 PetscErrorCode PETSCKSP_DLLEXPORT PCShellGetName(PC pc,char *name[]) 652 { 653 PetscErrorCode ierr,(*f)(PC,char *[]); 654 655 PetscFunctionBegin; 656 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 657 PetscValidPointer(name,2); 658 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellGetName_C",(void (**)(void))&f);CHKERRQ(ierr); 659 if (f) { 660 ierr = (*f)(pc,name);CHKERRQ(ierr); 661 } else { 662 SETERRQ(PETSC_ERR_ARG_WRONG,"Not shell preconditioner, cannot get name"); 663 } 664 PetscFunctionReturn(0); 665 } 666 667 #undef __FUNCT__ 668 #define __FUNCT__ "PCShellSetApplyRichardson" 669 /*@C 670 PCShellSetApplyRichardson - Sets routine to use as preconditioner 671 in Richardson iteration. 672 673 Collective on PC 674 675 Input Parameters: 676 + pc - the preconditioner context 677 - apply - the application-provided preconditioning routine 678 679 Calling sequence of apply: 680 .vb 681 PetscErrorCode apply (void *ptr,Vec b,Vec x,Vec r,PetscReal rtol,PetscReal abstol,PetscReal dtol,PetscInt maxits) 682 .ve 683 684 + ptr - the application context 685 . b - right-hand-side 686 . x - current iterate 687 . r - work space 688 . rtol - relative tolerance of residual norm to stop at 689 . abstol - absolute tolerance of residual norm to stop at 690 . dtol - if residual norm increases by this factor than return 691 - maxits - number of iterations to run 692 693 Level: developer 694 695 .keywords: PC, shell, set, apply, Richardson, user-provided 696 697 .seealso: PCShellSetApply(), PCShellSetContext() 698 @*/ 699 PetscErrorCode PETSCKSP_DLLEXPORT PCShellSetApplyRichardson(PC pc,PetscErrorCode (*apply)(void*,Vec,Vec,Vec,PetscReal,PetscReal,PetscReal,PetscInt)) 700 { 701 PetscErrorCode ierr,(*f)(PC,PetscErrorCode (*)(void*,Vec,Vec,Vec,PetscReal,PetscReal,PetscReal,PetscInt)); 702 703 PetscFunctionBegin; 704 PetscValidHeaderSpecific(pc,PC_COOKIE,1); 705 ierr = PetscObjectQueryFunction((PetscObject)pc,"PCShellSetApplyRichardson_C",(void (**)(void))&f);CHKERRQ(ierr); 706 if (f) { 707 ierr = (*f)(pc,apply);CHKERRQ(ierr); 708 } 709 PetscFunctionReturn(0); 710 } 711 712 /*MC 713 PCSHELL - Creates a new preconditioner class for use with your 714 own private data storage format. 715 716 Level: advanced 717 718 Concepts: providing your own preconditioner 719 720 Usage: 721 $ PetscErrorCode (*mult)(void*,Vec,Vec); 722 $ PetscErrorCode (*setup)(void*); 723 $ PCCreate(comm,&pc); 724 $ PCSetType(pc,PCSHELL); 725 $ PCShellSetApply(pc,mult); 726 $ PCShellSetContext(pc,ctx) 727 $ PCShellSetSetUp(pc,setup); (optional) 728 729 .seealso: PCCreate(), PCSetType(), PCType (for list of available types), PC, 730 MATSHELL, PCShellSetUp(), PCShellSetApply(), PCShellSetView(), 731 PCShellSetApplyTranpose(), PCShellSetName(), PCShellSetApplyRichardson(), 732 PCShellGetName(), PCShellSetContext(), PCShellGetContext() 733 M*/ 734 735 EXTERN_C_BEGIN 736 #undef __FUNCT__ 737 #define __FUNCT__ "PCCreate_Shell" 738 PetscErrorCode PETSCKSP_DLLEXPORT PCCreate_Shell(PC pc) 739 { 740 PetscErrorCode ierr; 741 PC_Shell *shell; 742 743 PetscFunctionBegin; 744 pc->ops->destroy = PCDestroy_Shell; 745 ierr = PetscNew(PC_Shell,&shell);CHKERRQ(ierr); 746 ierr = PetscLogObjectMemory(pc,sizeof(PC_Shell));CHKERRQ(ierr); 747 pc->data = (void*)shell; 748 pc->name = 0; 749 750 pc->ops->apply = PCApply_Shell; 751 pc->ops->view = PCView_Shell; 752 pc->ops->applytranspose = PCApplyTranspose_Shell; 753 pc->ops->applyrichardson = 0; 754 pc->ops->setup = PCSetUp_Shell; 755 pc->ops->presolve = 0; 756 pc->ops->postsolve = 0; 757 pc->ops->view = PCView_Shell; 758 759 shell->apply = 0; 760 shell->applytranspose = 0; 761 shell->name = 0; 762 shell->applyrich = 0; 763 shell->presolve = 0; 764 shell->postsolve = 0; 765 shell->ctx = 0; 766 shell->setup = 0; 767 shell->view = 0; 768 769 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetSetUp_C","PCShellSetSetUp_Shell", 770 PCShellSetSetUp_Shell);CHKERRQ(ierr); 771 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetApply_C","PCShellSetApply_Shell", 772 PCShellSetApply_Shell);CHKERRQ(ierr); 773 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetPreSolve_C","PCShellSetPreSolve_Shell", 774 PCShellSetPreSolve_Shell);CHKERRQ(ierr); 775 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetPostSolve_C","PCShellSetPostSolve_Shell", 776 PCShellSetPostSolve_Shell);CHKERRQ(ierr); 777 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetView_C","PCShellSetView_Shell", 778 PCShellSetView_Shell);CHKERRQ(ierr); 779 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetApplyTranspose_C","PCShellSetApplyTranspose_Shell", 780 PCShellSetApplyTranspose_Shell);CHKERRQ(ierr); 781 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetName_C","PCShellSetName_Shell", 782 PCShellSetName_Shell);CHKERRQ(ierr); 783 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellGetName_C","PCShellGetName_Shell", 784 PCShellGetName_Shell);CHKERRQ(ierr); 785 ierr = PetscObjectComposeFunctionDynamic((PetscObject)pc,"PCShellSetApplyRichardson_C","PCShellSetApplyRichardson_Shell", 786 PCShellSetApplyRichardson_Shell);CHKERRQ(ierr); 787 PetscFunctionReturn(0); 788 } 789 EXTERN_C_END 790 791 792 793 794 795 796