xref: /petsc/src/tao/snes/taosnes.c (revision 4e8208cbcbc709572b8abe32f33c78b69c819375)
1f4f59681SStefano Zampini #include <petsc/private/taoimpl.h> /*I "petsctao.h" I*/
2f4f59681SStefano Zampini 
3f4f59681SStefano Zampini typedef struct {
4f4f59681SStefano Zampini   SNES      snes;
5f8a48b51SStefano Zampini   PetscBool setfromoptionscalled;
6f4f59681SStefano Zampini } Tao_SNES;
7f4f59681SStefano Zampini 
TaoSolve_SNES(Tao tao)8f4f59681SStefano Zampini static PetscErrorCode TaoSolve_SNES(Tao tao)
9f4f59681SStefano Zampini {
10f4f59681SStefano Zampini   Tao_SNES *taosnes = (Tao_SNES *)tao->data;
114936d809SStefano Zampini   PetscInt  its;
12f4f59681SStefano Zampini 
13f4f59681SStefano Zampini   PetscFunctionBegin;
144936d809SStefano Zampini   /* TODO SNES fails if KSP reaches max_it, while TAO accepts whatever we got */
15f4f59681SStefano Zampini   PetscCall(SNESSolve(taosnes->snes, NULL, tao->solution));
16f4f59681SStefano Zampini   /* TODO REASONS */
17f4f59681SStefano Zampini   tao->reason = TAO_CONVERGED_USER;
184936d809SStefano Zampini   PetscCall(SNESGetIterationNumber(taosnes->snes, &its));
194936d809SStefano Zampini   PetscCall(TaoSetIterationNumber(tao, its));
20f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
21f4f59681SStefano Zampini }
22f4f59681SStefano Zampini 
TaoDestroy_SNES(Tao tao)23f4f59681SStefano Zampini static PetscErrorCode TaoDestroy_SNES(Tao tao)
24f4f59681SStefano Zampini {
25f4f59681SStefano Zampini   Tao_SNES *taosnes = (Tao_SNES *)tao->data;
26f4f59681SStefano Zampini 
27f4f59681SStefano Zampini   PetscFunctionBegin;
28f4f59681SStefano Zampini   PetscCall(SNESDestroy(&taosnes->snes));
29f4f59681SStefano Zampini   PetscCall(PetscFree(tao->data));
30f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
31f4f59681SStefano Zampini }
32f4f59681SStefano Zampini 
TAOSNESObj(SNES snes,Vec X,PetscReal * f,PetscCtx ctx)33*2a8381b2SBarry Smith static PetscErrorCode TAOSNESObj(SNES snes, Vec X, PetscReal *f, PetscCtx ctx)
34f4f59681SStefano Zampini {
35f4f59681SStefano Zampini   Tao tao = (Tao)ctx;
36f4f59681SStefano Zampini 
37f4f59681SStefano Zampini   PetscFunctionBegin;
38f4f59681SStefano Zampini   PetscCall(TaoComputeObjective(tao, X, f));
39f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
40f4f59681SStefano Zampini }
41f4f59681SStefano Zampini 
TAOSNESFunc(SNES snes,Vec X,Vec F,PetscCtx ctx)42*2a8381b2SBarry Smith static PetscErrorCode TAOSNESFunc(SNES snes, Vec X, Vec F, PetscCtx ctx)
43f4f59681SStefano Zampini {
44f4f59681SStefano Zampini   Tao tao = (Tao)ctx;
45f4f59681SStefano Zampini 
46f4f59681SStefano Zampini   PetscFunctionBegin;
47f4f59681SStefano Zampini   PetscCall(TaoComputeGradient(tao, X, F));
48f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
49f4f59681SStefano Zampini }
50f4f59681SStefano Zampini 
TAOSNESJac(SNES snes,Vec X,Mat A,Mat P,PetscCtx ctx)51*2a8381b2SBarry Smith static PetscErrorCode TAOSNESJac(SNES snes, Vec X, Mat A, Mat P, PetscCtx ctx)
52f4f59681SStefano Zampini {
53f4f59681SStefano Zampini   Tao tao = (Tao)ctx;
54f4f59681SStefano Zampini 
55f4f59681SStefano Zampini   PetscFunctionBegin;
56f4f59681SStefano Zampini   PetscCall(TaoComputeHessian(tao, X, A, P));
57f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
58f4f59681SStefano Zampini }
59f4f59681SStefano Zampini 
TAOSNESMonitor(SNES snes,PetscInt its,PetscReal fnorm,PetscCtx ctx)60*2a8381b2SBarry Smith static PetscErrorCode TAOSNESMonitor(SNES snes, PetscInt its, PetscReal fnorm, PetscCtx ctx)
614936d809SStefano Zampini {
624936d809SStefano Zampini   Tao       tao = (Tao)ctx;
634936d809SStefano Zampini   PetscReal obj;
644936d809SStefano Zampini   Vec       X;
654936d809SStefano Zampini 
664936d809SStefano Zampini   PetscFunctionBegin;
674936d809SStefano Zampini   PetscCall(SNESGetSolution(snes, &X));
684936d809SStefano Zampini   PetscCall(TaoComputeObjective(tao, X, &obj));
694936d809SStefano Zampini   PetscCall(TaoSetIterationNumber(tao, its));
704936d809SStefano Zampini   PetscCall(TaoMonitor(tao, its, obj, fnorm, 0.0, 0.0));
714936d809SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
724936d809SStefano Zampini }
734936d809SStefano Zampini 
TaoSetUp_SNES(Tao tao)74f4f59681SStefano Zampini static PetscErrorCode TaoSetUp_SNES(Tao tao)
75f4f59681SStefano Zampini {
76f4f59681SStefano Zampini   Tao_SNES   *taosnes = (Tao_SNES *)tao->data;
77f4f59681SStefano Zampini   Mat         A, P;
78f8a48b51SStefano Zampini   const char *prefix;
79f4f59681SStefano Zampini 
80f4f59681SStefano Zampini   PetscFunctionBegin;
81f8a48b51SStefano Zampini   PetscCall(TaoGetOptionsPrefix(tao, &prefix));
82f8a48b51SStefano Zampini   PetscCall(SNESSetOptionsPrefix(taosnes->snes, prefix));
83f4f59681SStefano Zampini   PetscCall(SNESSetSolution(taosnes->snes, tao->solution));
84f4f59681SStefano Zampini   PetscCall(SNESSetObjective(taosnes->snes, TAOSNESObj, tao));
85f4f59681SStefano Zampini   PetscCall(SNESSetFunction(taosnes->snes, NULL, TAOSNESFunc, tao));
864936d809SStefano Zampini   PetscCall(SNESMonitorSet(taosnes->snes, TAOSNESMonitor, tao, NULL));
87f4f59681SStefano Zampini   PetscCall(TaoGetHessian(tao, &A, &P, NULL, NULL));
88f4f59681SStefano Zampini   if (A) PetscCall(SNESSetJacobian(taosnes->snes, A, P, TAOSNESJac, tao));
89f8a48b51SStefano Zampini   if (taosnes->setfromoptionscalled) PetscCall(SNESSetFromOptions(taosnes->snes));
90f8a48b51SStefano Zampini   taosnes->setfromoptionscalled = PETSC_FALSE;
91f4f59681SStefano Zampini   PetscCall(SNESSetUp(taosnes->snes));
92f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
93f4f59681SStefano Zampini }
94f4f59681SStefano Zampini 
TaoSetFromOptions_SNES(Tao tao,PetscOptionItems PetscOptionsObject)95ce78bad3SBarry Smith static PetscErrorCode TaoSetFromOptions_SNES(Tao tao, PetscOptionItems PetscOptionsObject)
96f4f59681SStefano Zampini {
97f4f59681SStefano Zampini   Tao_SNES *taosnes = (Tao_SNES *)tao->data;
98f4f59681SStefano Zampini 
99f4f59681SStefano Zampini   PetscFunctionBegin;
100f8a48b51SStefano Zampini   taosnes->setfromoptionscalled = PETSC_TRUE;
101f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
102f4f59681SStefano Zampini }
103f4f59681SStefano Zampini 
TaoView_SNES(Tao tao,PetscViewer viewer)10466976f2fSJacob Faibussowitsch static PetscErrorCode TaoView_SNES(Tao tao, PetscViewer viewer)
105f4f59681SStefano Zampini {
106f4f59681SStefano Zampini   Tao_SNES *taosnes = (Tao_SNES *)tao->data;
107f4f59681SStefano Zampini 
108f4f59681SStefano Zampini   PetscFunctionBegin;
109f4f59681SStefano Zampini   PetscCall(SNESView(taosnes->snes, viewer));
110f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
111f4f59681SStefano Zampini }
112f4f59681SStefano Zampini 
113f4f59681SStefano Zampini /*MC
114f4f59681SStefano Zampini   TAOSNES - nonlinear solver using SNES
115f4f59681SStefano Zampini 
116f4f59681SStefano Zampini    Level: advanced
117f4f59681SStefano Zampini 
118f4f59681SStefano Zampini .seealso: `TaoCreate()`, `Tao`, `TaoSetType()`, `TaoType`
119f4f59681SStefano Zampini M*/
TaoCreate_SNES(Tao tao)120f4f59681SStefano Zampini PETSC_EXTERN PetscErrorCode TaoCreate_SNES(Tao tao)
121f4f59681SStefano Zampini {
122f4f59681SStefano Zampini   Tao_SNES *taosnes;
123f4f59681SStefano Zampini 
124f4f59681SStefano Zampini   PetscFunctionBegin;
125f4f59681SStefano Zampini   tao->ops->destroy        = TaoDestroy_SNES;
126f4f59681SStefano Zampini   tao->ops->setup          = TaoSetUp_SNES;
127f4f59681SStefano Zampini   tao->ops->setfromoptions = TaoSetFromOptions_SNES;
128f4f59681SStefano Zampini   tao->ops->view           = TaoView_SNES;
129f4f59681SStefano Zampini   tao->ops->solve          = TaoSolve_SNES;
130f4f59681SStefano Zampini 
131606f75f6SBarry Smith   PetscCall(TaoParametersInitialize(tao));
132606f75f6SBarry Smith 
133f4f59681SStefano Zampini   PetscCall(PetscNew(&taosnes));
134f4f59681SStefano Zampini   tao->data = (void *)taosnes;
135f4f59681SStefano Zampini   PetscCall(SNESCreate(PetscObjectComm((PetscObject)tao), &taosnes->snes));
136f4f59681SStefano Zampini   PetscCall(PetscObjectIncrementTabLevel((PetscObject)taosnes->snes, (PetscObject)tao, 1));
137f4f59681SStefano Zampini   PetscFunctionReturn(PETSC_SUCCESS);
138f4f59681SStefano Zampini }
139