xref: /petsc/src/dm/dt/space/interface/space.c (revision 20cf1dd8cd656e27510885a71ea4be028bf48813)
1*20cf1dd8SToby Isaac #include <petsc/private/petscfeimpl.h>     /*I  "petscfe.h"  I*/
2*20cf1dd8SToby Isaac #include <petscdmshell.h>
3*20cf1dd8SToby Isaac 
4*20cf1dd8SToby Isaac PetscClassId PETSCSPACE_CLASSID = 0;
5*20cf1dd8SToby Isaac 
6*20cf1dd8SToby Isaac PetscFunctionList PetscSpaceList              = NULL;
7*20cf1dd8SToby Isaac PetscBool         PetscSpaceRegisterAllCalled = PETSC_FALSE;
8*20cf1dd8SToby Isaac 
9*20cf1dd8SToby Isaac /*@C
10*20cf1dd8SToby Isaac   PetscSpaceRegister - Adds a new PetscSpace implementation
11*20cf1dd8SToby Isaac 
12*20cf1dd8SToby Isaac   Not Collective
13*20cf1dd8SToby Isaac 
14*20cf1dd8SToby Isaac   Input Parameters:
15*20cf1dd8SToby Isaac + name        - The name of a new user-defined creation routine
16*20cf1dd8SToby Isaac - create_func - The creation routine for the implementation type
17*20cf1dd8SToby Isaac 
18*20cf1dd8SToby Isaac   Notes:
19*20cf1dd8SToby Isaac   PetscSpaceRegister() may be called multiple times to add several user-defined types of PetscSpaces.  The creation function is called
20*20cf1dd8SToby Isaac   when the type is set to 'name'.
21*20cf1dd8SToby Isaac 
22*20cf1dd8SToby Isaac   Sample usage:
23*20cf1dd8SToby Isaac .vb
24*20cf1dd8SToby Isaac     PetscSpaceRegister("my_space", MyPetscSpaceCreate);
25*20cf1dd8SToby Isaac .ve
26*20cf1dd8SToby Isaac 
27*20cf1dd8SToby Isaac   Then, your PetscSpace type can be chosen with the procedural interface via
28*20cf1dd8SToby Isaac .vb
29*20cf1dd8SToby Isaac     PetscSpaceCreate(MPI_Comm, PetscSpace *);
30*20cf1dd8SToby Isaac     PetscSpaceSetType(PetscSpace, "my_space");
31*20cf1dd8SToby Isaac .ve
32*20cf1dd8SToby Isaac    or at runtime via the option
33*20cf1dd8SToby Isaac .vb
34*20cf1dd8SToby Isaac     -petscspace_type my_space
35*20cf1dd8SToby Isaac .ve
36*20cf1dd8SToby Isaac 
37*20cf1dd8SToby Isaac   Level: advanced
38*20cf1dd8SToby Isaac 
39*20cf1dd8SToby Isaac .keywords: PetscSpace, register
40*20cf1dd8SToby Isaac .seealso: PetscSpaceRegisterAll(), PetscSpaceRegisterDestroy()
41*20cf1dd8SToby Isaac 
42*20cf1dd8SToby Isaac @*/
43*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceRegister(const char sname[], PetscErrorCode (*function)(PetscSpace))
44*20cf1dd8SToby Isaac {
45*20cf1dd8SToby Isaac   PetscErrorCode ierr;
46*20cf1dd8SToby Isaac 
47*20cf1dd8SToby Isaac   PetscFunctionBegin;
48*20cf1dd8SToby Isaac   ierr = PetscFunctionListAdd(&PetscSpaceList, sname, function);CHKERRQ(ierr);
49*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
50*20cf1dd8SToby Isaac }
51*20cf1dd8SToby Isaac 
52*20cf1dd8SToby Isaac /*@C
53*20cf1dd8SToby Isaac   PetscSpaceSetType - Builds a particular PetscSpace
54*20cf1dd8SToby Isaac 
55*20cf1dd8SToby Isaac   Collective on PetscSpace
56*20cf1dd8SToby Isaac 
57*20cf1dd8SToby Isaac   Input Parameters:
58*20cf1dd8SToby Isaac + sp   - The PetscSpace object
59*20cf1dd8SToby Isaac - name - The kind of space
60*20cf1dd8SToby Isaac 
61*20cf1dd8SToby Isaac   Options Database Key:
62*20cf1dd8SToby Isaac . -petscspace_type <type> - Sets the PetscSpace type; use -help for a list of available types
63*20cf1dd8SToby Isaac 
64*20cf1dd8SToby Isaac   Level: intermediate
65*20cf1dd8SToby Isaac 
66*20cf1dd8SToby Isaac .keywords: PetscSpace, set, type
67*20cf1dd8SToby Isaac .seealso: PetscSpaceGetType(), PetscSpaceCreate()
68*20cf1dd8SToby Isaac @*/
69*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetType(PetscSpace sp, PetscSpaceType name)
70*20cf1dd8SToby Isaac {
71*20cf1dd8SToby Isaac   PetscErrorCode (*r)(PetscSpace);
72*20cf1dd8SToby Isaac   PetscBool      match;
73*20cf1dd8SToby Isaac   PetscErrorCode ierr;
74*20cf1dd8SToby Isaac 
75*20cf1dd8SToby Isaac   PetscFunctionBegin;
76*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
77*20cf1dd8SToby Isaac   ierr = PetscObjectTypeCompare((PetscObject) sp, name, &match);CHKERRQ(ierr);
78*20cf1dd8SToby Isaac   if (match) PetscFunctionReturn(0);
79*20cf1dd8SToby Isaac 
80*20cf1dd8SToby Isaac   ierr = PetscSpaceRegisterAll();CHKERRQ(ierr);
81*20cf1dd8SToby Isaac   ierr = PetscFunctionListFind(PetscSpaceList, name, &r);CHKERRQ(ierr);
82*20cf1dd8SToby Isaac   if (!r) SETERRQ1(PetscObjectComm((PetscObject) sp), PETSC_ERR_ARG_UNKNOWN_TYPE, "Unknown PetscSpace type: %s", name);
83*20cf1dd8SToby Isaac 
84*20cf1dd8SToby Isaac   if (sp->ops->destroy) {
85*20cf1dd8SToby Isaac     ierr             = (*sp->ops->destroy)(sp);CHKERRQ(ierr);
86*20cf1dd8SToby Isaac     sp->ops->destroy = NULL;
87*20cf1dd8SToby Isaac   }
88*20cf1dd8SToby Isaac   ierr = (*r)(sp);CHKERRQ(ierr);
89*20cf1dd8SToby Isaac   ierr = PetscObjectChangeTypeName((PetscObject) sp, name);CHKERRQ(ierr);
90*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
91*20cf1dd8SToby Isaac }
92*20cf1dd8SToby Isaac 
93*20cf1dd8SToby Isaac /*@C
94*20cf1dd8SToby Isaac   PetscSpaceGetType - Gets the PetscSpace type name (as a string) from the object.
95*20cf1dd8SToby Isaac 
96*20cf1dd8SToby Isaac   Not Collective
97*20cf1dd8SToby Isaac 
98*20cf1dd8SToby Isaac   Input Parameter:
99*20cf1dd8SToby Isaac . sp  - The PetscSpace
100*20cf1dd8SToby Isaac 
101*20cf1dd8SToby Isaac   Output Parameter:
102*20cf1dd8SToby Isaac . name - The PetscSpace type name
103*20cf1dd8SToby Isaac 
104*20cf1dd8SToby Isaac   Level: intermediate
105*20cf1dd8SToby Isaac 
106*20cf1dd8SToby Isaac .keywords: PetscSpace, get, type, name
107*20cf1dd8SToby Isaac .seealso: PetscSpaceSetType(), PetscSpaceCreate()
108*20cf1dd8SToby Isaac @*/
109*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetType(PetscSpace sp, PetscSpaceType *name)
110*20cf1dd8SToby Isaac {
111*20cf1dd8SToby Isaac   PetscErrorCode ierr;
112*20cf1dd8SToby Isaac 
113*20cf1dd8SToby Isaac   PetscFunctionBegin;
114*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
115*20cf1dd8SToby Isaac   PetscValidPointer(name, 2);
116*20cf1dd8SToby Isaac   if (!PetscSpaceRegisterAllCalled) {
117*20cf1dd8SToby Isaac     ierr = PetscSpaceRegisterAll();CHKERRQ(ierr);
118*20cf1dd8SToby Isaac   }
119*20cf1dd8SToby Isaac   *name = ((PetscObject) sp)->type_name;
120*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
121*20cf1dd8SToby Isaac }
122*20cf1dd8SToby Isaac 
123*20cf1dd8SToby Isaac /*@C
124*20cf1dd8SToby Isaac   PetscSpaceView - Views a PetscSpace
125*20cf1dd8SToby Isaac 
126*20cf1dd8SToby Isaac   Collective on PetscSpace
127*20cf1dd8SToby Isaac 
128*20cf1dd8SToby Isaac   Input Parameter:
129*20cf1dd8SToby Isaac + sp - the PetscSpace object to view
130*20cf1dd8SToby Isaac - v  - the viewer
131*20cf1dd8SToby Isaac 
132*20cf1dd8SToby Isaac   Level: developer
133*20cf1dd8SToby Isaac 
134*20cf1dd8SToby Isaac .seealso PetscSpaceDestroy()
135*20cf1dd8SToby Isaac @*/
136*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceView(PetscSpace sp, PetscViewer v)
137*20cf1dd8SToby Isaac {
138*20cf1dd8SToby Isaac   PetscBool      iascii;
139*20cf1dd8SToby Isaac   PetscErrorCode ierr;
140*20cf1dd8SToby Isaac 
141*20cf1dd8SToby Isaac   PetscFunctionBegin;
142*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
143*20cf1dd8SToby Isaac   if (v) PetscValidHeaderSpecific(v, PETSC_VIEWER_CLASSID, 2);
144*20cf1dd8SToby Isaac   if (!v) {ierr = PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject) sp), &v);CHKERRQ(ierr);}
145*20cf1dd8SToby Isaac   ierr = PetscObjectTypeCompare((PetscObject) v, PETSCVIEWERASCII, &iascii);CHKERRQ(ierr);
146*20cf1dd8SToby Isaac   if (iascii) {
147*20cf1dd8SToby Isaac     ierr = PetscObjectPrintClassNamePrefixType((PetscObject)sp,v);CHKERRQ(ierr);
148*20cf1dd8SToby Isaac     ierr = PetscViewerASCIIPushTab(v);CHKERRQ(ierr);
149*20cf1dd8SToby Isaac     ierr = PetscViewerASCIIPrintf(v, "Space in %D variables of order %D with %D components\n", sp->Nv, sp->degree, sp->Nc);CHKERRQ(ierr);
150*20cf1dd8SToby Isaac     ierr = PetscViewerASCIIPopTab(v);CHKERRQ(ierr);
151*20cf1dd8SToby Isaac   }
152*20cf1dd8SToby Isaac   ierr = PetscViewerASCIIPushTab(v);CHKERRQ(ierr);
153*20cf1dd8SToby Isaac   if (sp->ops->view) {ierr = (*sp->ops->view)(sp, v);CHKERRQ(ierr);}
154*20cf1dd8SToby Isaac   ierr = PetscViewerASCIIPopTab(v);CHKERRQ(ierr);
155*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
156*20cf1dd8SToby Isaac }
157*20cf1dd8SToby Isaac 
158*20cf1dd8SToby Isaac /*@
159*20cf1dd8SToby Isaac   PetscSpaceSetFromOptions - sets parameters in a PetscSpace from the options database
160*20cf1dd8SToby Isaac 
161*20cf1dd8SToby Isaac   Collective on PetscSpace
162*20cf1dd8SToby Isaac 
163*20cf1dd8SToby Isaac   Input Parameter:
164*20cf1dd8SToby Isaac . sp - the PetscSpace object to set options for
165*20cf1dd8SToby Isaac 
166*20cf1dd8SToby Isaac   Options Database:
167*20cf1dd8SToby Isaac . -petscspace_order the approximation order of the space
168*20cf1dd8SToby Isaac 
169*20cf1dd8SToby Isaac   Level: developer
170*20cf1dd8SToby Isaac 
171*20cf1dd8SToby Isaac .seealso PetscSpaceView()
172*20cf1dd8SToby Isaac @*/
173*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetFromOptions(PetscSpace sp)
174*20cf1dd8SToby Isaac {
175*20cf1dd8SToby Isaac   const char    *defaultType;
176*20cf1dd8SToby Isaac   char           name[256];
177*20cf1dd8SToby Isaac   PetscBool      flg;
178*20cf1dd8SToby Isaac   PetscErrorCode ierr;
179*20cf1dd8SToby Isaac 
180*20cf1dd8SToby Isaac   PetscFunctionBegin;
181*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
182*20cf1dd8SToby Isaac   if (!((PetscObject) sp)->type_name) {
183*20cf1dd8SToby Isaac     defaultType = PETSCSPACEPOLYNOMIAL;
184*20cf1dd8SToby Isaac   } else {
185*20cf1dd8SToby Isaac     defaultType = ((PetscObject) sp)->type_name;
186*20cf1dd8SToby Isaac   }
187*20cf1dd8SToby Isaac   if (!PetscSpaceRegisterAllCalled) {ierr = PetscSpaceRegisterAll();CHKERRQ(ierr);}
188*20cf1dd8SToby Isaac 
189*20cf1dd8SToby Isaac   ierr = PetscObjectOptionsBegin((PetscObject) sp);CHKERRQ(ierr);
190*20cf1dd8SToby Isaac   ierr = PetscOptionsFList("-petscspace_type", "Linear space", "PetscSpaceSetType", PetscSpaceList, defaultType, name, 256, &flg);CHKERRQ(ierr);
191*20cf1dd8SToby Isaac   if (flg) {
192*20cf1dd8SToby Isaac     ierr = PetscSpaceSetType(sp, name);CHKERRQ(ierr);
193*20cf1dd8SToby Isaac   } else if (!((PetscObject) sp)->type_name) {
194*20cf1dd8SToby Isaac     ierr = PetscSpaceSetType(sp, defaultType);CHKERRQ(ierr);
195*20cf1dd8SToby Isaac   }
196*20cf1dd8SToby Isaac   ierr = PetscOptionsInt("-petscspace_order", "The approximation order", "PetscSpaceSetDegree", sp->degree, &sp->degree, NULL);CHKERRQ(ierr);
197*20cf1dd8SToby Isaac   ierr = PetscOptionsInt("-petscspace_variables", "The number of different variables, e.g. x and y", "PetscSpaceSetNumVariables", sp->Nv, &sp->Nv, NULL);CHKERRQ(ierr);
198*20cf1dd8SToby Isaac   ierr = PetscOptionsInt("-petscspace_components", "The number of components", "PetscSpaceSetNumComponents", sp->Nc, &sp->Nc, NULL);CHKERRQ(ierr);
199*20cf1dd8SToby Isaac   if (sp->ops->setfromoptions) {
200*20cf1dd8SToby Isaac     ierr = (*sp->ops->setfromoptions)(PetscOptionsObject,sp);CHKERRQ(ierr);
201*20cf1dd8SToby Isaac   }
202*20cf1dd8SToby Isaac   /* process any options handlers added with PetscObjectAddOptionsHandler() */
203*20cf1dd8SToby Isaac   ierr = PetscObjectProcessOptionsHandlers(PetscOptionsObject,(PetscObject) sp);CHKERRQ(ierr);
204*20cf1dd8SToby Isaac   ierr = PetscOptionsEnd();CHKERRQ(ierr);
205*20cf1dd8SToby Isaac   ierr = PetscSpaceViewFromOptions(sp, NULL, "-petscspace_view");CHKERRQ(ierr);
206*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
207*20cf1dd8SToby Isaac }
208*20cf1dd8SToby Isaac 
209*20cf1dd8SToby Isaac /*@C
210*20cf1dd8SToby Isaac   PetscSpaceSetUp - Construct data structures for the PetscSpace
211*20cf1dd8SToby Isaac 
212*20cf1dd8SToby Isaac   Collective on PetscSpace
213*20cf1dd8SToby Isaac 
214*20cf1dd8SToby Isaac   Input Parameter:
215*20cf1dd8SToby Isaac . sp - the PetscSpace object to setup
216*20cf1dd8SToby Isaac 
217*20cf1dd8SToby Isaac   Level: developer
218*20cf1dd8SToby Isaac 
219*20cf1dd8SToby Isaac .seealso PetscSpaceView(), PetscSpaceDestroy()
220*20cf1dd8SToby Isaac @*/
221*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetUp(PetscSpace sp)
222*20cf1dd8SToby Isaac {
223*20cf1dd8SToby Isaac   PetscErrorCode ierr;
224*20cf1dd8SToby Isaac 
225*20cf1dd8SToby Isaac   PetscFunctionBegin;
226*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
227*20cf1dd8SToby Isaac   if (sp->ops->setup) {ierr = (*sp->ops->setup)(sp);CHKERRQ(ierr);}
228*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
229*20cf1dd8SToby Isaac }
230*20cf1dd8SToby Isaac 
231*20cf1dd8SToby Isaac /*@
232*20cf1dd8SToby Isaac   PetscSpaceDestroy - Destroys a PetscSpace object
233*20cf1dd8SToby Isaac 
234*20cf1dd8SToby Isaac   Collective on PetscSpace
235*20cf1dd8SToby Isaac 
236*20cf1dd8SToby Isaac   Input Parameter:
237*20cf1dd8SToby Isaac . sp - the PetscSpace object to destroy
238*20cf1dd8SToby Isaac 
239*20cf1dd8SToby Isaac   Level: developer
240*20cf1dd8SToby Isaac 
241*20cf1dd8SToby Isaac .seealso PetscSpaceView()
242*20cf1dd8SToby Isaac @*/
243*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceDestroy(PetscSpace *sp)
244*20cf1dd8SToby Isaac {
245*20cf1dd8SToby Isaac   PetscErrorCode ierr;
246*20cf1dd8SToby Isaac 
247*20cf1dd8SToby Isaac   PetscFunctionBegin;
248*20cf1dd8SToby Isaac   if (!*sp) PetscFunctionReturn(0);
249*20cf1dd8SToby Isaac   PetscValidHeaderSpecific((*sp), PETSCSPACE_CLASSID, 1);
250*20cf1dd8SToby Isaac 
251*20cf1dd8SToby Isaac   if (--((PetscObject)(*sp))->refct > 0) {*sp = 0; PetscFunctionReturn(0);}
252*20cf1dd8SToby Isaac   ((PetscObject) (*sp))->refct = 0;
253*20cf1dd8SToby Isaac   ierr = DMDestroy(&(*sp)->dm);CHKERRQ(ierr);
254*20cf1dd8SToby Isaac 
255*20cf1dd8SToby Isaac   ierr = (*(*sp)->ops->destroy)(*sp);CHKERRQ(ierr);
256*20cf1dd8SToby Isaac   ierr = PetscHeaderDestroy(sp);CHKERRQ(ierr);
257*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
258*20cf1dd8SToby Isaac }
259*20cf1dd8SToby Isaac 
260*20cf1dd8SToby Isaac /*@
261*20cf1dd8SToby Isaac   PetscSpaceCreate - Creates an empty PetscSpace object. The type can then be set with PetscSpaceSetType().
262*20cf1dd8SToby Isaac 
263*20cf1dd8SToby Isaac   Collective on MPI_Comm
264*20cf1dd8SToby Isaac 
265*20cf1dd8SToby Isaac   Input Parameter:
266*20cf1dd8SToby Isaac . comm - The communicator for the PetscSpace object
267*20cf1dd8SToby Isaac 
268*20cf1dd8SToby Isaac   Output Parameter:
269*20cf1dd8SToby Isaac . sp - The PetscSpace object
270*20cf1dd8SToby Isaac 
271*20cf1dd8SToby Isaac   Level: beginner
272*20cf1dd8SToby Isaac 
273*20cf1dd8SToby Isaac .seealso: PetscSpaceSetType(), PETSCSPACEPOLYNOMIAL
274*20cf1dd8SToby Isaac @*/
275*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceCreate(MPI_Comm comm, PetscSpace *sp)
276*20cf1dd8SToby Isaac {
277*20cf1dd8SToby Isaac   PetscSpace     s;
278*20cf1dd8SToby Isaac   PetscErrorCode ierr;
279*20cf1dd8SToby Isaac 
280*20cf1dd8SToby Isaac   PetscFunctionBegin;
281*20cf1dd8SToby Isaac   PetscValidPointer(sp, 2);
282*20cf1dd8SToby Isaac   ierr = PetscCitationsRegister(FECitation,&FEcite);CHKERRQ(ierr);
283*20cf1dd8SToby Isaac   *sp  = NULL;
284*20cf1dd8SToby Isaac   ierr = PetscFEInitializePackage();CHKERRQ(ierr);
285*20cf1dd8SToby Isaac 
286*20cf1dd8SToby Isaac   ierr = PetscHeaderCreate(s, PETSCSPACE_CLASSID, "PetscSpace", "Linear Space", "PetscSpace", comm, PetscSpaceDestroy, PetscSpaceView);CHKERRQ(ierr);
287*20cf1dd8SToby Isaac 
288*20cf1dd8SToby Isaac   s->degree = 0;
289*20cf1dd8SToby Isaac   s->Nc     = 1;
290*20cf1dd8SToby Isaac   s->Nv     = 0;
291*20cf1dd8SToby Isaac   ierr = DMShellCreate(comm, &s->dm);CHKERRQ(ierr);
292*20cf1dd8SToby Isaac   ierr = PetscSpaceSetType(s, PETSCSPACEPOLYNOMIAL);CHKERRQ(ierr);
293*20cf1dd8SToby Isaac 
294*20cf1dd8SToby Isaac   *sp = s;
295*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
296*20cf1dd8SToby Isaac }
297*20cf1dd8SToby Isaac 
298*20cf1dd8SToby Isaac /*@
299*20cf1dd8SToby Isaac   PetscSpaceGetDimension - Return the dimension of this space, i.e. the number of basis vectors
300*20cf1dd8SToby Isaac 
301*20cf1dd8SToby Isaac   Input Parameter:
302*20cf1dd8SToby Isaac . sp - The PetscSpace
303*20cf1dd8SToby Isaac 
304*20cf1dd8SToby Isaac   Output Parameter:
305*20cf1dd8SToby Isaac . dim - The dimension
306*20cf1dd8SToby Isaac 
307*20cf1dd8SToby Isaac   Level: intermediate
308*20cf1dd8SToby Isaac 
309*20cf1dd8SToby Isaac .seealso: PetscSpaceGetDegree(), PetscSpaceCreate(), PetscSpace
310*20cf1dd8SToby Isaac @*/
311*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetDimension(PetscSpace sp, PetscInt *dim)
312*20cf1dd8SToby Isaac {
313*20cf1dd8SToby Isaac   PetscErrorCode ierr;
314*20cf1dd8SToby Isaac 
315*20cf1dd8SToby Isaac   PetscFunctionBegin;
316*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
317*20cf1dd8SToby Isaac   PetscValidPointer(dim, 2);
318*20cf1dd8SToby Isaac   *dim = 0;
319*20cf1dd8SToby Isaac   if (sp->ops->getdimension) {ierr = (*sp->ops->getdimension)(sp, dim);CHKERRQ(ierr);}
320*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
321*20cf1dd8SToby Isaac }
322*20cf1dd8SToby Isaac 
323*20cf1dd8SToby Isaac /*@
324*20cf1dd8SToby Isaac   PetscSpaceGetDegree - Return the polynomial degrees that characterize this space
325*20cf1dd8SToby Isaac 
326*20cf1dd8SToby Isaac   Input Parameter:
327*20cf1dd8SToby Isaac . sp - The PetscSpace
328*20cf1dd8SToby Isaac 
329*20cf1dd8SToby Isaac   Output Parameter:
330*20cf1dd8SToby Isaac + minDegree - The degree of the largest polynomial space contained in the space
331*20cf1dd8SToby Isaac - maxDegree - The degree of the smallest polynomial space containing the space
332*20cf1dd8SToby Isaac 
333*20cf1dd8SToby Isaac 
334*20cf1dd8SToby Isaac   Level: intermediate
335*20cf1dd8SToby Isaac 
336*20cf1dd8SToby Isaac .seealso: PetscSpaceSetDegree(), PetscSpaceGetDimension(), PetscSpaceCreate(), PetscSpace
337*20cf1dd8SToby Isaac @*/
338*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetDegree(PetscSpace sp, PetscInt *minDegree, PetscInt *maxDegree)
339*20cf1dd8SToby Isaac {
340*20cf1dd8SToby Isaac   PetscFunctionBegin;
341*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
342*20cf1dd8SToby Isaac   if (minDegree) PetscValidPointer(minDegree, 2);
343*20cf1dd8SToby Isaac   if (maxDegree) PetscValidPointer(minDegree, 3);
344*20cf1dd8SToby Isaac   if (minDegree) *minDegree = sp->degree;
345*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
346*20cf1dd8SToby Isaac }
347*20cf1dd8SToby Isaac 
348*20cf1dd8SToby Isaac /*@
349*20cf1dd8SToby Isaac   PetscSpaceSetDegree - Set the degree of approximation for this space.
350*20cf1dd8SToby Isaac 
351*20cf1dd8SToby Isaac   Input Parameters:
352*20cf1dd8SToby Isaac + sp - The PetscSpace
353*20cf1dd8SToby Isaac - degree - The degree of the largest polynomial space contained in the space
354*20cf1dd8SToby Isaac 
355*20cf1dd8SToby Isaac   Level: intermediate
356*20cf1dd8SToby Isaac 
357*20cf1dd8SToby Isaac .seealso: PetscSpaceGetDegree(), PetscSpaceCreate(), PetscSpace
358*20cf1dd8SToby Isaac @*/
359*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetDegree(PetscSpace sp, PetscInt order)
360*20cf1dd8SToby Isaac {
361*20cf1dd8SToby Isaac   PetscFunctionBegin;
362*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
363*20cf1dd8SToby Isaac   sp->degree = order;
364*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
365*20cf1dd8SToby Isaac }
366*20cf1dd8SToby Isaac 
367*20cf1dd8SToby Isaac /*@
368*20cf1dd8SToby Isaac   PetscSpaceGetNumComponents - Return the number of components for this space
369*20cf1dd8SToby Isaac 
370*20cf1dd8SToby Isaac   Input Parameter:
371*20cf1dd8SToby Isaac . sp - The PetscSpace
372*20cf1dd8SToby Isaac 
373*20cf1dd8SToby Isaac   Output Parameter:
374*20cf1dd8SToby Isaac . Nc - The number of components
375*20cf1dd8SToby Isaac 
376*20cf1dd8SToby Isaac   Note: A vector space, for example, will have d components, where d is the spatial dimension
377*20cf1dd8SToby Isaac 
378*20cf1dd8SToby Isaac   Level: intermediate
379*20cf1dd8SToby Isaac 
380*20cf1dd8SToby Isaac .seealso: PetscSpaceSetNumComponents(), PetscSpaceGetDimension(), PetscSpaceCreate(), PetscSpace
381*20cf1dd8SToby Isaac @*/
382*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetNumComponents(PetscSpace sp, PetscInt *Nc)
383*20cf1dd8SToby Isaac {
384*20cf1dd8SToby Isaac   PetscFunctionBegin;
385*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
386*20cf1dd8SToby Isaac   PetscValidPointer(Nc, 2);
387*20cf1dd8SToby Isaac   *Nc = sp->Nc;
388*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
389*20cf1dd8SToby Isaac }
390*20cf1dd8SToby Isaac 
391*20cf1dd8SToby Isaac /*@
392*20cf1dd8SToby Isaac   PetscSpaceSetNumComponents - Set the number of components for this space
393*20cf1dd8SToby Isaac 
394*20cf1dd8SToby Isaac   Input Parameters:
395*20cf1dd8SToby Isaac + sp - The PetscSpace
396*20cf1dd8SToby Isaac - order - The number of components
397*20cf1dd8SToby Isaac 
398*20cf1dd8SToby Isaac   Level: intermediate
399*20cf1dd8SToby Isaac 
400*20cf1dd8SToby Isaac .seealso: PetscSpaceGetNumComponents(), PetscSpaceCreate(), PetscSpace
401*20cf1dd8SToby Isaac @*/
402*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetNumComponents(PetscSpace sp, PetscInt Nc)
403*20cf1dd8SToby Isaac {
404*20cf1dd8SToby Isaac   PetscFunctionBegin;
405*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
406*20cf1dd8SToby Isaac   sp->Nc = Nc;
407*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
408*20cf1dd8SToby Isaac }
409*20cf1dd8SToby Isaac 
410*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceSetNumVariables(PetscSpace sp, PetscInt n)
411*20cf1dd8SToby Isaac {
412*20cf1dd8SToby Isaac   PetscFunctionBegin;
413*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
414*20cf1dd8SToby Isaac   sp->Nv = n;
415*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
416*20cf1dd8SToby Isaac }
417*20cf1dd8SToby Isaac 
418*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetNumVariables(PetscSpace sp, PetscInt *n)
419*20cf1dd8SToby Isaac {
420*20cf1dd8SToby Isaac   PetscFunctionBegin;
421*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
422*20cf1dd8SToby Isaac   PetscValidPointer(n, 2);
423*20cf1dd8SToby Isaac   *n = sp->Nv;
424*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
425*20cf1dd8SToby Isaac }
426*20cf1dd8SToby Isaac 
427*20cf1dd8SToby Isaac 
428*20cf1dd8SToby Isaac /*@C
429*20cf1dd8SToby Isaac   PetscSpaceEvaluate - Evaluate the basis functions and their derivatives (jet) at each point
430*20cf1dd8SToby Isaac 
431*20cf1dd8SToby Isaac   Input Parameters:
432*20cf1dd8SToby Isaac + sp      - The PetscSpace
433*20cf1dd8SToby Isaac . npoints - The number of evaluation points, in reference coordinates
434*20cf1dd8SToby Isaac - points  - The point coordinates
435*20cf1dd8SToby Isaac 
436*20cf1dd8SToby Isaac   Output Parameters:
437*20cf1dd8SToby Isaac + B - The function evaluations in a npoints x nfuncs array
438*20cf1dd8SToby Isaac . D - The derivative evaluations in a npoints x nfuncs x dim array
439*20cf1dd8SToby Isaac - H - The second derivative evaluations in a npoints x nfuncs x dim x dim array
440*20cf1dd8SToby Isaac 
441*20cf1dd8SToby Isaac   Note: Above nfuncs is the dimension of the space, and dim is the spatial dimension. The coordinates are given
442*20cf1dd8SToby Isaac   on the reference cell, not in real space.
443*20cf1dd8SToby Isaac 
444*20cf1dd8SToby Isaac   Level: advanced
445*20cf1dd8SToby Isaac 
446*20cf1dd8SToby Isaac .seealso: PetscFEGetTabulation(), PetscFEGetDefaultTabulation(), PetscSpaceCreate()
447*20cf1dd8SToby Isaac @*/
448*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceEvaluate(PetscSpace sp, PetscInt npoints, const PetscReal points[], PetscReal B[], PetscReal D[], PetscReal H[])
449*20cf1dd8SToby Isaac {
450*20cf1dd8SToby Isaac   PetscErrorCode ierr;
451*20cf1dd8SToby Isaac 
452*20cf1dd8SToby Isaac   PetscFunctionBegin;
453*20cf1dd8SToby Isaac   if (!npoints) PetscFunctionReturn(0);
454*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
455*20cf1dd8SToby Isaac   if (sp->Nv) PetscValidPointer(points, 3);
456*20cf1dd8SToby Isaac   if (B) PetscValidPointer(B, 4);
457*20cf1dd8SToby Isaac   if (D) PetscValidPointer(D, 5);
458*20cf1dd8SToby Isaac   if (H) PetscValidPointer(H, 6);
459*20cf1dd8SToby Isaac   if (sp->ops->evaluate) {ierr = (*sp->ops->evaluate)(sp, npoints, points, B, D, H);CHKERRQ(ierr);}
460*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
461*20cf1dd8SToby Isaac }
462*20cf1dd8SToby Isaac 
463*20cf1dd8SToby Isaac /*@
464*20cf1dd8SToby Isaac   PetscSpaceGetHeightSubspace - Get the subset of the primal space basis that is supported on a mesh point of a given height.
465*20cf1dd8SToby Isaac 
466*20cf1dd8SToby Isaac   If the space is not defined on mesh points of the given height (e.g. if the space is discontinuous and
467*20cf1dd8SToby Isaac   pointwise values are not defined on the element boundaries), or if the implementation of PetscSpace does not
468*20cf1dd8SToby Isaac   support extracting subspaces, then NULL is returned.
469*20cf1dd8SToby Isaac 
470*20cf1dd8SToby Isaac   This does not increment the reference count on the returned space, and the user should not destroy it.
471*20cf1dd8SToby Isaac 
472*20cf1dd8SToby Isaac   Not collective
473*20cf1dd8SToby Isaac 
474*20cf1dd8SToby Isaac   Input Parameters:
475*20cf1dd8SToby Isaac + sp - the PetscSpace object
476*20cf1dd8SToby Isaac - height - the height of the mesh point for which the subspace is desired
477*20cf1dd8SToby Isaac 
478*20cf1dd8SToby Isaac   Output Parameter:
479*20cf1dd8SToby Isaac . subsp - the subspace
480*20cf1dd8SToby Isaac 
481*20cf1dd8SToby Isaac   Level: advanced
482*20cf1dd8SToby Isaac 
483*20cf1dd8SToby Isaac .seealso: PetscDualSpaceGetHeightSubspace(), PetscSpace
484*20cf1dd8SToby Isaac @*/
485*20cf1dd8SToby Isaac PetscErrorCode PetscSpaceGetHeightSubspace(PetscSpace sp, PetscInt height, PetscSpace *subsp)
486*20cf1dd8SToby Isaac {
487*20cf1dd8SToby Isaac   PetscErrorCode ierr;
488*20cf1dd8SToby Isaac 
489*20cf1dd8SToby Isaac   PetscFunctionBegin;
490*20cf1dd8SToby Isaac   PetscValidHeaderSpecific(sp, PETSCSPACE_CLASSID, 1);
491*20cf1dd8SToby Isaac   PetscValidPointer(subsp, 3);
492*20cf1dd8SToby Isaac   *subsp = NULL;
493*20cf1dd8SToby Isaac   if (sp->ops->getheightsubspace) {
494*20cf1dd8SToby Isaac     ierr = (*sp->ops->getheightsubspace)(sp, height, subsp);CHKERRQ(ierr);
495*20cf1dd8SToby Isaac   }
496*20cf1dd8SToby Isaac   PetscFunctionReturn(0);
497*20cf1dd8SToby Isaac }
498*20cf1dd8SToby Isaac 
499