xref: /petsc/src/dm/dt/fe/interface/fegeom.c (revision f4f49eeac7efa77fffa46b7ff95a3ed169f659ed)
120cf1dd8SToby Isaac #include <petsc/private/petscfeimpl.h> /*I "petscfe.h" I*/
220cf1dd8SToby Isaac 
32b99622eSMatthew G. Knepley /*@C
4dce8aebaSBarry Smith   PetscFEGeomCreate - Create a `PetscFEGeom` object to manage geometry for a group of cells
52b99622eSMatthew G. Knepley 
62b99622eSMatthew G. Knepley   Input Parameters:
7dce8aebaSBarry Smith + quad     - A `PetscQuadrature` determining the tabulation
82b99622eSMatthew G. Knepley . numCells - The number of cells in the group
92b99622eSMatthew G. Knepley . dimEmbed - The coordinate dimension
102b99622eSMatthew G. Knepley - faceData - Flag to construct geometry data for the faces
112b99622eSMatthew G. Knepley 
122b99622eSMatthew G. Knepley   Output Parameter:
13dce8aebaSBarry Smith . geom - The `PetscFEGeom` object
142b99622eSMatthew G. Knepley 
152b99622eSMatthew G. Knepley   Level: beginner
162b99622eSMatthew G. Knepley 
1760225df5SJacob Faibussowitsch .seealso: `PetscFEGeom`, `PetscQuadrature`, `PetscFEGeomDestroy()`, `PetscFEGeomComplete()`
182b99622eSMatthew G. Knepley @*/
19d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomCreate(PetscQuadrature quad, PetscInt numCells, PetscInt dimEmbed, PetscBool faceData, PetscFEGeom **geom)
20d71ae5a4SJacob Faibussowitsch {
2120cf1dd8SToby Isaac   PetscFEGeom     *g;
227489efa5SMatthew G. Knepley   PetscInt         dim, Nq, N;
2320cf1dd8SToby Isaac   const PetscReal *p;
2420cf1dd8SToby Isaac 
2520cf1dd8SToby Isaac   PetscFunctionBegin;
269566063dSJacob Faibussowitsch   PetscCall(PetscQuadratureGetData(quad, &dim, NULL, &Nq, &p, NULL));
279566063dSJacob Faibussowitsch   PetscCall(PetscNew(&g));
2820cf1dd8SToby Isaac   g->xi         = p;
2920cf1dd8SToby Isaac   g->numCells   = numCells;
307489efa5SMatthew G. Knepley   g->numPoints  = Nq;
3120cf1dd8SToby Isaac   g->dim        = dim;
3220cf1dd8SToby Isaac   g->dimEmbed   = dimEmbed;
335fedec97SMatthew G. Knepley   g->isCohesive = PETSC_FALSE;
347489efa5SMatthew G. Knepley   N             = numCells * Nq;
359566063dSJacob Faibussowitsch   PetscCall(PetscCalloc3(N * dimEmbed, &g->v, N * dimEmbed * dimEmbed, &g->J, N, &g->detJ));
3620cf1dd8SToby Isaac   if (faceData) {
379566063dSJacob Faibussowitsch     PetscCall(PetscCalloc2(numCells, &g->face, N * dimEmbed, &g->n));
38*f4f49eeaSPierre Jolivet     PetscCall(PetscCalloc6(N * dimEmbed * dimEmbed, &g->suppJ[0], N * dimEmbed * dimEmbed, &g->suppJ[1], N * dimEmbed * dimEmbed, &g->suppInvJ[0], N * dimEmbed * dimEmbed, &g->suppInvJ[1], N, &g->suppDetJ[0], N, &g->suppDetJ[1]));
3920cf1dd8SToby Isaac   }
409566063dSJacob Faibussowitsch   PetscCall(PetscCalloc1(N * dimEmbed * dimEmbed, &g->invJ));
4120cf1dd8SToby Isaac   *geom = g;
423ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
4320cf1dd8SToby Isaac }
4420cf1dd8SToby Isaac 
452b99622eSMatthew G. Knepley /*@C
46dce8aebaSBarry Smith   PetscFEGeomDestroy - Destroy a `PetscFEGeom` object
472b99622eSMatthew G. Knepley 
482b99622eSMatthew G. Knepley   Input Parameter:
49dce8aebaSBarry Smith . geom - `PetscFEGeom` object
502b99622eSMatthew G. Knepley 
512b99622eSMatthew G. Knepley   Level: beginner
522b99622eSMatthew G. Knepley 
53dce8aebaSBarry Smith .seealso: `PetscFEGeom`, `PetscFEGeomCreate()`
542b99622eSMatthew G. Knepley @*/
55d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomDestroy(PetscFEGeom **geom)
56d71ae5a4SJacob Faibussowitsch {
5720cf1dd8SToby Isaac   PetscFunctionBegin;
583ba16761SJacob Faibussowitsch   if (!*geom) PetscFunctionReturn(PETSC_SUCCESS);
599566063dSJacob Faibussowitsch   PetscCall(PetscFree3((*geom)->v, (*geom)->J, (*geom)->detJ));
609566063dSJacob Faibussowitsch   PetscCall(PetscFree((*geom)->invJ));
619566063dSJacob Faibussowitsch   PetscCall(PetscFree2((*geom)->face, (*geom)->n));
629566063dSJacob Faibussowitsch   PetscCall(PetscFree6((*geom)->suppJ[0], (*geom)->suppJ[1], (*geom)->suppInvJ[0], (*geom)->suppInvJ[1], (*geom)->suppDetJ[0], (*geom)->suppDetJ[1]));
639566063dSJacob Faibussowitsch   PetscCall(PetscFree(*geom));
643ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
6520cf1dd8SToby Isaac }
6620cf1dd8SToby Isaac 
672b99622eSMatthew G. Knepley /*@C
68dce8aebaSBarry Smith   PetscFEGeomGetChunk - Get a chunk of cells in the group as a `PetscFEGeom`
692b99622eSMatthew G. Knepley 
702b99622eSMatthew G. Knepley   Input Parameters:
71dce8aebaSBarry Smith + geom   - `PetscFEGeom` object
722b99622eSMatthew G. Knepley . cStart - The first cell in the chunk
732b99622eSMatthew G. Knepley - cEnd   - The first cell not in the chunk
742b99622eSMatthew G. Knepley 
752b99622eSMatthew G. Knepley   Output Parameter:
762b99622eSMatthew G. Knepley . chunkGeom - The chunk of cells
772b99622eSMatthew G. Knepley 
782b99622eSMatthew G. Knepley   Level: intermediate
792b99622eSMatthew G. Knepley 
80dce8aebaSBarry Smith   Note:
81dce8aebaSBarry Smith   Use `PetscFEGeomRestoreChunk()` to return the result
82dce8aebaSBarry Smith 
83dce8aebaSBarry Smith .seealso: `PetscFEGeom`, `PetscFEGeomRestoreChunk()`, `PetscFEGeomCreate()`
842b99622eSMatthew G. Knepley @*/
85d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomGetChunk(PetscFEGeom *geom, PetscInt cStart, PetscInt cEnd, PetscFEGeom **chunkGeom)
86d71ae5a4SJacob Faibussowitsch {
8720cf1dd8SToby Isaac   PetscInt Nq;
8820cf1dd8SToby Isaac   PetscInt dE;
8920cf1dd8SToby Isaac 
9020cf1dd8SToby Isaac   PetscFunctionBegin;
914f572ea9SToby Isaac   PetscAssertPointer(geom, 1);
924f572ea9SToby Isaac   PetscAssertPointer(chunkGeom, 4);
9348a46eb9SPierre Jolivet   if (!(*chunkGeom)) PetscCall(PetscNew(chunkGeom));
9420cf1dd8SToby Isaac   Nq                        = geom->numPoints;
9520cf1dd8SToby Isaac   dE                        = geom->dimEmbed;
9620cf1dd8SToby Isaac   (*chunkGeom)->dim         = geom->dim;
9720cf1dd8SToby Isaac   (*chunkGeom)->dimEmbed    = geom->dimEmbed;
9820cf1dd8SToby Isaac   (*chunkGeom)->numPoints   = geom->numPoints;
9920cf1dd8SToby Isaac   (*chunkGeom)->numCells    = cEnd - cStart;
10020cf1dd8SToby Isaac   (*chunkGeom)->xi          = geom->xi;
1018e3a54c0SPierre Jolivet   (*chunkGeom)->v           = PetscSafePointerPlusOffset(geom->v, Nq * dE * cStart);
1028e3a54c0SPierre Jolivet   (*chunkGeom)->J           = PetscSafePointerPlusOffset(geom->J, Nq * dE * dE * cStart);
1038e3a54c0SPierre Jolivet   (*chunkGeom)->invJ        = PetscSafePointerPlusOffset(geom->invJ, Nq * dE * dE * cStart);
1048e3a54c0SPierre Jolivet   (*chunkGeom)->detJ        = PetscSafePointerPlusOffset(geom->detJ, Nq * cStart);
1058e3a54c0SPierre Jolivet   (*chunkGeom)->n           = PetscSafePointerPlusOffset(geom->n, Nq * dE * cStart);
1068e3a54c0SPierre Jolivet   (*chunkGeom)->face        = PetscSafePointerPlusOffset(geom->face, cStart);
1078e3a54c0SPierre Jolivet   (*chunkGeom)->suppJ[0]    = PetscSafePointerPlusOffset(geom->suppJ[0], Nq * dE * dE * cStart);
1088e3a54c0SPierre Jolivet   (*chunkGeom)->suppJ[1]    = PetscSafePointerPlusOffset(geom->suppJ[1], Nq * dE * dE * cStart);
1098e3a54c0SPierre Jolivet   (*chunkGeom)->suppInvJ[0] = PetscSafePointerPlusOffset(geom->suppInvJ[0], Nq * dE * dE * cStart);
1108e3a54c0SPierre Jolivet   (*chunkGeom)->suppInvJ[1] = PetscSafePointerPlusOffset(geom->suppInvJ[1], Nq * dE * dE * cStart);
1118e3a54c0SPierre Jolivet   (*chunkGeom)->suppDetJ[0] = PetscSafePointerPlusOffset(geom->suppDetJ[0], Nq * cStart);
1128e3a54c0SPierre Jolivet   (*chunkGeom)->suppDetJ[1] = PetscSafePointerPlusOffset(geom->suppDetJ[1], Nq * cStart);
11320cf1dd8SToby Isaac   (*chunkGeom)->isAffine    = geom->isAffine;
1143ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
11520cf1dd8SToby Isaac }
11620cf1dd8SToby Isaac 
1172b99622eSMatthew G. Knepley /*@C
118dce8aebaSBarry Smith   PetscFEGeomRestoreChunk - Restore the chunk obtained with `PetscFEGeomCreateChunk()`
1192b99622eSMatthew G. Knepley 
1202b99622eSMatthew G. Knepley   Input Parameters:
121dce8aebaSBarry Smith + geom      - `PetscFEGeom` object
1222b99622eSMatthew G. Knepley . cStart    - The first cell in the chunk
1232b99622eSMatthew G. Knepley . cEnd      - The first cell not in the chunk
1242b99622eSMatthew G. Knepley - chunkGeom - The chunk of cells
1252b99622eSMatthew G. Knepley 
1262b99622eSMatthew G. Knepley   Level: intermediate
1272b99622eSMatthew G. Knepley 
128dce8aebaSBarry Smith .seealso: `PetscFEGeom`, `PetscFEGeomGetChunk()`, `PetscFEGeomCreate()`
1292b99622eSMatthew G. Knepley @*/
130d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomRestoreChunk(PetscFEGeom *geom, PetscInt cStart, PetscInt cEnd, PetscFEGeom **chunkGeom)
131d71ae5a4SJacob Faibussowitsch {
13220cf1dd8SToby Isaac   PetscFunctionBegin;
1339566063dSJacob Faibussowitsch   PetscCall(PetscFree(*chunkGeom));
1343ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
13520cf1dd8SToby Isaac }
13620cf1dd8SToby Isaac 
1376587ee25SMatthew G. Knepley /*@C
138dce8aebaSBarry Smith   PetscFEGeomGetPoint - Get the geometry for cell c at point p as a `PetscFEGeom`
1396587ee25SMatthew G. Knepley 
1406587ee25SMatthew G. Knepley   Input Parameters:
141dce8aebaSBarry Smith + geom    - `PetscFEGeom` object
1426587ee25SMatthew G. Knepley . c       - The cell
1436587ee25SMatthew G. Knepley . p       - The point
1446587ee25SMatthew G. Knepley - pcoords - The reference coordinates of point p, or NULL
1456587ee25SMatthew G. Knepley 
1466587ee25SMatthew G. Knepley   Output Parameter:
1476587ee25SMatthew G. Knepley . pgeom - The geometry of cell c at point p
1486587ee25SMatthew G. Knepley 
149dce8aebaSBarry Smith   Level: intermediate
150dce8aebaSBarry Smith 
151dce8aebaSBarry Smith   Notes:
152dce8aebaSBarry Smith   For affine geometries, this only copies to pgeom at point 0. Since we copy pointers into pgeom,
1536587ee25SMatthew G. Knepley   nothing needs to be done with it afterwards.
1546587ee25SMatthew G. Knepley 
1556587ee25SMatthew G. Knepley   In the affine case, pgeom must have storage for the integration point coordinates in pgeom->v if pcoords is passed in.
1566587ee25SMatthew G. Knepley 
157dce8aebaSBarry Smith .seealso: `PetscFEGeom`, `PetscFEGeomRestoreChunk()`, `PetscFEGeomCreate()`
1586587ee25SMatthew G. Knepley @*/
159d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomGetPoint(PetscFEGeom *geom, PetscInt c, PetscInt p, const PetscReal pcoords[], PetscFEGeom *pgeom)
160d71ae5a4SJacob Faibussowitsch {
1616587ee25SMatthew G. Knepley   const PetscInt dim = geom->dim;
1626587ee25SMatthew G. Knepley   const PetscInt dE  = geom->dimEmbed;
1636587ee25SMatthew G. Knepley   const PetscInt Np  = geom->numPoints;
1646587ee25SMatthew G. Knepley 
1656587ee25SMatthew G. Knepley   PetscFunctionBeginHot;
1666587ee25SMatthew G. Knepley   pgeom->dim      = dim;
1676587ee25SMatthew G. Knepley   pgeom->dimEmbed = dE;
1686587ee25SMatthew G. Knepley   //pgeom->isAffine = geom->isAffine;
1696587ee25SMatthew G. Knepley   if (geom->isAffine) {
1706587ee25SMatthew G. Knepley     if (!p) {
1716587ee25SMatthew G. Knepley       pgeom->xi   = geom->xi;
1726587ee25SMatthew G. Knepley       pgeom->J    = &geom->J[c * Np * dE * dE];
1736587ee25SMatthew G. Knepley       pgeom->invJ = &geom->invJ[c * Np * dE * dE];
1746587ee25SMatthew G. Knepley       pgeom->detJ = &geom->detJ[c * Np];
1758e3a54c0SPierre Jolivet       pgeom->n    = PetscSafePointerPlusOffset(geom->n, c * Np * dE);
1766587ee25SMatthew G. Knepley     }
177ad540459SPierre Jolivet     if (pcoords) CoordinatesRefToReal(dE, dim, pgeom->xi, &geom->v[c * Np * dE], pgeom->J, pcoords, pgeom->v);
1786587ee25SMatthew G. Knepley   } else {
1796587ee25SMatthew G. Knepley     pgeom->v    = &geom->v[(c * Np + p) * dE];
1806587ee25SMatthew G. Knepley     pgeom->J    = &geom->J[(c * Np + p) * dE * dE];
1816587ee25SMatthew G. Knepley     pgeom->invJ = &geom->invJ[(c * Np + p) * dE * dE];
1826587ee25SMatthew G. Knepley     pgeom->detJ = &geom->detJ[c * Np + p];
1838e3a54c0SPierre Jolivet     pgeom->n    = PetscSafePointerPlusOffset(geom->n, (c * Np + p) * dE);
1846587ee25SMatthew G. Knepley   }
1853ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
1866587ee25SMatthew G. Knepley }
1876587ee25SMatthew G. Knepley 
1886587ee25SMatthew G. Knepley /*@C
189dce8aebaSBarry Smith   PetscFEGeomGetCellPoint - Get the cell geometry for face f at point p as a `PetscFEGeom`
1906587ee25SMatthew G. Knepley 
1916587ee25SMatthew G. Knepley   Input Parameters:
192dce8aebaSBarry Smith + geom - `PetscFEGeom` object
19360225df5SJacob Faibussowitsch . c    - The face
1946587ee25SMatthew G. Knepley - p    - The point
1956587ee25SMatthew G. Knepley 
1966587ee25SMatthew G. Knepley   Output Parameter:
1976587ee25SMatthew G. Knepley . pgeom - The cell geometry of face f at point p
1986587ee25SMatthew G. Knepley 
1996587ee25SMatthew G. Knepley   Level: intermediate
2006587ee25SMatthew G. Knepley 
201dce8aebaSBarry Smith   Note:
202dce8aebaSBarry Smith   For affine geometries, this only copies to pgeom at point 0. Since we copy pointers into pgeom,
203dce8aebaSBarry Smith   nothing needs to be done with it afterwards.
204dce8aebaSBarry Smith 
205dce8aebaSBarry Smith .seealso: `PetscFEGeom()`, `PetscFEGeomRestoreChunk()`, `PetscFEGeomCreate()`
2066587ee25SMatthew G. Knepley @*/
207d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomGetCellPoint(PetscFEGeom *geom, PetscInt c, PetscInt p, PetscFEGeom *pgeom)
208d71ae5a4SJacob Faibussowitsch {
2095fedec97SMatthew G. Knepley   const PetscBool bd  = geom->dimEmbed > geom->dim && !geom->isCohesive ? PETSC_TRUE : PETSC_FALSE;
2106587ee25SMatthew G. Knepley   const PetscInt  dim = bd ? geom->dimEmbed : geom->dim;
2116587ee25SMatthew G. Knepley   const PetscInt  dE  = geom->dimEmbed;
2126587ee25SMatthew G. Knepley   const PetscInt  Np  = geom->numPoints;
2136587ee25SMatthew G. Knepley 
2146587ee25SMatthew G. Knepley   PetscFunctionBeginHot;
2156587ee25SMatthew G. Knepley   pgeom->dim      = dim;
2166587ee25SMatthew G. Knepley   pgeom->dimEmbed = dE;
2176587ee25SMatthew G. Knepley   //pgeom->isAffine = geom->isAffine;
2186587ee25SMatthew G. Knepley   if (geom->isAffine) {
2196587ee25SMatthew G. Knepley     if (!p) {
2206587ee25SMatthew G. Knepley       if (bd) {
2216587ee25SMatthew G. Knepley         pgeom->J    = &geom->suppJ[0][c * Np * dE * dE];
2226587ee25SMatthew G. Knepley         pgeom->invJ = &geom->suppInvJ[0][c * Np * dE * dE];
2236587ee25SMatthew G. Knepley         pgeom->detJ = &geom->suppDetJ[0][c * Np];
2246587ee25SMatthew G. Knepley       } else {
2256587ee25SMatthew G. Knepley         pgeom->J    = &geom->J[c * Np * dE * dE];
2266587ee25SMatthew G. Knepley         pgeom->invJ = &geom->invJ[c * Np * dE * dE];
2276587ee25SMatthew G. Knepley         pgeom->detJ = &geom->detJ[c * Np];
2286587ee25SMatthew G. Knepley       }
2296587ee25SMatthew G. Knepley     }
2306587ee25SMatthew G. Knepley   } else {
2316587ee25SMatthew G. Knepley     if (bd) {
2326587ee25SMatthew G. Knepley       pgeom->J    = &geom->suppJ[0][(c * Np + p) * dE * dE];
2336587ee25SMatthew G. Knepley       pgeom->invJ = &geom->suppInvJ[0][(c * Np + p) * dE * dE];
2346587ee25SMatthew G. Knepley       pgeom->detJ = &geom->suppDetJ[0][c * Np + p];
2356587ee25SMatthew G. Knepley     } else {
2366587ee25SMatthew G. Knepley       pgeom->J    = &geom->J[(c * Np + p) * dE * dE];
2376587ee25SMatthew G. Knepley       pgeom->invJ = &geom->invJ[(c * Np + p) * dE * dE];
2386587ee25SMatthew G. Knepley       pgeom->detJ = &geom->detJ[c * Np + p];
2396587ee25SMatthew G. Knepley     }
2406587ee25SMatthew G. Knepley   }
2413ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
2426587ee25SMatthew G. Knepley }
2436587ee25SMatthew G. Knepley 
2442b99622eSMatthew G. Knepley /*@
245dce8aebaSBarry Smith   PetscFEGeomComplete - Calculate derived quantities from base geometry specification
2462b99622eSMatthew G. Knepley 
2472b99622eSMatthew G. Knepley   Input Parameter:
248dce8aebaSBarry Smith . geom - `PetscFEGeom` object
2492b99622eSMatthew G. Knepley 
2502b99622eSMatthew G. Knepley   Level: intermediate
2512b99622eSMatthew G. Knepley 
252dce8aebaSBarry Smith .seealso: `PetscFEGeom`, `PetscFEGeomCreate()`
2532b99622eSMatthew G. Knepley @*/
254d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscFEGeomComplete(PetscFEGeom *geom)
255d71ae5a4SJacob Faibussowitsch {
25620cf1dd8SToby Isaac   PetscInt i, j, N, dE;
25720cf1dd8SToby Isaac 
25820cf1dd8SToby Isaac   PetscFunctionBeginHot;
25920cf1dd8SToby Isaac   N  = geom->numPoints * geom->numCells;
26020cf1dd8SToby Isaac   dE = geom->dimEmbed;
26120cf1dd8SToby Isaac   switch (dE) {
26220cf1dd8SToby Isaac   case 3:
26320cf1dd8SToby Isaac     for (i = 0; i < N; i++) {
26420cf1dd8SToby Isaac       DMPlex_Det3D_Internal(&geom->detJ[i], &geom->J[dE * dE * i]);
26520cf1dd8SToby Isaac       if (geom->invJ) DMPlex_Invert3D_Internal(&geom->invJ[dE * dE * i], &geom->J[dE * dE * i], geom->detJ[i]);
26620cf1dd8SToby Isaac     }
26720cf1dd8SToby Isaac     break;
26820cf1dd8SToby Isaac   case 2:
26920cf1dd8SToby Isaac     for (i = 0; i < N; i++) {
27020cf1dd8SToby Isaac       DMPlex_Det2D_Internal(&geom->detJ[i], &geom->J[dE * dE * i]);
27120cf1dd8SToby Isaac       if (geom->invJ) DMPlex_Invert2D_Internal(&geom->invJ[dE * dE * i], &geom->J[dE * dE * i], geom->detJ[i]);
27220cf1dd8SToby Isaac     }
27320cf1dd8SToby Isaac     break;
27420cf1dd8SToby Isaac   case 1:
27520cf1dd8SToby Isaac     for (i = 0; i < N; i++) {
27620cf1dd8SToby Isaac       geom->detJ[i] = PetscAbsReal(geom->J[i]);
27720cf1dd8SToby Isaac       if (geom->invJ) geom->invJ[i] = 1. / geom->J[i];
27820cf1dd8SToby Isaac     }
27920cf1dd8SToby Isaac     break;
28020cf1dd8SToby Isaac   }
28120cf1dd8SToby Isaac   if (geom->n) {
28220cf1dd8SToby Isaac     for (i = 0; i < N; i++) {
283ad540459SPierre Jolivet       for (j = 0; j < dE; j++) geom->n[dE * i + j] = geom->J[dE * dE * i + dE * j + dE - 1] * ((dE == 2) ? -1. : 1.);
28420cf1dd8SToby Isaac     }
28520cf1dd8SToby Isaac   }
2863ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
28720cf1dd8SToby Isaac }
288