xref: /petsc/src/snes/impls/shell/snesshell.c (revision c3339decea92175325d9368fa13196bcd0e0e58b)
1af0996ceSBarry Smith #include <petsc/private/snesimpl.h> /*I   "petscsnes.h"   I*/
2074cc835SBarry Smith 
39371c9d4SSatish Balay typedef struct {
49371c9d4SSatish Balay   PetscErrorCode (*solve)(SNES, Vec);
59371c9d4SSatish Balay   void *ctx;
69371c9d4SSatish Balay } SNES_Shell;
7074cc835SBarry Smith 
8074cc835SBarry Smith /*@C
9074cc835SBarry Smith    SNESShellSetSolve - Sets routine to apply as solver
10074cc835SBarry Smith 
11*c3339decSBarry Smith    Logically Collective
12074cc835SBarry Smith 
13074cc835SBarry Smith    Input Parameters:
14f6dfbefdSBarry Smith +  snes - the `SNES` nonlinear solver context
15074cc835SBarry Smith -  apply - the application-provided solver routine
16074cc835SBarry Smith 
17074cc835SBarry Smith    Calling sequence of solve:
18074cc835SBarry Smith .vb
19074cc835SBarry Smith    PetscErrorCode apply (SNES snes,Vec xout)
20074cc835SBarry Smith .ve
21074cc835SBarry Smith 
22f6dfbefdSBarry Smith +  snes - the preconditioner, get the application context with `SNESShellGetContext()` provided with `SNESShelletContext()`
23074cc835SBarry Smith -  xout - solution vector
24074cc835SBarry Smith 
25074cc835SBarry Smith    Level: advanced
26074cc835SBarry Smith 
27db781477SPatrick Sanan .seealso: `SNESSHELL`, `SNESShellSetContext()`, `SNESShellGetContext()`
28074cc835SBarry Smith @*/
29d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESShellSetSolve(SNES snes, PetscErrorCode (*solve)(SNES, Vec))
30d71ae5a4SJacob Faibussowitsch {
31074cc835SBarry Smith   PetscFunctionBegin;
32074cc835SBarry Smith   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
33cac4c232SBarry Smith   PetscTryMethod(snes, "SNESShellSetSolve_C", (SNES, PetscErrorCode(*)(SNES, Vec)), (snes, solve));
34074cc835SBarry Smith   PetscFunctionReturn(0);
35074cc835SBarry Smith }
36074cc835SBarry Smith 
37d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESReset_Shell(SNES snes)
38d71ae5a4SJacob Faibussowitsch {
39074cc835SBarry Smith   PetscFunctionBegin;
40074cc835SBarry Smith   PetscFunctionReturn(0);
41074cc835SBarry Smith }
42074cc835SBarry Smith 
43d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESDestroy_Shell(SNES snes)
44d71ae5a4SJacob Faibussowitsch {
45074cc835SBarry Smith   PetscFunctionBegin;
469566063dSJacob Faibussowitsch   PetscCall(SNESReset_Shell(snes));
479566063dSJacob Faibussowitsch   PetscCall(PetscFree(snes->data));
48074cc835SBarry Smith   PetscFunctionReturn(0);
49074cc835SBarry Smith }
50074cc835SBarry Smith 
51d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESSetUp_Shell(SNES snes)
52d71ae5a4SJacob Faibussowitsch {
53074cc835SBarry Smith   PetscFunctionBegin;
54074cc835SBarry Smith   PetscFunctionReturn(0);
55074cc835SBarry Smith }
56074cc835SBarry Smith 
57d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESSetFromOptions_Shell(SNES snes, PetscOptionItems *PetscOptionsObject)
58d71ae5a4SJacob Faibussowitsch {
59074cc835SBarry Smith   PetscFunctionBegin;
60d0609cedSBarry Smith   PetscOptionsHeadBegin(PetscOptionsObject, "SNES Shell options");
61074cc835SBarry Smith   PetscFunctionReturn(0);
62074cc835SBarry Smith }
63074cc835SBarry Smith 
64d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESView_Shell(SNES snes, PetscViewer viewer)
65d71ae5a4SJacob Faibussowitsch {
66074cc835SBarry Smith   PetscFunctionBegin;
67074cc835SBarry Smith   PetscFunctionReturn(0);
68074cc835SBarry Smith }
69074cc835SBarry Smith 
7090b77ac2SPeter Brune /*@
71f6dfbefdSBarry Smith     SNESShellGetContext - Returns the user-provided context associated with a `SNESSHELL`
72074cc835SBarry Smith 
73074cc835SBarry Smith     Not Collective
74074cc835SBarry Smith 
75074cc835SBarry Smith     Input Parameter:
76f6dfbefdSBarry Smith .   snes - should have been created with `SNESSetType`(snes,`SNESSHELL`);
77074cc835SBarry Smith 
78074cc835SBarry Smith     Output Parameter:
79074cc835SBarry Smith .   ctx - the user provided context
80074cc835SBarry Smith 
81074cc835SBarry Smith     Level: advanced
82074cc835SBarry Smith 
83f6dfbefdSBarry Smith .seealso: `SNESSHELL`, `SNESCreateShell()`, `SNESShellSetContext()`
84074cc835SBarry Smith @*/
85d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESShellGetContext(SNES snes, void *ctx)
86d71ae5a4SJacob Faibussowitsch {
87074cc835SBarry Smith   PetscBool flg;
88074cc835SBarry Smith 
89074cc835SBarry Smith   PetscFunctionBegin;
90074cc835SBarry Smith   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
91074cc835SBarry Smith   PetscValidPointer(ctx, 2);
929566063dSJacob Faibussowitsch   PetscCall(PetscObjectTypeCompare((PetscObject)snes, SNESSHELL, &flg));
933ec1f749SStefano Zampini   if (!flg) *(void **)ctx = NULL;
943ec1f749SStefano Zampini   else *(void **)ctx = ((SNES_Shell *)(snes->data))->ctx;
95074cc835SBarry Smith   PetscFunctionReturn(0);
96074cc835SBarry Smith }
97074cc835SBarry Smith 
98074cc835SBarry Smith /*@
99f6dfbefdSBarry Smith     SNESShellSetContext - sets the context for a `SNESSHELL`
100074cc835SBarry Smith 
101*c3339decSBarry Smith    Logically Collective
102074cc835SBarry Smith 
103074cc835SBarry Smith     Input Parameters:
104f6dfbefdSBarry Smith +   snes - the `SNESSHELL`
105074cc835SBarry Smith -   ctx - the context
106074cc835SBarry Smith 
107074cc835SBarry Smith    Level: advanced
108074cc835SBarry Smith 
109f6dfbefdSBarry Smith    Fortran Note:
110f6dfbefdSBarry Smith    The context can only be an integer or a `PetscObject` it cannot be a Fortran array or derived type.
111074cc835SBarry Smith 
112f6dfbefdSBarry Smith .seealso: `SNESSHELL`, `SNESCreateShell()`, `SNESShellGetContext()`
113074cc835SBarry Smith @*/
114d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESShellSetContext(SNES snes, void *ctx)
115d71ae5a4SJacob Faibussowitsch {
116074cc835SBarry Smith   SNES_Shell *shell = (SNES_Shell *)snes->data;
117074cc835SBarry Smith   PetscBool   flg;
118074cc835SBarry Smith 
119074cc835SBarry Smith   PetscFunctionBegin;
120074cc835SBarry Smith   PetscValidHeaderSpecific(snes, SNES_CLASSID, 1);
1219566063dSJacob Faibussowitsch   PetscCall(PetscObjectTypeCompare((PetscObject)snes, SNESSHELL, &flg));
1221aa26658SKarl Rupp   if (flg) shell->ctx = ctx;
123074cc835SBarry Smith   PetscFunctionReturn(0);
124074cc835SBarry Smith }
125074cc835SBarry Smith 
126d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESSolve_Shell(SNES snes)
127d71ae5a4SJacob Faibussowitsch {
128074cc835SBarry Smith   SNES_Shell *shell = (SNES_Shell *)snes->data;
129074cc835SBarry Smith 
130074cc835SBarry Smith   PetscFunctionBegin;
13128b400f6SJacob Faibussowitsch   PetscCheck(shell->solve, PetscObjectComm((PetscObject)snes), PETSC_ERR_ARG_WRONGSTATE, "Must call SNESShellSetSolve() first");
1321e633543SBarry Smith   snes->reason = SNES_CONVERGED_ITS;
1339566063dSJacob Faibussowitsch   PetscCall((*shell->solve)(snes, snes->vec_sol));
134074cc835SBarry Smith   PetscFunctionReturn(0);
135074cc835SBarry Smith }
136074cc835SBarry Smith 
137d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESShellSetSolve_Shell(SNES snes, PetscErrorCode (*solve)(SNES, Vec))
138d71ae5a4SJacob Faibussowitsch {
139074cc835SBarry Smith   SNES_Shell *shell = (SNES_Shell *)snes->data;
140074cc835SBarry Smith 
141074cc835SBarry Smith   PetscFunctionBegin;
142074cc835SBarry Smith   shell->solve = solve;
143074cc835SBarry Smith   PetscFunctionReturn(0);
144074cc835SBarry Smith }
145074cc835SBarry Smith 
146074cc835SBarry Smith /*MC
147074cc835SBarry Smith   SNESSHELL - a user provided nonlinear solver
148074cc835SBarry Smith 
149074cc835SBarry Smith    Level: advanced
150074cc835SBarry Smith 
151f6dfbefdSBarry Smith .seealso: `SNESCreate()`, `SNES`, `SNESSetType()`, `SNESType`, `SNESShellGetContext()`, `SNESShellSetContext()`, `SNESShellSetSolve()`
152074cc835SBarry Smith M*/
153074cc835SBarry Smith 
154d71ae5a4SJacob Faibussowitsch PETSC_EXTERN PetscErrorCode SNESCreate_Shell(SNES snes)
155d71ae5a4SJacob Faibussowitsch {
156074cc835SBarry Smith   SNES_Shell *shell;
157074cc835SBarry Smith 
158074cc835SBarry Smith   PetscFunctionBegin;
159074cc835SBarry Smith   snes->ops->destroy        = SNESDestroy_Shell;
160074cc835SBarry Smith   snes->ops->setup          = SNESSetUp_Shell;
161074cc835SBarry Smith   snes->ops->setfromoptions = SNESSetFromOptions_Shell;
162074cc835SBarry Smith   snes->ops->view           = SNESView_Shell;
163074cc835SBarry Smith   snes->ops->solve          = SNESSolve_Shell;
164074cc835SBarry Smith   snes->ops->reset          = SNESReset_Shell;
165074cc835SBarry Smith 
166074cc835SBarry Smith   snes->usesksp = PETSC_FALSE;
167efd4aadfSBarry Smith   snes->usesnpc = PETSC_FALSE;
168074cc835SBarry Smith 
1694fc747eaSLawrence Mitchell   snes->alwayscomputesfinalresidual = PETSC_FALSE;
1704fc747eaSLawrence Mitchell 
1714dfa11a4SJacob Faibussowitsch   PetscCall(PetscNew(&shell));
172074cc835SBarry Smith   snes->data = (void *)shell;
1739566063dSJacob Faibussowitsch   PetscCall(PetscObjectComposeFunction((PetscObject)snes, "SNESShellSetSolve_C", SNESShellSetSolve_Shell));
174074cc835SBarry Smith   PetscFunctionReturn(0);
175074cc835SBarry Smith }
176