xref: /petsc/src/snes/impls/shell/snesshell.c (revision 1e633543be291cfcfe1cde705e1b44f9f92cb5cc)
1b2951d5eSSatish Balay #include <private/snesimpl.h>             /*I   "petscsnes.h"   I*/
2074cc835SBarry Smith 
3074cc835SBarry Smith typedef struct {PetscErrorCode (*solve)(SNES,Vec);void *ctx;} SNES_Shell;
4074cc835SBarry Smith 
5074cc835SBarry Smith #undef __FUNCT__
6074cc835SBarry Smith #define __FUNCT__ "SNESShellSetSolve"
7074cc835SBarry Smith /*@C
8074cc835SBarry Smith    SNESShellSetSolve - Sets routine to apply as solver
9074cc835SBarry Smith 
10074cc835SBarry Smith    Logically Collective on SNES
11074cc835SBarry Smith 
12074cc835SBarry Smith    Input Parameters:
13074cc835SBarry Smith +  snes - the nonlinear solver context
14074cc835SBarry Smith -  apply - the application-provided solver routine
15074cc835SBarry Smith 
16074cc835SBarry Smith    Calling sequence of solve:
17074cc835SBarry Smith .vb
18074cc835SBarry Smith    PetscErrorCode apply (SNES snes,Vec xout)
19074cc835SBarry Smith .ve
20074cc835SBarry Smith 
21074cc835SBarry Smith +  snes - the preconditioner, get the application context with SNESShellGetContext()
22074cc835SBarry Smith -  xout - solution vector
23074cc835SBarry Smith 
24074cc835SBarry Smith    Notes: the function MUST return an error code of 0 on success and nonzero on failure.
25074cc835SBarry Smith 
26074cc835SBarry Smith    Level: advanced
27074cc835SBarry Smith 
28074cc835SBarry Smith .keywords: SNES, shell, set, apply, user-provided
29074cc835SBarry Smith 
30074cc835SBarry Smith .seealso: SNESSHELL, SNESShellSetContext(), SNESShellGetContext()
31074cc835SBarry Smith @*/
32074cc835SBarry Smith PetscErrorCode  SNESShellSetSolve(SNES snes,PetscErrorCode (*solve)(SNES,Vec))
33074cc835SBarry Smith {
34074cc835SBarry Smith   PetscErrorCode ierr;
35074cc835SBarry Smith 
36074cc835SBarry Smith   PetscFunctionBegin;
37074cc835SBarry Smith   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
38074cc835SBarry Smith   ierr = PetscTryMethod(snes,"SNESShellSetSolve_C",(SNES,PetscErrorCode (*)(SNES,Vec)),(snes,solve));CHKERRQ(ierr);
39074cc835SBarry Smith   PetscFunctionReturn(0);
40074cc835SBarry Smith }
41074cc835SBarry Smith 
42074cc835SBarry Smith #undef __FUNCT__
43074cc835SBarry Smith #define __FUNCT__ "SNESReset_Shell"
44074cc835SBarry Smith PetscErrorCode SNESReset_Shell(SNES snes)
45074cc835SBarry Smith {
46074cc835SBarry Smith   SNES_Shell     *shell = (SNES_Shell*) snes->data;
47074cc835SBarry Smith 
48074cc835SBarry Smith   PetscFunctionBegin;
49074cc835SBarry Smith   PetscFunctionReturn(0);
50074cc835SBarry Smith }
51074cc835SBarry Smith 
52074cc835SBarry Smith #undef __FUNCT__
53074cc835SBarry Smith #define __FUNCT__ "SNESDestroy_Shell"
54074cc835SBarry Smith PetscErrorCode SNESDestroy_Shell(SNES snes)
55074cc835SBarry Smith {
56074cc835SBarry Smith   PetscErrorCode ierr;
57074cc835SBarry Smith 
58074cc835SBarry Smith   PetscFunctionBegin;
59074cc835SBarry Smith   ierr = SNESReset_Shell(snes);CHKERRQ(ierr);
60074cc835SBarry Smith   ierr = PetscFree(snes->data);
61074cc835SBarry Smith   PetscFunctionReturn(0);
62074cc835SBarry Smith }
63074cc835SBarry Smith 
64074cc835SBarry Smith #undef __FUNCT__
65074cc835SBarry Smith #define __FUNCT__ "SNESSetUp_Shell"
66074cc835SBarry Smith PetscErrorCode SNESSetUp_Shell(SNES snes)
67074cc835SBarry Smith {
68074cc835SBarry Smith   SNES_Shell    *shell = (SNES_Shell *) snes->data;
69074cc835SBarry Smith 
70074cc835SBarry Smith   PetscFunctionBegin;
71074cc835SBarry Smith   PetscFunctionReturn(0);
72074cc835SBarry Smith }
73074cc835SBarry Smith 
74074cc835SBarry Smith #undef __FUNCT__
75074cc835SBarry Smith #define __FUNCT__ "SNESSetFromOptions_Shell"
76074cc835SBarry Smith PetscErrorCode SNESSetFromOptions_Shell(SNES snes)
77074cc835SBarry Smith {
78074cc835SBarry Smith   SNES_Shell     *shell = (SNES_Shell *) snes->data;
79074cc835SBarry Smith   PetscErrorCode ierr;
80074cc835SBarry Smith 
81074cc835SBarry Smith   PetscFunctionBegin;
82074cc835SBarry Smith   ierr = PetscOptionsHead("SNES Shell options");CHKERRQ(ierr);
83074cc835SBarry Smith   PetscFunctionReturn(0);
84074cc835SBarry Smith }
85074cc835SBarry Smith 
86074cc835SBarry Smith #undef __FUNCT__
87074cc835SBarry Smith #define __FUNCT__ "SNESView_Shell"
88074cc835SBarry Smith PetscErrorCode SNESView_Shell(SNES snes, PetscViewer viewer)
89074cc835SBarry Smith {
90074cc835SBarry Smith   SNES_Shell     *shell = (SNES_Shell *) snes->data;
91074cc835SBarry Smith 
92074cc835SBarry Smith   PetscFunctionBegin;
93074cc835SBarry Smith   PetscFunctionReturn(0);
94074cc835SBarry Smith }
95074cc835SBarry Smith 
96074cc835SBarry Smith #undef __FUNCT__
97074cc835SBarry Smith #define __FUNCT__ "SNESShellGetContext"
98074cc835SBarry Smith /*@C
99074cc835SBarry Smith     SNESShellGetContext - Returns the user-provided context associated with a shell SNES
100074cc835SBarry Smith 
101074cc835SBarry Smith     Not Collective
102074cc835SBarry Smith 
103074cc835SBarry Smith     Input Parameter:
104074cc835SBarry Smith .   snes - should have been created with SNESSetType(snes,SNESSHELL);
105074cc835SBarry Smith 
106074cc835SBarry Smith     Output Parameter:
107074cc835SBarry Smith .   ctx - the user provided context
108074cc835SBarry Smith 
109074cc835SBarry Smith     Level: advanced
110074cc835SBarry Smith 
111074cc835SBarry Smith     Notes:
112074cc835SBarry Smith     This routine is intended for use within various shell routines
113074cc835SBarry Smith 
114074cc835SBarry Smith .keywords: SNES, shell, get, context
115074cc835SBarry Smith 
116074cc835SBarry Smith .seealso: SNESCreateShell(), SNESShellSetContext()
117074cc835SBarry Smith @*/
118074cc835SBarry Smith PetscErrorCode  SNESShellGetContext(SNES snes,void **ctx)
119074cc835SBarry Smith {
120074cc835SBarry Smith   PetscErrorCode ierr;
121074cc835SBarry Smith   PetscBool      flg;
122074cc835SBarry Smith 
123074cc835SBarry Smith   PetscFunctionBegin;
124074cc835SBarry Smith   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
125074cc835SBarry Smith   PetscValidPointer(ctx,2);
126074cc835SBarry Smith   ierr = PetscTypeCompare((PetscObject)snes,SNESSHELL,&flg);CHKERRQ(ierr);
127074cc835SBarry Smith   if (!flg) *ctx = 0;
128074cc835SBarry Smith   else      *ctx = ((SNES_Shell*)(snes->data))->ctx;
129074cc835SBarry Smith   PetscFunctionReturn(0);
130074cc835SBarry Smith }
131074cc835SBarry Smith 
132074cc835SBarry Smith #undef __FUNCT__
133074cc835SBarry Smith #define __FUNCT__ "SNESShellSetContext"
134074cc835SBarry Smith /*@
135074cc835SBarry Smith     SNESShellSetContext - sets the context for a shell SNES
136074cc835SBarry Smith 
137074cc835SBarry Smith    Logically Collective on SNES
138074cc835SBarry Smith 
139074cc835SBarry Smith     Input Parameters:
140074cc835SBarry Smith +   snes - the shell SNES
141074cc835SBarry Smith -   ctx - the context
142074cc835SBarry Smith 
143074cc835SBarry Smith    Level: advanced
144074cc835SBarry Smith 
145074cc835SBarry Smith    Fortran Notes: The context can only be an integer or a PetscObject
146074cc835SBarry Smith       unfortunately it cannot be a Fortran array or derived type.
147074cc835SBarry Smith 
148074cc835SBarry Smith 
149074cc835SBarry Smith .seealso: SNESCreateShell(), SNESShellGetContext()
150074cc835SBarry Smith @*/
151074cc835SBarry Smith PetscErrorCode  SNESShellSetContext(SNES snes,void *ctx)
152074cc835SBarry Smith {
153074cc835SBarry Smith   SNES_Shell     *shell = (SNES_Shell*)snes->data;
154074cc835SBarry Smith   PetscErrorCode ierr;
155074cc835SBarry Smith   PetscBool      flg;
156074cc835SBarry Smith 
157074cc835SBarry Smith   PetscFunctionBegin;
158074cc835SBarry Smith   PetscValidHeaderSpecific(snes,SNES_CLASSID,1);
159074cc835SBarry Smith   ierr = PetscTypeCompare((PetscObject)snes,SNESSHELL,&flg);CHKERRQ(ierr);
160074cc835SBarry Smith   if (flg) {
161074cc835SBarry Smith     shell->ctx = ctx;
162074cc835SBarry Smith   }
163074cc835SBarry Smith   PetscFunctionReturn(0);
164074cc835SBarry Smith }
165074cc835SBarry Smith 
166074cc835SBarry Smith #undef __FUNCT__
167074cc835SBarry Smith #define __FUNCT__ "SNESSolve_Shell"
168074cc835SBarry Smith PetscErrorCode SNESSolve_Shell(SNES snes)
169074cc835SBarry Smith {
170074cc835SBarry Smith   SNES_Shell     *shell = (SNES_Shell *) snes->data;
171074cc835SBarry Smith   PetscErrorCode ierr;
172074cc835SBarry Smith 
173074cc835SBarry Smith   PetscFunctionBegin;
174074cc835SBarry Smith   if (!shell->solve) SETERRQ(((PetscObject)snes)->comm,PETSC_ERR_ARG_WRONGSTATE,"Must call SNESShellSetSolve() first");
175*1e633543SBarry Smith   snes->reason = SNES_CONVERGED_ITS;
176074cc835SBarry Smith   ierr = (*shell->solve)(snes,snes->vec_sol);CHKERRQ(ierr);
177074cc835SBarry Smith   PetscFunctionReturn(0);
178074cc835SBarry Smith }
179074cc835SBarry Smith 
180074cc835SBarry Smith EXTERN_C_BEGIN
181074cc835SBarry Smith #undef __FUNCT__
182074cc835SBarry Smith #define __FUNCT__ "SNESShellSetSolve_Shell"
183074cc835SBarry Smith PetscErrorCode  SNESShellSetSolve_Shell(SNES snes,PetscErrorCode (*solve)(SNES,Vec))
184074cc835SBarry Smith {
185074cc835SBarry Smith   SNES_Shell *shell = (SNES_Shell*)snes->data;
186074cc835SBarry Smith 
187074cc835SBarry Smith   PetscFunctionBegin;
188074cc835SBarry Smith   shell->solve = solve;
189074cc835SBarry Smith   PetscFunctionReturn(0);
190074cc835SBarry Smith }
191074cc835SBarry Smith EXTERN_C_END
192074cc835SBarry Smith 
193074cc835SBarry Smith /*MC
194074cc835SBarry Smith   SNESSHELL - a user provided nonlinear solver
195074cc835SBarry Smith 
196074cc835SBarry Smith    Level: advanced
197074cc835SBarry Smith 
198074cc835SBarry Smith .seealso: SNESCreate(), SNES, SNESSetType(), SNESType (for list of available types)
199074cc835SBarry Smith M*/
200074cc835SBarry Smith 
201074cc835SBarry Smith EXTERN_C_BEGIN
202074cc835SBarry Smith #undef __FUNCT__
203074cc835SBarry Smith #define __FUNCT__ "SNESCreate_Shell"
204074cc835SBarry Smith PetscErrorCode SNESCreate_Shell(SNES snes)
205074cc835SBarry Smith {
206074cc835SBarry Smith   SNES_Shell     *shell;
207074cc835SBarry Smith   PetscErrorCode ierr;
208074cc835SBarry Smith 
209074cc835SBarry Smith   PetscFunctionBegin;
210074cc835SBarry Smith   snes->ops->destroy        = SNESDestroy_Shell;
211074cc835SBarry Smith   snes->ops->setup          = SNESSetUp_Shell;
212074cc835SBarry Smith   snes->ops->setfromoptions = SNESSetFromOptions_Shell;
213074cc835SBarry Smith   snes->ops->view           = SNESView_Shell;
214074cc835SBarry Smith   snes->ops->solve          = SNESSolve_Shell;
215074cc835SBarry Smith   snes->ops->reset          = SNESReset_Shell;
216074cc835SBarry Smith 
217074cc835SBarry Smith   snes->usesksp             = PETSC_FALSE;
218074cc835SBarry Smith 
219074cc835SBarry Smith   ierr = PetscNewLog(snes, SNES_Shell, &shell);CHKERRQ(ierr);
220074cc835SBarry Smith   snes->data = (void*) shell;
221074cc835SBarry Smith   ierr = PetscObjectComposeFunctionDynamic((PetscObject)snes,"SNESShellSetSolve_C","SNESShellSetSolve_Shell",SNESShellSetSolve_Shell);CHKERRQ(ierr);
222074cc835SBarry Smith   PetscFunctionReturn(0);
223074cc835SBarry Smith }
224074cc835SBarry Smith EXTERN_C_END
225