1a7b5fb5fSBarry Smith #include <../src/snes/impls/fas/fasimpls.h> /*I "petscsnes.h" I*/ 2ab8d36c9SPeter Brune 3ab8d36c9SPeter Brune /*@ 4ab8d36c9SPeter Brune SNESFASGetGalerkin - Gets if the coarse problems are formed by projection to the fine problem 5ab8d36c9SPeter Brune 6*20f4b53cSBarry Smith Not Collective but the result would be the same on all MPI ranks 7f6dfbefdSBarry Smith 8ab8d36c9SPeter Brune Input Parameter: 9f6dfbefdSBarry Smith . snes - the `SNESFAS` nonlinear solver context 10ab8d36c9SPeter Brune 11ab8d36c9SPeter Brune Output parameter: 12f6dfbefdSBarry Smith . flg - `PETSC_TRUE` if the coarse problem is formed by projection 13ab8d36c9SPeter Brune 14ab8d36c9SPeter Brune Level: advanced 15ab8d36c9SPeter Brune 16f6dfbefdSBarry Smith .seealso: `SNESFAS`, `SNESFASSetLevels()`, `SNESFASSetGalerkin()` 17ab8d36c9SPeter Brune @*/ 18d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESFASGetGalerkin(SNES snes, PetscBool *flg) 19d71ae5a4SJacob Faibussowitsch { 20f833ba53SLisandro Dalcin SNES_FAS *fas; 215fd66863SKarl Rupp 22ab8d36c9SPeter Brune PetscFunctionBegin; 23f833ba53SLisandro Dalcin PetscValidHeaderSpecificType(snes, SNES_CLASSID, 1, SNESFAS); 24f833ba53SLisandro Dalcin fas = (SNES_FAS *)snes->data; 25ab8d36c9SPeter Brune *flg = fas->galerkin; 263ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 27ab8d36c9SPeter Brune } 28ab8d36c9SPeter Brune 29ab8d36c9SPeter Brune /*@ 30ab8d36c9SPeter Brune SNESFASSetGalerkin - Sets coarse problems as formed by projection to the fine problem 31ab8d36c9SPeter Brune 32c3339decSBarry Smith Collective 33f6dfbefdSBarry Smith 34d8d19677SJose E. Roman Input Parameters: 35f6dfbefdSBarry Smith + snes - the `SNESFAS` nonlinear solver context 36f6dfbefdSBarry Smith - flg - `PETSC_TRUE` to use the projection process 37ab8d36c9SPeter Brune 38ab8d36c9SPeter Brune Level: advanced 39ab8d36c9SPeter Brune 40f6dfbefdSBarry Smith .seealso: `SNESFAS`, `SNESFASSetLevels()`, `SNESFASGetGalerkin()` 41ab8d36c9SPeter Brune @*/ 42d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESFASSetGalerkin(SNES snes, PetscBool flg) 43d71ae5a4SJacob Faibussowitsch { 44f833ba53SLisandro Dalcin SNES_FAS *fas; 455fd66863SKarl Rupp 46ab8d36c9SPeter Brune PetscFunctionBegin; 47f833ba53SLisandro Dalcin PetscValidHeaderSpecificType(snes, SNES_CLASSID, 1, SNESFAS); 48f833ba53SLisandro Dalcin fas = (SNES_FAS *)snes->data; 49ab8d36c9SPeter Brune fas->galerkin = flg; 509566063dSJacob Faibussowitsch if (fas->next) PetscCall(SNESFASSetGalerkin(fas->next, flg)); 513ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 52ab8d36c9SPeter Brune } 536273346dSPeter Brune 5425acbd8eSLisandro Dalcin /*@C 5525acbd8eSLisandro Dalcin SNESFASGalerkinFunctionDefault - Computes the Galerkin FAS function 566273346dSPeter Brune 57c3339decSBarry Smith Collective 58f6dfbefdSBarry Smith 5925acbd8eSLisandro Dalcin Input Parameters: 60f6dfbefdSBarry Smith + snes - the `SNESFAS` nonlinear solver context 6125acbd8eSLisandro Dalcin . X - input vector 62f6dfbefdSBarry Smith - ctx - the application context 6325acbd8eSLisandro Dalcin 6425acbd8eSLisandro Dalcin Output Parameter: 6525acbd8eSLisandro Dalcin . F - output vector 6625acbd8eSLisandro Dalcin 67*20f4b53cSBarry Smith Level: developer 68*20f4b53cSBarry Smith 69f6dfbefdSBarry Smith Note: 70da81f932SPierre Jolivet The Galerkin FAS function evaluation is defined as 7125acbd8eSLisandro Dalcin $ F^l(x^l) = I^l_0 F^0(P^0_l x^l) 7225acbd8eSLisandro Dalcin 73f6dfbefdSBarry Smith .seealso: `SNESFAS`, `SNESFASGetGalerkin()`, `SNESFASSetGalerkin()` 7425acbd8eSLisandro Dalcin @*/ 75d71ae5a4SJacob Faibussowitsch PetscErrorCode SNESFASGalerkinFunctionDefault(SNES snes, Vec X, Vec F, void *ctx) 76d71ae5a4SJacob Faibussowitsch { 776273346dSPeter Brune SNES fassnes; 786273346dSPeter Brune SNES_FAS *fas; 796273346dSPeter Brune SNES_FAS *prevfas; 806273346dSPeter Brune SNES prevsnes; 8175d4ebe3SPeter Brune Vec b_temp; 820adebc6cSBarry Smith 836273346dSPeter Brune PetscFunctionBegin; 846273346dSPeter Brune /* prolong to the fine level and evaluate there. */ 856273346dSPeter Brune fassnes = (SNES)ctx; 866273346dSPeter Brune fas = (SNES_FAS *)fassnes->data; 876273346dSPeter Brune prevsnes = fas->previous; 886273346dSPeter Brune prevfas = (SNES_FAS *)prevsnes->data; 896273346dSPeter Brune /* interpolate down the solution */ 909566063dSJacob Faibussowitsch PetscCall(MatInterpolate(prevfas->interpolate, X, prevfas->Xg)); 9175d4ebe3SPeter Brune /* the RHS we care about is at the coarsest level */ 9275d4ebe3SPeter Brune b_temp = prevsnes->vec_rhs; 930298fd71SBarry Smith prevsnes->vec_rhs = NULL; 949566063dSJacob Faibussowitsch PetscCall(SNESComputeFunction(prevsnes, prevfas->Xg, prevfas->Fg)); 9575d4ebe3SPeter Brune prevsnes->vec_rhs = b_temp; 966273346dSPeter Brune /* restrict up the function */ 979566063dSJacob Faibussowitsch PetscCall(MatRestrict(prevfas->restrct, prevfas->Fg, F)); 983ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 996273346dSPeter Brune } 100