1*b45d2f2cSJed Brown #include <petsc-private/linesearchimpl.h> 2*b45d2f2cSJed Brown #include <petsc-private/snesimpl.h> 36a388c36SPeter Brune 4f40b411bSPeter Brune 56a388c36SPeter Brune typedef struct { 6f1c6b773SPeter Brune SNESLineSearchUserFunc func; 76a388c36SPeter Brune void *ctx; 8f1c6b773SPeter Brune } SNESLineSearch_Shell; 96a388c36SPeter Brune 106a388c36SPeter Brune #undef __FUNCT__ 11f1c6b773SPeter Brune #define __FUNCT__ "SNESLineSearchShellSetUserFunc" 12f40b411bSPeter Brune /*@C 13f1c6b773SPeter Brune SNESLineSearchShellSetUserFunc - Sets the user function for the SNESLineSearch Shell implementation. 14f40b411bSPeter Brune 15f40b411bSPeter Brune Not Collective 16f40b411bSPeter Brune 17cd7522eaSPeter Brune Input Parameters: 18cd7522eaSPeter Brune + linesearch - SNESLineSearch context 19cd7522eaSPeter Brune . func - function implementing the linesearch shell. 20cd7522eaSPeter Brune - ctx - context for func 21cd7522eaSPeter Brune 22cd7522eaSPeter Brune Calling sequence of func: 23cd7522eaSPeter Brune + linesearch - the linesearch instance 24cd7522eaSPeter Brune - ctx - the above mentioned context 25cd7522eaSPeter Brune 26cd7522eaSPeter Brune Usage: 27cd7522eaSPeter Brune 28cd7522eaSPeter Brune $ PetscErrorCode shellfunc(SNESLineSearch linesearch, void * ctx) { 29cd7522eaSPeter Brune $ Vec X, Y, F; 30cd7522eaSPeter Brune $ PetscFunctionBegin; 31cd7522eaSPeter Brune $ ierr = SNESLineSearchSetSuccess(linesearch, PETSC_TRUE);CHKERRQ(ierr); 32cd7522eaSPeter Brune $ ierr = SNESLineSearchGetVecs(linesearch, X, Y, F);CHKERRQ(ierr); 33cd7522eaSPeter Brune $ .. determine lambda .. 34cd7522eaSPeter Brune $ ierr = VecAXPY(X, -lambda, Y);CHKERRQ(ierr) 35cd7522eaSPeter Brune $ ierr = SNESLineSearchComputeNorms(linesearch);CHKERRQ(ierr); 36cd7522eaSPeter Brune $ PetscFunctionReturn(0); 37cd7522eaSPeter Brune $ } 38cd7522eaSPeter Brune $ 39cd7522eaSPeter Brune $ ... 40cd7522eaSPeter Brune $ 41cd7522eaSPeter Brune $ ierr = SNESGetSNESLineSearch(snes, &linesearch);CHKERRQ(ierr); 42cd7522eaSPeter Brune $ ierr = SNESLineSearchSetType(linesearch, SNES_LINESEARCH_SHELL);CHKERRQ(ierr); 43cd7522eaSPeter Brune $ ierr = SNESLineSearchShellSetUserFunc(linesearch, shellfunc, PETSC_NULL);CHKERRQ(ierr); 44cd7522eaSPeter Brune 45f40b411bSPeter Brune Level: advanced 46f40b411bSPeter Brune 47f1c6b773SPeter Brune .keywords: SNESLineSearch, SNESLineSearchShell, Shell 48f40b411bSPeter Brune 49f1c6b773SPeter Brune .seealso: SNESLineSearchShellGetUserFunc() 50f40b411bSPeter Brune @*/ 51f1c6b773SPeter Brune PetscErrorCode SNESLineSearchShellSetUserFunc(SNESLineSearch linesearch, SNESLineSearchUserFunc func, void *ctx) { 526a388c36SPeter Brune 536a388c36SPeter Brune PetscErrorCode ierr; 546a388c36SPeter Brune PetscBool flg; 55f1c6b773SPeter Brune SNESLineSearch_Shell *shell = (SNESLineSearch_Shell *)linesearch->data; 566a388c36SPeter Brune PetscFunctionBegin; 57f1c6b773SPeter Brune PetscValidHeaderSpecific(linesearch, SNESLINESEARCH_CLASSID, 1); 58f1c6b773SPeter Brune ierr = PetscTypeCompare((PetscObject)linesearch,SNES_LINESEARCH_SHELL,&flg);CHKERRQ(ierr); 596a388c36SPeter Brune if (flg) { 606a388c36SPeter Brune shell->ctx = ctx; 619e764e56SPeter Brune shell->func = func; 626a388c36SPeter Brune } 636a388c36SPeter Brune PetscFunctionReturn(0); 646a388c36SPeter Brune } 656a388c36SPeter Brune 666a388c36SPeter Brune 676a388c36SPeter Brune #undef __FUNCT__ 68f1c6b773SPeter Brune #define __FUNCT__ "SNESLineSearchShellGetUserFunc" 69f40b411bSPeter Brune /*@C 70f1c6b773SPeter Brune SNESLineSearchShellGetUserFunc - Gets the user function and context for the shell implementation. 71f40b411bSPeter Brune 72f40b411bSPeter Brune Not Collective 73f40b411bSPeter Brune 74f40b411bSPeter Brune Level: advanced 75f40b411bSPeter Brune 76f1c6b773SPeter Brune .keywords: SNESLineSearch, SNESLineSearchShell, Shell 77f40b411bSPeter Brune 78f1c6b773SPeter Brune .seealso: SNESLineSearchShellSetUserFunc() 79f40b411bSPeter Brune @*/ 80f1c6b773SPeter Brune PetscErrorCode SNESLineSearchShellGetUserFunc(SNESLineSearch linesearch, SNESLineSearchUserFunc *func, void **ctx) { 816a388c36SPeter Brune 826a388c36SPeter Brune PetscErrorCode ierr; 836a388c36SPeter Brune PetscBool flg; 84f1c6b773SPeter Brune SNESLineSearch_Shell *shell = (SNESLineSearch_Shell *)linesearch->data; 856a388c36SPeter Brune PetscFunctionBegin; 86f1c6b773SPeter Brune PetscValidHeaderSpecific(linesearch, SNESLINESEARCH_CLASSID, 1); 876a388c36SPeter Brune if (func) PetscValidPointer(func,2); 886a388c36SPeter Brune if (ctx) PetscValidPointer(ctx,3); 89f1c6b773SPeter Brune ierr = PetscTypeCompare((PetscObject)linesearch,SNES_LINESEARCH_SHELL,&flg);CHKERRQ(ierr); 906a388c36SPeter Brune if (flg) { 916a388c36SPeter Brune *ctx = shell->ctx; 926a388c36SPeter Brune *func = shell->func; 936a388c36SPeter Brune } 946a388c36SPeter Brune PetscFunctionReturn(0); 956a388c36SPeter Brune } 966a388c36SPeter Brune 976a388c36SPeter Brune 986a388c36SPeter Brune #undef __FUNCT__ 99f1c6b773SPeter Brune #define __FUNCT__ "SNESLineSearchApply_Shell" 100f1c6b773SPeter Brune static PetscErrorCode SNESLineSearchApply_Shell(SNESLineSearch linesearch) 1016a388c36SPeter Brune { 102f1c6b773SPeter Brune SNESLineSearch_Shell *shell = (SNESLineSearch_Shell *)linesearch->data; 1036a388c36SPeter Brune PetscErrorCode ierr; 1046a388c36SPeter Brune 1056a388c36SPeter Brune PetscFunctionBegin; 1066a388c36SPeter Brune 1076a388c36SPeter Brune /* apply the user function */ 1086a388c36SPeter Brune if (shell->func) { 1096a388c36SPeter Brune ierr = (*shell->func)(linesearch, shell->ctx);CHKERRQ(ierr); 1106a388c36SPeter Brune } else { 111f1c6b773SPeter Brune SETERRQ(((PetscObject)linesearch)->comm, PETSC_ERR_USER, "SNESLineSearchShell needs to have a shell function set with SNESLineSearchShellSetUserFunc"); 1126a388c36SPeter Brune } 1136a388c36SPeter Brune PetscFunctionReturn(0); 1146a388c36SPeter Brune } 1156a388c36SPeter Brune 1166a388c36SPeter Brune #undef __FUNCT__ 117f1c6b773SPeter Brune #define __FUNCT__ "SNESLineSearchDestroy_Shell" 118f1c6b773SPeter Brune static PetscErrorCode SNESLineSearchDestroy_Shell(SNESLineSearch linesearch) 1196a388c36SPeter Brune { 120f1c6b773SPeter Brune SNESLineSearch_Shell *shell = (SNESLineSearch_Shell *)linesearch->data; 1216a388c36SPeter Brune PetscErrorCode ierr; 1226a388c36SPeter Brune 1236a388c36SPeter Brune PetscFunctionBegin; 1246a388c36SPeter Brune ierr = PetscFree(shell);CHKERRQ(ierr); 1256a388c36SPeter Brune PetscFunctionReturn(0); 1266a388c36SPeter Brune } 1276a388c36SPeter Brune 1286a388c36SPeter Brune #undef __FUNCT__ 129f1c6b773SPeter Brune #define __FUNCT__ "SNESLineSearchCreate_Shell" 130954494b2SJed Brown /*MC 131954494b2SJed Brown 132f1c6b773SPeter Brune SNES_LINESEARCH_SHELL - Provides context for a user-provided line search routine. 133954494b2SJed Brown 134f1c6b773SPeter Brune The user routine has one argument, the SNESLineSearch context. The user uses the interface to 135954494b2SJed Brown extract line search parameters and set them accordingly when the computation is finished. 136954494b2SJed Brown 137cd7522eaSPeter Brune Any of the other line searches may serve as a guide to how this is to be done. There is also a basic 138cd7522eaSPeter Brune template in the documentation for SNESLineSearchShellSetUserFunc(). 139954494b2SJed Brown 140954494b2SJed Brown Level: advanced 141954494b2SJed Brown 142954494b2SJed Brown M*/ 143f1c6b773SPeter Brune PETSC_EXTERN_C PetscErrorCode SNESLineSearchCreate_Shell(SNESLineSearch linesearch) 1446a388c36SPeter Brune { 1456a388c36SPeter Brune 146f1c6b773SPeter Brune SNESLineSearch_Shell *shell; 1476a388c36SPeter Brune PetscErrorCode ierr; 1486a388c36SPeter Brune 1496a388c36SPeter Brune PetscFunctionBegin; 1506a388c36SPeter Brune 151f1c6b773SPeter Brune linesearch->ops->apply = SNESLineSearchApply_Shell; 152f1c6b773SPeter Brune linesearch->ops->destroy = SNESLineSearchDestroy_Shell; 1536a388c36SPeter Brune linesearch->ops->setfromoptions = PETSC_NULL; 1546a388c36SPeter Brune linesearch->ops->reset = PETSC_NULL; 1556a388c36SPeter Brune linesearch->ops->view = PETSC_NULL; 1566a388c36SPeter Brune linesearch->ops->setup = PETSC_NULL; 1576a388c36SPeter Brune 158f1c6b773SPeter Brune ierr = PetscNewLog(linesearch, SNESLineSearch_Shell, &shell);CHKERRQ(ierr); 1596a388c36SPeter Brune linesearch->data = (void*) shell; 1606a388c36SPeter Brune PetscFunctionReturn(0); 1616a388c36SPeter Brune } 162