Actual source code: pcset.c


  2: /*
  3:     Routines to set PC methods and options.
  4: */

  6: #include <petsc/private/pcimpl.h>
  7: #include <petscdm.h>

  9: PetscBool PCRegisterAllCalled = PETSC_FALSE;
 10: /*
 11:    Contains the list of registered PC routines
 12: */
 13: PetscFunctionList PCList = NULL;

 15: /*@C
 16:    PCSetType - Builds PC for a particular preconditioner type

 18:    Collective

 20:    Input Parameters:
 21: +  pc - the preconditioner context.
 22: -  type - a known method

 24:    Options Database Key:
 25: .  -pc_type <type> - Sets PC type

 27:    Use -help for a list of available methods (for instance,
 28:    jacobi or bjacobi)

 30:   Notes:
 31:   See "petsc/include/petscpc.h" for available methods (for instance,
 32:   PCJACOBI, PCILU, or PCBJACOBI).

 34:   Normally, it is best to use the KSPSetFromOptions() command and
 35:   then set the PC type from the options database rather than by using
 36:   this routine.  Using the options database provides the user with
 37:   maximum flexibility in evaluating the many different preconditioners.
 38:   The PCSetType() routine is provided for those situations where it
 39:   is necessary to set the preconditioner independently of the command
 40:   line or options database.  This might be the case, for example, when
 41:   the choice of preconditioner changes during the execution of the
 42:   program, and the user's application is taking responsibility for
 43:   choosing the appropriate preconditioner.  In other words, this
 44:   routine is not for beginners.

 46:   Level: intermediate

 48:   Developer Note: PCRegister() is used to add preconditioner types to PCList from which they
 49:   are accessed by PCSetType().

 51: .seealso: `KSPSetType()`, `PCType`, `PCRegister()`, `PCCreate()`, `KSPGetPC()`

 53: @*/
 54: PetscErrorCode PCSetType(PC pc, PCType type)
 55: {
 56:   PetscBool match;
 57:   PetscErrorCode (*r)(PC);


 62:   PetscObjectTypeCompare((PetscObject)pc, type, &match);
 63:   if (match) return 0;

 65:   PetscFunctionListFind(PCList, type, &r);
 67:   /* Destroy the previous private PC context */
 68:   PetscTryTypeMethod(pc, destroy);
 69:   pc->ops->destroy = NULL;
 70:   pc->data         = NULL;

 72:   PetscFunctionListDestroy(&((PetscObject)pc)->qlist);
 73:   /* Reinitialize function pointers in PCOps structure */
 74:   PetscMemzero(pc->ops, sizeof(struct _PCOps));
 75:   /* XXX Is this OK?? */
 76:   pc->modifysubmatrices  = NULL;
 77:   pc->modifysubmatricesP = NULL;
 78:   /* Call the PCCreate_XXX routine for this particular preconditioner */
 79:   pc->setupcalled = 0;

 81:   PetscObjectChangeTypeName((PetscObject)pc, type);
 82:   (*r)(pc);
 83:   return 0;
 84: }

 86: /*@C
 87:    PCGetType - Gets the PC method type and name (as a string) from the PC
 88:    context.

 90:    Not Collective

 92:    Input Parameter:
 93: .  pc - the preconditioner context

 95:    Output Parameter:
 96: .  type - name of preconditioner method

 98:    Level: intermediate

100: .seealso: `PCSetType()`

102: @*/
103: PetscErrorCode PCGetType(PC pc, PCType *type)
104: {
107:   *type = ((PetscObject)pc)->type_name;
108:   return 0;
109: }

111: extern PetscErrorCode PCGetDefaultType_Private(PC, const char *[]);

113: /*@
114:    PCSetFromOptions - Sets PC options from the options database.
115:    This routine must be called before PCSetUp() if the user is to be
116:    allowed to set the preconditioner method.

118:    Collective

120:    Input Parameter:
121: .  pc - the preconditioner context

123:    Options Database Key:
124: .   -pc_use_amat true,false - see PCSetUseAmat()

126:    Level: developer

128: .seealso: `PCSetUseAmat()`

130: @*/
131: PetscErrorCode PCSetFromOptions(PC pc)
132: {
133:   char        type[256];
134:   const char *def;
135:   PetscBool   flg;


139:   PCRegisterAll();
140:   PetscObjectOptionsBegin((PetscObject)pc);
141:   if (!((PetscObject)pc)->type_name) {
142:     PCGetDefaultType_Private(pc, &def);
143:   } else {
144:     def = ((PetscObject)pc)->type_name;
145:   }

147:   PetscOptionsFList("-pc_type", "Preconditioner", "PCSetType", PCList, def, type, 256, &flg);
148:   if (flg) {
149:     PCSetType(pc, type);
150:   } else if (!((PetscObject)pc)->type_name) {
151:     PCSetType(pc, def);
152:   }

154:   PetscObjectTypeCompare((PetscObject)pc, PCNONE, &flg);
155:   if (flg) goto skipoptions;

157:   PetscOptionsBool("-pc_use_amat", "use Amat (instead of Pmat) to define preconditioner in nested inner solves", "PCSetUseAmat", pc->useAmat, &pc->useAmat, NULL);

159:   PetscTryTypeMethod(pc, setfromoptions, PetscOptionsObject);

161: skipoptions:
162:   /* process any options handlers added with PetscObjectAddOptionsHandler() */
163:   PetscObjectProcessOptionsHandlers((PetscObject)pc, PetscOptionsObject);
164:   PetscOptionsEnd();
165:   pc->setfromoptionscalled++;
166:   return 0;
167: }

169: /*@
170:    PCSetDM - Sets the DM that may be used by some preconditioners

172:    Logically Collective

174:    Input Parameters:
175: +  pc - the preconditioner context
176: -  dm - the dm, can be NULL

178:    Level: intermediate

180:    Developer Note:
181:     The routines KSP/SNES/TSSetDM() require the dm to be non-NULL, but this one can be NULL since all it does is
182:     replace the current DM

184: .seealso: `PCGetDM()`, `KSPSetDM()`, `KSPGetDM()`
185: @*/
186: PetscErrorCode PCSetDM(PC pc, DM dm)
187: {
189:   if (dm) PetscObjectReference((PetscObject)dm);
190:   DMDestroy(&pc->dm);
191:   pc->dm = dm;
192:   return 0;
193: }

195: /*@
196:    PCGetDM - Gets the DM that may be used by some preconditioners

198:    Not Collective

200:    Input Parameter:
201: . pc - the preconditioner context

203:    Output Parameter:
204: .  dm - the dm

206:    Level: intermediate

208: .seealso: `PCSetDM()`, `KSPSetDM()`, `KSPGetDM()`
209: @*/
210: PetscErrorCode PCGetDM(PC pc, DM *dm)
211: {
213:   *dm = pc->dm;
214:   return 0;
215: }

217: /*@
218:    PCSetApplicationContext - Sets the optional user-defined context for the linear solver.

220:    Logically Collective

222:    Input Parameters:
223: +  pc - the PC context
224: -  usrP - optional user context

226:    Level: intermediate

228: .seealso: `PCGetApplicationContext()`
229: @*/
230: PetscErrorCode PCSetApplicationContext(PC pc, void *usrP)
231: {
233:   pc->user = usrP;
234:   return 0;
235: }

237: /*@
238:    PCGetApplicationContext - Gets the user-defined context for the linear solver.

240:    Not Collective

242:    Input Parameter:
243: .  pc - PC context

245:    Output Parameter:
246: .  usrP - user context

248:    Level: intermediate

250: .seealso: `PCSetApplicationContext()`
251: @*/
252: PetscErrorCode PCGetApplicationContext(PC pc, void *usrP)
253: {
255:   *(void **)usrP = pc->user;
256:   return 0;
257: }