xref: /petsc/src/tao/shell/taoshell.c (revision 4dbf25a8fa98e38799e7b47dcb2d8a9309975f41)
1 #include <petsc/private/taoimpl.h> /*I "petsctao.h" I*/
2 
3 typedef struct _n_TaoShell Tao_Shell;
4 
5 struct _n_TaoShell {
6   PetscErrorCode (*solve)(Tao);
7   void *ctx;
8 };
9 
10 /*@C
11   TaoShellSetSolve - Sets routine to apply as solver
12 
13   Logically Collective
14 
15   Input Parameters:
16 + tao   - the nonlinear solver context
17 - solve - the application-provided solver routine
18 
19   Calling sequence of `solve`:
20 . tao - the optimizer, get the application context with `TaoShellGetContext()`
21 
22   Level: advanced
23 
24 .seealso: `Tao`, `TAOSHELL`, `TaoShellSetContext()`, `TaoShellGetContext()`
25 @*/
26 PetscErrorCode TaoShellSetSolve(Tao tao, PetscErrorCode (*solve)(Tao))
27 {
28   Tao_Shell *shell = (Tao_Shell *)tao->data;
29 
30   PetscFunctionBegin;
31   PetscValidHeaderSpecific(tao, TAO_CLASSID, 1);
32   shell->solve = solve;
33   PetscFunctionReturn(PETSC_SUCCESS);
34 }
35 
36 /*@
37   TaoShellGetContext - Returns the user-provided context associated with a `TAOSHELL`
38 
39   Not Collective
40 
41   Input Parameter:
42 . tao - should have been created with `TaoSetType`(tao,`TAOSHELL`);
43 
44   Output Parameter:
45 . ctx - the user provided context
46 
47   Level: advanced
48 
49   Note:
50   This routine is intended for use within various shell routines
51 
52 .seealso: `Tao`, `TAOSHELL`, `TaoShellSetContext()`
53 @*/
54 PetscErrorCode TaoShellGetContext(Tao tao, void *ctx)
55 {
56   PetscBool flg;
57 
58   PetscFunctionBegin;
59   PetscValidHeaderSpecific(tao, TAO_CLASSID, 1);
60   PetscAssertPointer(ctx, 2);
61   PetscCall(PetscObjectTypeCompare((PetscObject)tao, TAOSHELL, &flg));
62   if (!flg) *(void **)ctx = NULL;
63   else *(void **)ctx = ((Tao_Shell *)tao->data)->ctx;
64   PetscFunctionReturn(PETSC_SUCCESS);
65 }
66 
67 /*@
68   TaoShellSetContext - sets the context for a `TAOSHELL`
69 
70   Logically Collective
71 
72   Input Parameters:
73 + tao - the shell Tao
74 - ctx - the context
75 
76   Level: advanced
77 
78 .seealso: `Tao`, `TAOSHELL`, `TaoShellGetContext()`
79 @*/
80 PetscErrorCode TaoShellSetContext(Tao tao, void *ctx)
81 {
82   Tao_Shell *shell = (Tao_Shell *)tao->data;
83   PetscBool  flg;
84 
85   PetscFunctionBegin;
86   PetscValidHeaderSpecific(tao, TAO_CLASSID, 1);
87   PetscCall(PetscObjectTypeCompare((PetscObject)tao, TAOSHELL, &flg));
88   if (flg) shell->ctx = ctx;
89   PetscFunctionReturn(PETSC_SUCCESS);
90 }
91 
92 static PetscErrorCode TaoSolve_Shell(Tao tao)
93 {
94   Tao_Shell *shell = (Tao_Shell *)tao->data;
95 
96   PetscFunctionBegin;
97   PetscCheck(shell->solve, PetscObjectComm((PetscObject)tao), PETSC_ERR_ARG_WRONGSTATE, "Must call TaoShellSetSolve() first");
98   tao->reason = TAO_CONVERGED_USER;
99   PetscCall((*shell->solve)(tao));
100   PetscFunctionReturn(PETSC_SUCCESS);
101 }
102 
103 static PetscErrorCode TaoDestroy_Shell(Tao tao)
104 {
105   PetscFunctionBegin;
106   PetscCall(PetscFree(tao->data));
107   PetscFunctionReturn(PETSC_SUCCESS);
108 }
109 
110 static PetscErrorCode TaoSetUp_Shell(Tao tao)
111 {
112   PetscFunctionBegin;
113   PetscFunctionReturn(PETSC_SUCCESS);
114 }
115 
116 static PetscErrorCode TaoSetFromOptions_Shell(Tao tao, PetscOptionItems PetscOptionsObject)
117 {
118   PetscFunctionBegin;
119   PetscFunctionReturn(PETSC_SUCCESS);
120 }
121 
122 static PetscErrorCode TaoView_Shell(Tao tao, PetscViewer viewer)
123 {
124   PetscFunctionBegin;
125   PetscFunctionReturn(PETSC_SUCCESS);
126 }
127 
128 /*MC
129   TAOSHELL - a user provided optimizer
130 
131    Level: advanced
132 
133 .seealso: `TaoCreate()`, `Tao`, `TaoSetType()`, `TaoType`
134 M*/
135 PETSC_EXTERN PetscErrorCode TaoCreate_Shell(Tao tao)
136 {
137   Tao_Shell *shell;
138 
139   PetscFunctionBegin;
140   tao->ops->destroy        = TaoDestroy_Shell;
141   tao->ops->setup          = TaoSetUp_Shell;
142   tao->ops->setfromoptions = TaoSetFromOptions_Shell;
143   tao->ops->view           = TaoView_Shell;
144   tao->ops->solve          = TaoSolve_Shell;
145 
146   PetscCall(TaoParametersInitialize(tao));
147 
148   PetscCall(PetscNew(&shell));
149   tao->data = (void *)shell;
150   PetscFunctionReturn(PETSC_SUCCESS);
151 }
152