175d3a19aSMatthew G. Knepley #include <petsc-private/dmpleximpl.h> /*I "petscdmplex.h" I*/ 275d3a19aSMatthew G. Knepley #include <petscsf.h> 375d3a19aSMatthew G. Knepley 475d3a19aSMatthew G. Knepley #undef __FUNCT__ 575d3a19aSMatthew G. Knepley #define __FUNCT__ "GetDepthStart_Private" 675d3a19aSMatthew G. Knepley PETSC_STATIC_INLINE PetscErrorCode GetDepthStart_Private(PetscInt depth, PetscInt depthSize[], PetscInt *cStart, PetscInt *fStart, PetscInt *eStart, PetscInt *vStart) 775d3a19aSMatthew G. Knepley { 875d3a19aSMatthew G. Knepley PetscFunctionBegin; 975d3a19aSMatthew G. Knepley if (cStart) *cStart = 0; 1075d3a19aSMatthew G. Knepley if (vStart) *vStart = depthSize[depth]; 1175d3a19aSMatthew G. Knepley if (fStart) *fStart = depthSize[depth] + depthSize[0]; 1275d3a19aSMatthew G. Knepley if (eStart) *eStart = depthSize[depth] + depthSize[0] + depthSize[depth-1]; 1375d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 1475d3a19aSMatthew G. Knepley } 1575d3a19aSMatthew G. Knepley 1675d3a19aSMatthew G. Knepley #undef __FUNCT__ 1775d3a19aSMatthew G. Knepley #define __FUNCT__ "GetDepthEnd_Private" 1875d3a19aSMatthew G. Knepley PETSC_STATIC_INLINE PetscErrorCode GetDepthEnd_Private(PetscInt depth, PetscInt depthSize[], PetscInt *cEnd, PetscInt *fEnd, PetscInt *eEnd, PetscInt *vEnd) 1975d3a19aSMatthew G. Knepley { 2075d3a19aSMatthew G. Knepley PetscFunctionBegin; 2175d3a19aSMatthew G. Knepley if (cEnd) *cEnd = depthSize[depth]; 2275d3a19aSMatthew G. Knepley if (vEnd) *vEnd = depthSize[depth] + depthSize[0]; 2375d3a19aSMatthew G. Knepley if (fEnd) *fEnd = depthSize[depth] + depthSize[0] + depthSize[depth-1]; 2475d3a19aSMatthew G. Knepley if (eEnd) *eEnd = depthSize[depth] + depthSize[0] + depthSize[depth-1] + depthSize[1]; 2575d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 2675d3a19aSMatthew G. Knepley } 2775d3a19aSMatthew G. Knepley 2875d3a19aSMatthew G. Knepley #undef __FUNCT__ 29b5da9499SMatthew G. Knepley #define __FUNCT__ "DMPlexGetNumHybridFaces_Internal" 30b5da9499SMatthew G. Knepley /* This is a stopgap since we do not currently keep track of faces for hybrid cells */ 31b5da9499SMatthew G. Knepley static PetscErrorCode DMPlexGetNumHybridFaces_Internal(DM dm, PetscInt *numHybridFaces) 32b5da9499SMatthew G. Knepley { 33b5da9499SMatthew G. Knepley PetscInt eStart, eEnd, eMax, cEnd, cMax, c, hEdges = 0; 34b5da9499SMatthew G. Knepley PetscErrorCode ierr; 35b5da9499SMatthew G. Knepley 36b5da9499SMatthew G. Knepley PetscFunctionBegin; 37b5da9499SMatthew G. Knepley *numHybridFaces = 0; 38b5da9499SMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 39b5da9499SMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, NULL, &cEnd);CHKERRQ(ierr); 40b5da9499SMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, NULL, &eMax, NULL);CHKERRQ(ierr); 41b5da9499SMatthew G. Knepley if (cMax < 0) PetscFunctionReturn(0); 42b5da9499SMatthew G. Knepley /* Count interior edges in hybrid cells */ 43b5da9499SMatthew G. Knepley for (c = cMax; c < cEnd; ++c) { 44b5da9499SMatthew G. Knepley PetscInt *closure = NULL, closureSize, cl; 45b5da9499SMatthew G. Knepley 46b5da9499SMatthew G. Knepley ierr = DMPlexGetTransitiveClosure(dm, c, PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); 47b5da9499SMatthew G. Knepley for (cl = 0; cl < closureSize*2; cl += 2) { 48b5da9499SMatthew G. Knepley const PetscInt p = closure[cl]; 49b5da9499SMatthew G. Knepley 50b5da9499SMatthew G. Knepley if ((p >= eStart) && (p < eMax)) ++hEdges; 51b5da9499SMatthew G. Knepley } 52b5da9499SMatthew G. Knepley ierr = DMPlexRestoreTransitiveClosure(dm, c, PETSC_TRUE, &closureSize, &closure);CHKERRQ(ierr); 53b5da9499SMatthew G. Knepley } 54b5da9499SMatthew G. Knepley if (hEdges%2) SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Number of interior edges in hybrid cells cannot be odd: %d", hEdges); 55b5da9499SMatthew G. Knepley *numHybridFaces = hEdges/2; 56b5da9499SMatthew G. Knepley PetscFunctionReturn(0); 57b5da9499SMatthew G. Knepley } 58b5da9499SMatthew G. Knepley 59b5da9499SMatthew G. Knepley #undef __FUNCT__ 6075d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerGetSizes" 6175d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerGetSizes(CellRefiner refiner, DM dm, PetscInt depthSize[]) 6275d3a19aSMatthew G. Knepley { 63b5da9499SMatthew G. Knepley PetscInt numHybridFaces, cStart, cEnd, cMax, vStart, vEnd, vMax, fStart, fEnd, fMax, eStart, eEnd, eMax; 6475d3a19aSMatthew G. Knepley PetscErrorCode ierr; 6575d3a19aSMatthew G. Knepley 6675d3a19aSMatthew G. Knepley PetscFunctionBegin; 6775d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 6875d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 6975d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 7075d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 7175d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, &fMax, &eMax, &vMax);CHKERRQ(ierr); 7275d3a19aSMatthew G. Knepley switch (refiner) { 7375d3a19aSMatthew G. Knepley case 1: 7475d3a19aSMatthew G. Knepley /* Simplicial 2D */ 7575d3a19aSMatthew G. Knepley depthSize[0] = vEnd - vStart + fEnd - fStart; /* Add a vertex on every face */ 7675d3a19aSMatthew G. Knepley depthSize[1] = 2*(fEnd - fStart) + 3*(cEnd - cStart); /* Every face is split into 2 faces and 3 faces are added for each cell */ 7775d3a19aSMatthew G. Knepley depthSize[2] = 4*(cEnd - cStart); /* Every cell split into 4 cells */ 7875d3a19aSMatthew G. Knepley break; 7975d3a19aSMatthew G. Knepley case 3: 80d963de37SMatthew G. Knepley /* Hybrid Simplicial 2D */ 8175d3a19aSMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 8275d3a19aSMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 8375d3a19aSMatthew G. Knepley if (fMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No face maximum specified in hybrid mesh"); 8475d3a19aSMatthew G. Knepley fMax = PetscMin(fEnd, fMax); 8575d3a19aSMatthew G. Knepley depthSize[0] = vEnd - vStart + fMax - fStart; /* Add a vertex on every face, but not hybrid faces */ 8675d3a19aSMatthew G. Knepley depthSize[1] = 2*(fMax - fStart) + 3*(cMax - cStart) + (fEnd - fMax) + (cEnd - cMax); /* Every interior face is split into 2 faces, 3 faces are added for each interior cell, and one in each hybrid cell */ 8775d3a19aSMatthew G. Knepley depthSize[2] = 4*(cMax - cStart) + 2*(cEnd - cMax); /* Interior cells split into 4 cells, Hybrid cells split into 2 cells */ 8875d3a19aSMatthew G. Knepley break; 8975d3a19aSMatthew G. Knepley case 2: 9075d3a19aSMatthew G. Knepley /* Hex 2D */ 9175d3a19aSMatthew G. Knepley depthSize[0] = vEnd - vStart + cEnd - cStart + fEnd - fStart; /* Add a vertex on every face and cell */ 9275d3a19aSMatthew G. Knepley depthSize[1] = 2*(fEnd - fStart) + 4*(cEnd - cStart); /* Every face is split into 2 faces and 4 faces are added for each cell */ 9375d3a19aSMatthew G. Knepley depthSize[2] = 4*(cEnd - cStart); /* Every cell split into 4 cells */ 9475d3a19aSMatthew G. Knepley break; 95b5da9499SMatthew G. Knepley case 5: 96b5da9499SMatthew G. Knepley /* Simplicial 3D */ 97b5da9499SMatthew G. Knepley depthSize[0] = vEnd - vStart + eEnd - eStart; /* Add a vertex on every edge */ 98b5da9499SMatthew G. Knepley depthSize[1] = 2*(eEnd - eStart) + 3*(fEnd - fStart) + (cEnd - cStart); /* Every edge is split into 2 edges, 3 edges are added for each face, and 1 edge for each cell */ 99b5da9499SMatthew G. Knepley depthSize[2] = 4*(fEnd - fStart) + 8*(cEnd - cStart); /* Every face split into 4 faces and 8 faces are added for each cell */ 100b5da9499SMatthew G. Knepley depthSize[3] = 8*(cEnd - cStart); /* Every cell split into 8 cells */ 101b5da9499SMatthew G. Knepley break; 102b5da9499SMatthew G. Knepley case 7: 103b5da9499SMatthew G. Knepley /* Hybrid Simplicial 3D */ 104b5da9499SMatthew G. Knepley ierr = DMPlexGetNumHybridFaces_Internal(dm, &numHybridFaces);CHKERRQ(ierr); 105b5da9499SMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 106b5da9499SMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 107b5da9499SMatthew G. Knepley if (eMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No edge maximum specified in hybrid mesh"); 108b5da9499SMatthew G. Knepley eMax = PetscMin(eEnd, eMax); 109b5da9499SMatthew G. Knepley depthSize[0] = vEnd - vStart + eMax - eStart; /* Add a vertex on every edge, but not hybrid edges */ 110b5da9499SMatthew G. Knepley depthSize[1] = 2*(eMax - eStart) + 13*(cMax - cStart) + (eEnd - eMax) + numHybridFaces; /* Every interior edge is split into 2 edges and 13 edges are added for each interior cell, each hybrid edge stays intact, and one new hybrid edge for each two interior edges (hybrid face) on a hybrid cell */ 111b5da9499SMatthew G. Knepley depthSize[2] = 4*(fEnd - fStart) + 8*(cEnd - cStart); /* Every face split into 4 faces and 8 faces are added for each cell */ 112b5da9499SMatthew G. Knepley depthSize[3] = 8*(cMax - cStart) + 4*(cEnd - cMax); /* Every interior cell split into 8 cells, and every hybrid cell split into 4 cells */ 113b5da9499SMatthew G. Knepley break; 11475d3a19aSMatthew G. Knepley default: 11575d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 11675d3a19aSMatthew G. Knepley } 11775d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 11875d3a19aSMatthew G. Knepley } 11975d3a19aSMatthew G. Knepley 12075d3a19aSMatthew G. Knepley #undef __FUNCT__ 12175d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerSetConeSizes" 12275d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerSetConeSizes(CellRefiner refiner, DM dm, PetscInt depthSize[], DM rdm) 12375d3a19aSMatthew G. Knepley { 124b5da9499SMatthew G. Knepley PetscInt depth, cStart, cStartNew, cEnd, cMax, c, vStart, vStartNew, vEnd, vMax, v, fStart, fStartNew, fEnd, fMax, f, eStart, eStartNew, eEnd, eMax, e, r; 12575d3a19aSMatthew G. Knepley PetscErrorCode ierr; 12675d3a19aSMatthew G. Knepley 12775d3a19aSMatthew G. Knepley PetscFunctionBegin; 12875d3a19aSMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 12975d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 13075d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 13175d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 13275d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 13375d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, &fMax, &eMax, &vMax);CHKERRQ(ierr); 13475d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, depthSize, &cStartNew, &fStartNew, &eStartNew, &vStartNew);CHKERRQ(ierr); 13575d3a19aSMatthew G. Knepley switch (refiner) { 13675d3a19aSMatthew G. Knepley case 1: 13775d3a19aSMatthew G. Knepley /* Simplicial 2D */ 13875d3a19aSMatthew G. Knepley /* All cells have 3 faces */ 13975d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 14075d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 14175d3a19aSMatthew G. Knepley const PetscInt newp = (c - cStart)*4 + r; 14275d3a19aSMatthew G. Knepley 14375d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 3);CHKERRQ(ierr); 14475d3a19aSMatthew G. Knepley } 14575d3a19aSMatthew G. Knepley } 14675d3a19aSMatthew G. Knepley /* Split faces have 2 vertices and the same cells as the parent */ 14775d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 14875d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 14975d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 15075d3a19aSMatthew G. Knepley PetscInt size; 15175d3a19aSMatthew G. Knepley 15275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 15375d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 15475d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 15575d3a19aSMatthew G. Knepley } 15675d3a19aSMatthew G. Knepley } 15775d3a19aSMatthew G. Knepley /* Interior faces have 2 vertices and 2 cells */ 15875d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 15975d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 16075d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + r; 16175d3a19aSMatthew G. Knepley 16275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 16375d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2);CHKERRQ(ierr); 16475d3a19aSMatthew G. Knepley } 16575d3a19aSMatthew G. Knepley } 16675d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 16775d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 16875d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 16975d3a19aSMatthew G. Knepley PetscInt size; 17075d3a19aSMatthew G. Knepley 17175d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 17275d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 17375d3a19aSMatthew G. Knepley } 17475d3a19aSMatthew G. Knepley /* Face vertices have 2 + cells*2 supports */ 17575d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 17675d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 17775d3a19aSMatthew G. Knepley PetscInt size; 17875d3a19aSMatthew G. Knepley 17975d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 18075d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2 + size*2);CHKERRQ(ierr); 18175d3a19aSMatthew G. Knepley } 18275d3a19aSMatthew G. Knepley break; 18375d3a19aSMatthew G. Knepley case 2: 18475d3a19aSMatthew G. Knepley /* Hex 2D */ 18575d3a19aSMatthew G. Knepley /* All cells have 4 faces */ 18675d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 18775d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 18875d3a19aSMatthew G. Knepley const PetscInt newp = (c - cStart)*4 + r; 18975d3a19aSMatthew G. Knepley 19075d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 4);CHKERRQ(ierr); 19175d3a19aSMatthew G. Knepley } 19275d3a19aSMatthew G. Knepley } 19375d3a19aSMatthew G. Knepley /* Split faces have 2 vertices and the same cells as the parent */ 19475d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 19575d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 19675d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 19775d3a19aSMatthew G. Knepley PetscInt size; 19875d3a19aSMatthew G. Knepley 19975d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 20075d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 20175d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 20275d3a19aSMatthew G. Knepley } 20375d3a19aSMatthew G. Knepley } 20475d3a19aSMatthew G. Knepley /* Interior faces have 2 vertices and 2 cells */ 20575d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 20675d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 20775d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + r; 20875d3a19aSMatthew G. Knepley 20975d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 21075d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2);CHKERRQ(ierr); 21175d3a19aSMatthew G. Knepley } 21275d3a19aSMatthew G. Knepley } 21375d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 21475d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 21575d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 21675d3a19aSMatthew G. Knepley PetscInt size; 21775d3a19aSMatthew G. Knepley 21875d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 21975d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 22075d3a19aSMatthew G. Knepley } 22175d3a19aSMatthew G. Knepley /* Face vertices have 2 + cells supports */ 22275d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 22375d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 22475d3a19aSMatthew G. Knepley PetscInt size; 22575d3a19aSMatthew G. Knepley 22675d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 22775d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2 + size);CHKERRQ(ierr); 22875d3a19aSMatthew G. Knepley } 22975d3a19aSMatthew G. Knepley /* Cell vertices have 4 supports */ 23075d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 23175d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (fEnd - fStart) + (c - cStart); 23275d3a19aSMatthew G. Knepley 23375d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 4);CHKERRQ(ierr); 23475d3a19aSMatthew G. Knepley } 23575d3a19aSMatthew G. Knepley break; 23675d3a19aSMatthew G. Knepley case 3: 237d963de37SMatthew G. Knepley /* Hybrid Simplicial 2D */ 23875d3a19aSMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 23975d3a19aSMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 24075d3a19aSMatthew G. Knepley if (fMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No face maximum specified in hybrid mesh"); 24175d3a19aSMatthew G. Knepley fMax = PetscMin(fEnd, fMax); 24275d3a19aSMatthew G. Knepley ierr = DMPlexSetHybridBounds(rdm, cStartNew + (cMax - cStart)*4, fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3, PETSC_DETERMINE, PETSC_DETERMINE);CHKERRQ(ierr); 24375d3a19aSMatthew G. Knepley /* Interior cells have 3 faces */ 24475d3a19aSMatthew G. Knepley for (c = cStart; c < cMax; ++c) { 24575d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 24675d3a19aSMatthew G. Knepley const PetscInt newp = cStartNew + (c - cStart)*4 + r; 24775d3a19aSMatthew G. Knepley 24875d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 3);CHKERRQ(ierr); 24975d3a19aSMatthew G. Knepley } 25075d3a19aSMatthew G. Knepley } 25175d3a19aSMatthew G. Knepley /* Hybrid cells have 4 faces */ 25275d3a19aSMatthew G. Knepley for (c = cMax; c < cEnd; ++c) { 25375d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 25475d3a19aSMatthew G. Knepley const PetscInt newp = cStartNew + (cMax - cStart)*4 + (c - cMax)*2 + r; 25575d3a19aSMatthew G. Knepley 25675d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 4);CHKERRQ(ierr); 25775d3a19aSMatthew G. Knepley } 25875d3a19aSMatthew G. Knepley } 25975d3a19aSMatthew G. Knepley /* Interior split faces have 2 vertices and the same cells as the parent */ 26075d3a19aSMatthew G. Knepley for (f = fStart; f < fMax; ++f) { 26175d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 26275d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 26375d3a19aSMatthew G. Knepley PetscInt size; 26475d3a19aSMatthew G. Knepley 26575d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 26675d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 26775d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 26875d3a19aSMatthew G. Knepley } 26975d3a19aSMatthew G. Knepley } 27075d3a19aSMatthew G. Knepley /* Interior cell faces have 2 vertices and 2 cells */ 27175d3a19aSMatthew G. Knepley for (c = cStart; c < cMax; ++c) { 27275d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 27375d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + r; 27475d3a19aSMatthew G. Knepley 27575d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 27675d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2);CHKERRQ(ierr); 27775d3a19aSMatthew G. Knepley } 27875d3a19aSMatthew G. Knepley } 27975d3a19aSMatthew G. Knepley /* Hybrid faces have 2 vertices and the same cells */ 28075d3a19aSMatthew G. Knepley for (f = fMax; f < fEnd; ++f) { 28175d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (f - fMax); 28275d3a19aSMatthew G. Knepley PetscInt size; 28375d3a19aSMatthew G. Knepley 28475d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 28575d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 28675d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 28775d3a19aSMatthew G. Knepley } 28875d3a19aSMatthew G. Knepley /* Hybrid cell faces have 2 vertices and 2 cells */ 28975d3a19aSMatthew G. Knepley for (c = cMax; c < cEnd; ++c) { 29075d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (fEnd - fMax) + (c - cMax); 29175d3a19aSMatthew G. Knepley 29275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 29375d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2);CHKERRQ(ierr); 29475d3a19aSMatthew G. Knepley } 29575d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 29675d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 29775d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 29875d3a19aSMatthew G. Knepley PetscInt size; 29975d3a19aSMatthew G. Knepley 30075d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 30175d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 30275d3a19aSMatthew G. Knepley } 30375d3a19aSMatthew G. Knepley /* Face vertices have 2 + (2 interior, 1 hybrid) supports */ 30475d3a19aSMatthew G. Knepley for (f = fStart; f < fMax; ++f) { 30575d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 30675d3a19aSMatthew G. Knepley const PetscInt *support; 30775d3a19aSMatthew G. Knepley PetscInt size, newSize = 2, s; 30875d3a19aSMatthew G. Knepley 30975d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 31075d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 31175d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 31275d3a19aSMatthew G. Knepley if (support[s] >= cMax) newSize += 1; 31375d3a19aSMatthew G. Knepley else newSize += 2; 31475d3a19aSMatthew G. Knepley } 31575d3a19aSMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, newSize);CHKERRQ(ierr); 31675d3a19aSMatthew G. Knepley } 31775d3a19aSMatthew G. Knepley break; 318b5da9499SMatthew G. Knepley case 5: 319b5da9499SMatthew G. Knepley /* Simplicial 3D */ 320b5da9499SMatthew G. Knepley /* All cells have 4 faces */ 321b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 322b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r) { 323b5da9499SMatthew G. Knepley const PetscInt newp = (c - cStart)*8 + r; 324b5da9499SMatthew G. Knepley 325b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 4);CHKERRQ(ierr); 326b5da9499SMatthew G. Knepley } 327b5da9499SMatthew G. Knepley } 328b5da9499SMatthew G. Knepley /* Split faces have 3 edges and the same cells as the parent */ 329b5da9499SMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 330b5da9499SMatthew G. Knepley for (r = 0; r < 4; ++r) { 331b5da9499SMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*4 + r; 332b5da9499SMatthew G. Knepley PetscInt size; 333b5da9499SMatthew G. Knepley 334b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 3);CHKERRQ(ierr); 335b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 336b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 337b5da9499SMatthew G. Knepley } 338b5da9499SMatthew G. Knepley } 339b5da9499SMatthew G. Knepley /* Interior faces have 3 edges and 2 cells */ 340b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 341b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r) { 342b5da9499SMatthew G. Knepley const PetscInt newp = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + r; 343b5da9499SMatthew G. Knepley 344b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 3);CHKERRQ(ierr); 345b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2);CHKERRQ(ierr); 346b5da9499SMatthew G. Knepley } 347b5da9499SMatthew G. Knepley } 348b5da9499SMatthew G. Knepley /* Split edges have 2 vertices and the same faces */ 349b5da9499SMatthew G. Knepley for (e = eStart; e < eEnd; ++e) { 350b5da9499SMatthew G. Knepley for (r = 0; r < 2; ++r) { 351b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (e - eStart)*2 + r; 352b5da9499SMatthew G. Knepley PetscInt size; 353b5da9499SMatthew G. Knepley 354b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 355b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, e, &size);CHKERRQ(ierr); 356b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 357b5da9499SMatthew G. Knepley } 358b5da9499SMatthew G. Knepley } 359b5da9499SMatthew G. Knepley /* Face edges have 2 vertices and 2+cells*(1/2) faces */ 360b5da9499SMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 361b5da9499SMatthew G. Knepley for (r = 0; r < 3; ++r) { 362b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + r; 363b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt, *support, eint[4] = {1, 0, 2, 0}; 364b5da9499SMatthew G. Knepley PetscInt coneSize, c, supportSize, s, er, intFaces = 0; 365b5da9499SMatthew G. Knepley 366b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 367b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 368b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 369b5da9499SMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 370b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 371b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 372b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 373b5da9499SMatthew G. Knepley for (c = 0; c < coneSize; ++c) {if (cone[c] == f) break;} 37486f0afeeSMatthew G. Knepley /* Here we want to determine whether edge newp contains a vertex which is part of the cross-tet edge */ 37586f0afeeSMatthew G. Knepley er = ornt[c] < 0 ? (-(ornt[c]+1) + 2-r)%3 : (ornt[c] + r)%3; 376b5da9499SMatthew G. Knepley if (er == eint[c]) { 377b5da9499SMatthew G. Knepley intFaces += 1; 378b5da9499SMatthew G. Knepley } else { 379b5da9499SMatthew G. Knepley intFaces += 2; 380b5da9499SMatthew G. Knepley } 381b5da9499SMatthew G. Knepley } 382b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2+intFaces);CHKERRQ(ierr); 383b5da9499SMatthew G. Knepley } 384b5da9499SMatthew G. Knepley } 385b5da9499SMatthew G. Knepley /* Interior edges have 2 vertices and 4 faces */ 386b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 387b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 388b5da9499SMatthew G. Knepley 389b5da9499SMatthew G. Knepley ierr = DMPlexSetConeSize(rdm, newp, 2);CHKERRQ(ierr); 390b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 4);CHKERRQ(ierr); 391b5da9499SMatthew G. Knepley } 392b5da9499SMatthew G. Knepley /* Old vertices have identical supports */ 393b5da9499SMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 394b5da9499SMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 395b5da9499SMatthew G. Knepley PetscInt size; 396b5da9499SMatthew G. Knepley 397b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 398b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, size);CHKERRQ(ierr); 399b5da9499SMatthew G. Knepley } 400b5da9499SMatthew G. Knepley /* Edge vertices have 2 + faces*2 + cells*0/1 supports */ 401b5da9499SMatthew G. Knepley for (e = eStart; e < eEnd; ++e) { 402b5da9499SMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (e - eStart); 403b5da9499SMatthew G. Knepley PetscInt size, *star = NULL, starSize, s, cellSize = 0; 404b5da9499SMatthew G. Knepley 405b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, e, &size);CHKERRQ(ierr); 406b5da9499SMatthew G. Knepley ierr = DMPlexGetTransitiveClosure(dm, e, PETSC_FALSE, &starSize, &star);CHKERRQ(ierr); 407b5da9499SMatthew G. Knepley for (s = 0; s < starSize*2; s += 2) { 408b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt; 409b5da9499SMatthew G. Knepley PetscInt e01, e23; 410b5da9499SMatthew G. Knepley 411b5da9499SMatthew G. Knepley if ((star[s] >= cStart) && (star[s] < cEnd)) { 412b5da9499SMatthew G. Knepley /* Check edge 0-1 */ 413b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, star[s], &cone);CHKERRQ(ierr); 414b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, star[s], &ornt);CHKERRQ(ierr); 415b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[0], &cone);CHKERRQ(ierr); 416b5da9499SMatthew G. Knepley e01 = cone[ornt[0] < 0 ? (-(ornt[0]+1) + 0)%3 : ornt[0]]; 417b5da9499SMatthew G. Knepley /* Check edge 2-3 */ 418b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, star[s], &cone);CHKERRQ(ierr); 419b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, star[s], &ornt);CHKERRQ(ierr); 420b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[3], &cone);CHKERRQ(ierr); 421b5da9499SMatthew G. Knepley e23 = cone[ornt[3] < 0 ? (-(ornt[3]+1) + 2)%3 : (ornt[3] + 2)%3]; 422b5da9499SMatthew G. Knepley if ((e01 == e) || (e23 == e)) ++cellSize; 423b5da9499SMatthew G. Knepley } 424b5da9499SMatthew G. Knepley } 425b5da9499SMatthew G. Knepley ierr = DMPlexRestoreTransitiveClosure(dm, e, PETSC_FALSE, &starSize, &star);CHKERRQ(ierr); 426b5da9499SMatthew G. Knepley ierr = DMPlexSetSupportSize(rdm, newp, 2 + size*2 + cellSize);CHKERRQ(ierr); 427b5da9499SMatthew G. Knepley } 428b5da9499SMatthew G. Knepley break; 42975d3a19aSMatthew G. Knepley default: 43075d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 43175d3a19aSMatthew G. Knepley } 43275d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 43375d3a19aSMatthew G. Knepley } 43475d3a19aSMatthew G. Knepley 43575d3a19aSMatthew G. Knepley #undef __FUNCT__ 43675d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerSetCones" 43775d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerSetCones(CellRefiner refiner, DM dm, PetscInt depthSize[], DM rdm) 43875d3a19aSMatthew G. Knepley { 439b5da9499SMatthew G. Knepley const PetscInt *faces, cellInd[4] = {0, 1, 2, 3}; 440b5da9499SMatthew G. Knepley PetscInt depth, cStart, cEnd, cMax, cStartNew, cEndNew, c, vStart, vEnd, vMax, vStartNew, vEndNew, v, fStart, fEnd, fMax, fStartNew, fEndNew, f, eStart, eEnd, eMax, eStartNew, eEndNew, e, r, p; 44175d3a19aSMatthew G. Knepley PetscInt maxSupportSize, *supportRef; 44275d3a19aSMatthew G. Knepley PetscErrorCode ierr; 44375d3a19aSMatthew G. Knepley 44475d3a19aSMatthew G. Knepley PetscFunctionBegin; 44575d3a19aSMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 44675d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 44775d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 44875d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 44975d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 45075d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, &fMax, &eMax, &vMax);CHKERRQ(ierr); 45175d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, depthSize, &cStartNew, &fStartNew, &eStartNew, &vStartNew);CHKERRQ(ierr); 45275d3a19aSMatthew G. Knepley ierr = GetDepthEnd_Private(depth, depthSize, &cEndNew, &fEndNew, &eEndNew, &vEndNew);CHKERRQ(ierr); 45375d3a19aSMatthew G. Knepley switch (refiner) { 45475d3a19aSMatthew G. Knepley case 1: 45575d3a19aSMatthew G. Knepley /* Simplicial 2D */ 45675d3a19aSMatthew G. Knepley /* 45775d3a19aSMatthew G. Knepley 2 45875d3a19aSMatthew G. Knepley |\ 45975d3a19aSMatthew G. Knepley | \ 46075d3a19aSMatthew G. Knepley | \ 46175d3a19aSMatthew G. Knepley | \ 46275d3a19aSMatthew G. Knepley | C \ 46375d3a19aSMatthew G. Knepley | \ 46475d3a19aSMatthew G. Knepley | \ 46575d3a19aSMatthew G. Knepley 2---1---1 46675d3a19aSMatthew G. Knepley |\ D / \ 46775d3a19aSMatthew G. Knepley | 2 0 \ 46875d3a19aSMatthew G. Knepley |A \ / B \ 46975d3a19aSMatthew G. Knepley 0---0-------1 47075d3a19aSMatthew G. Knepley */ 47175d3a19aSMatthew G. Knepley /* All cells have 3 faces */ 47275d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 47375d3a19aSMatthew G. Knepley const PetscInt newp = cStartNew + (c - cStart)*4; 47475d3a19aSMatthew G. Knepley const PetscInt *cone, *ornt; 47575d3a19aSMatthew G. Knepley PetscInt coneNew[3], orntNew[3]; 47675d3a19aSMatthew G. Knepley 47775d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 47875d3a19aSMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 47975d3a19aSMatthew G. Knepley /* A triangle */ 48075d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 1 : 0); 48175d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 48275d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 2; 48375d3a19aSMatthew G. Knepley orntNew[1] = -2; 48475d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 0 : 1); 48575d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 48675d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 48775d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 48875d3a19aSMatthew G. Knepley #if 1 48975d3a19aSMatthew G. Knepley if ((newp+0 < cStartNew) || (newp+0 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+0, cStartNew, cEndNew); 49075d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 49175d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 49275d3a19aSMatthew G. Knepley } 49375d3a19aSMatthew G. Knepley #endif 49475d3a19aSMatthew G. Knepley /* B triangle */ 49575d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 0 : 1); 49675d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 49775d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 1 : 0); 49875d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 49975d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 0; 50075d3a19aSMatthew G. Knepley orntNew[2] = -2; 50175d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 50275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 50375d3a19aSMatthew G. Knepley #if 1 50475d3a19aSMatthew G. Knepley if ((newp+1 < cStartNew) || (newp+1 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+1, cStartNew, cEndNew); 50575d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 50675d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 50775d3a19aSMatthew G. Knepley } 50875d3a19aSMatthew G. Knepley #endif 50975d3a19aSMatthew G. Knepley /* C triangle */ 51075d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 1; 51175d3a19aSMatthew G. Knepley orntNew[0] = -2; 51275d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 0 : 1); 51375d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 51475d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 1 : 0); 51575d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 51675d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+2, coneNew);CHKERRQ(ierr); 51775d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+2, orntNew);CHKERRQ(ierr); 51875d3a19aSMatthew G. Knepley #if 1 51975d3a19aSMatthew G. Knepley if ((newp+2 < cStartNew) || (newp+2 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+2, cStartNew, cEndNew); 52075d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 52175d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 52275d3a19aSMatthew G. Knepley } 52375d3a19aSMatthew G. Knepley #endif 52475d3a19aSMatthew G. Knepley /* D triangle */ 52575d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 0; 52675d3a19aSMatthew G. Knepley orntNew[0] = 0; 52775d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 1; 52875d3a19aSMatthew G. Knepley orntNew[1] = 0; 52975d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + 2; 53075d3a19aSMatthew G. Knepley orntNew[2] = 0; 53175d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+3, coneNew);CHKERRQ(ierr); 53275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+3, orntNew);CHKERRQ(ierr); 53375d3a19aSMatthew G. Knepley #if 1 53475d3a19aSMatthew G. Knepley if ((newp+3 < cStartNew) || (newp+3 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+3, cStartNew, cEndNew); 53575d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 53675d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 53775d3a19aSMatthew G. Knepley } 53875d3a19aSMatthew G. Knepley #endif 53975d3a19aSMatthew G. Knepley } 54075d3a19aSMatthew G. Knepley /* Split faces have 2 vertices and the same cells as the parent */ 54175d3a19aSMatthew G. Knepley ierr = DMPlexGetMaxSizes(dm, NULL, &maxSupportSize);CHKERRQ(ierr); 54275d3a19aSMatthew G. Knepley ierr = PetscMalloc((2 + maxSupportSize*2) * sizeof(PetscInt), &supportRef);CHKERRQ(ierr); 54375d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 54475d3a19aSMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (f - fStart); 54575d3a19aSMatthew G. Knepley 54675d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 54775d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 548*297d2bf4SMatthew G. Knepley const PetscInt *cone, *ornt, *support; 54975d3a19aSMatthew G. Knepley PetscInt coneNew[2], coneSize, c, supportSize, s; 55075d3a19aSMatthew G. Knepley 55175d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 55275d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (cone[0] - vStart); 55375d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (cone[1] - vStart); 55475d3a19aSMatthew G. Knepley coneNew[(r+1)%2] = newv; 55575d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 55675d3a19aSMatthew G. Knepley #if 1 55775d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 55875d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 55975d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 56075d3a19aSMatthew G. Knepley } 56175d3a19aSMatthew G. Knepley #endif 56275d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 56375d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 56475d3a19aSMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 56575d3a19aSMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 56675d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 567*297d2bf4SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 56875d3a19aSMatthew G. Knepley for (c = 0; c < coneSize; ++c) { 56975d3a19aSMatthew G. Knepley if (cone[c] == f) break; 57075d3a19aSMatthew G. Knepley } 571*297d2bf4SMatthew G. Knepley supportRef[s] = cStartNew + (support[s] - cStart)*4 + (ornt[c] < 0 ? (c+1-r)%3 : (c+r)%3); 57275d3a19aSMatthew G. Knepley } 57375d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 57475d3a19aSMatthew G. Knepley #if 1 57575d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 57675d3a19aSMatthew G. Knepley for (p = 0; p < supportSize; ++p) { 57775d3a19aSMatthew G. Knepley if ((supportRef[p] < cStartNew) || (supportRef[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportRef[p], cStartNew, cEndNew); 57875d3a19aSMatthew G. Knepley } 57975d3a19aSMatthew G. Knepley #endif 58075d3a19aSMatthew G. Knepley } 58175d3a19aSMatthew G. Knepley } 58275d3a19aSMatthew G. Knepley /* Interior faces have 2 vertices and 2 cells */ 58375d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 58475d3a19aSMatthew G. Knepley const PetscInt *cone; 58575d3a19aSMatthew G. Knepley 58675d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 58775d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 58875d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fEnd - fStart)*2 + (c - cStart)*3 + r; 58975d3a19aSMatthew G. Knepley PetscInt coneNew[2]; 59075d3a19aSMatthew G. Knepley PetscInt supportNew[2]; 59175d3a19aSMatthew G. Knepley 59275d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (cone[r] - fStart); 59375d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (cone[(r+1)%3] - fStart); 59475d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 59575d3a19aSMatthew G. Knepley #if 1 59675d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 59775d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 59875d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 59975d3a19aSMatthew G. Knepley } 60075d3a19aSMatthew G. Knepley #endif 60175d3a19aSMatthew G. Knepley supportNew[0] = (c - cStart)*4 + (r+1)%3; 60275d3a19aSMatthew G. Knepley supportNew[1] = (c - cStart)*4 + 3; 60375d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 60475d3a19aSMatthew G. Knepley #if 1 60575d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 60675d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 60775d3a19aSMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 60875d3a19aSMatthew G. Knepley } 60975d3a19aSMatthew G. Knepley #endif 61075d3a19aSMatthew G. Knepley } 61175d3a19aSMatthew G. Knepley } 61275d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 61375d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 61475d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 61575d3a19aSMatthew G. Knepley const PetscInt *support, *cone; 61675d3a19aSMatthew G. Knepley PetscInt size, s; 61775d3a19aSMatthew G. Knepley 61875d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 61975d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, v, &support);CHKERRQ(ierr); 62075d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 62175d3a19aSMatthew G. Knepley PetscInt r = 0; 62275d3a19aSMatthew G. Knepley 62375d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 62475d3a19aSMatthew G. Knepley if (cone[1] == v) r = 1; 62575d3a19aSMatthew G. Knepley supportRef[s] = fStartNew + (support[s] - fStart)*2 + r; 62675d3a19aSMatthew G. Knepley } 62775d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 62875d3a19aSMatthew G. Knepley #if 1 62975d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 63075d3a19aSMatthew G. Knepley for (p = 0; p < size; ++p) { 63175d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 63275d3a19aSMatthew G. Knepley } 63375d3a19aSMatthew G. Knepley #endif 63475d3a19aSMatthew G. Knepley } 63575d3a19aSMatthew G. Knepley /* Face vertices have 2 + cells*2 supports */ 63675d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 63775d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 63875d3a19aSMatthew G. Knepley const PetscInt *cone, *support; 63975d3a19aSMatthew G. Knepley PetscInt size, s; 64075d3a19aSMatthew G. Knepley 64175d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 64275d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 64375d3a19aSMatthew G. Knepley supportRef[0] = fStartNew + (f - fStart)*2 + 0; 64475d3a19aSMatthew G. Knepley supportRef[1] = fStartNew + (f - fStart)*2 + 1; 64575d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 64675d3a19aSMatthew G. Knepley PetscInt r = 0; 64775d3a19aSMatthew G. Knepley 64875d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 64975d3a19aSMatthew G. Knepley if (cone[1] == f) r = 1; 65075d3a19aSMatthew G. Knepley else if (cone[2] == f) r = 2; 65175d3a19aSMatthew G. Knepley supportRef[2+s*2+0] = fStartNew + (fEnd - fStart)*2 + (support[s] - cStart)*3 + (r+2)%3; 65275d3a19aSMatthew G. Knepley supportRef[2+s*2+1] = fStartNew + (fEnd - fStart)*2 + (support[s] - cStart)*3 + r; 65375d3a19aSMatthew G. Knepley } 65475d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 65575d3a19aSMatthew G. Knepley #if 1 65675d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 65775d3a19aSMatthew G. Knepley for (p = 0; p < 2+size*2; ++p) { 65875d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 65975d3a19aSMatthew G. Knepley } 66075d3a19aSMatthew G. Knepley #endif 66175d3a19aSMatthew G. Knepley } 66275d3a19aSMatthew G. Knepley ierr = PetscFree(supportRef);CHKERRQ(ierr); 66375d3a19aSMatthew G. Knepley break; 66475d3a19aSMatthew G. Knepley case 2: 66575d3a19aSMatthew G. Knepley /* Hex 2D */ 66675d3a19aSMatthew G. Knepley /* 66775d3a19aSMatthew G. Knepley 3---------2---------2 66875d3a19aSMatthew G. Knepley | | | 66975d3a19aSMatthew G. Knepley | D 2 C | 67075d3a19aSMatthew G. Knepley | | | 67175d3a19aSMatthew G. Knepley 3----3----0----1----1 67275d3a19aSMatthew G. Knepley | | | 67375d3a19aSMatthew G. Knepley | A 0 B | 67475d3a19aSMatthew G. Knepley | | | 67575d3a19aSMatthew G. Knepley 0---------0---------1 67675d3a19aSMatthew G. Knepley */ 67775d3a19aSMatthew G. Knepley /* All cells have 4 faces */ 67875d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 67975d3a19aSMatthew G. Knepley const PetscInt newp = (c - cStart)*4; 68075d3a19aSMatthew G. Knepley const PetscInt *cone, *ornt; 68175d3a19aSMatthew G. Knepley PetscInt coneNew[4], orntNew[4]; 68275d3a19aSMatthew G. Knepley 68375d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 68475d3a19aSMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 68575d3a19aSMatthew G. Knepley /* A quad */ 68675d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 1 : 0); 68775d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 68875d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 0; 68975d3a19aSMatthew G. Knepley orntNew[1] = 0; 69075d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 3; 69175d3a19aSMatthew G. Knepley orntNew[2] = -2; 69275d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (cone[3] - fStart)*2 + (ornt[3] < 0 ? 0 : 1); 69375d3a19aSMatthew G. Knepley orntNew[3] = ornt[3]; 69475d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 69575d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 69675d3a19aSMatthew G. Knepley #if 1 69775d3a19aSMatthew G. Knepley if ((newp+0 < cStartNew) || (newp+0 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+0, cStartNew, cEndNew); 69875d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 69975d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 70075d3a19aSMatthew G. Knepley } 70175d3a19aSMatthew G. Knepley #endif 70275d3a19aSMatthew G. Knepley /* B quad */ 70375d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 0 : 1); 70475d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 70575d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 1 : 0); 70675d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 70775d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 1; 70875d3a19aSMatthew G. Knepley orntNew[2] = 0; 70975d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 0; 71075d3a19aSMatthew G. Knepley orntNew[3] = -2; 71175d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 71275d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 71375d3a19aSMatthew G. Knepley #if 1 71475d3a19aSMatthew G. Knepley if ((newp+1 < cStartNew) || (newp+1 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+1, cStartNew, cEndNew); 71575d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 71675d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 71775d3a19aSMatthew G. Knepley } 71875d3a19aSMatthew G. Knepley #endif 71975d3a19aSMatthew G. Knepley /* C quad */ 72075d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 1; 72175d3a19aSMatthew G. Knepley orntNew[0] = -2; 72275d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 0 : 1); 72375d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 72475d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 1 : 0); 72575d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 72675d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 2; 72775d3a19aSMatthew G. Knepley orntNew[3] = 0; 72875d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+2, coneNew);CHKERRQ(ierr); 72975d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+2, orntNew);CHKERRQ(ierr); 73075d3a19aSMatthew G. Knepley #if 1 73175d3a19aSMatthew G. Knepley if ((newp+2 < cStartNew) || (newp+2 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+2, cStartNew, cEndNew); 73275d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 73375d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 73475d3a19aSMatthew G. Knepley } 73575d3a19aSMatthew G. Knepley #endif 73675d3a19aSMatthew G. Knepley /* D quad */ 73775d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 3; 73875d3a19aSMatthew G. Knepley orntNew[0] = 0; 73975d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + 2; 74075d3a19aSMatthew G. Knepley orntNew[1] = -2; 74175d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 0 : 1); 74275d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 74375d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (cone[3] - fStart)*2 + (ornt[3] < 0 ? 1 : 0); 74475d3a19aSMatthew G. Knepley orntNew[3] = ornt[3]; 74575d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+3, coneNew);CHKERRQ(ierr); 74675d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+3, orntNew);CHKERRQ(ierr); 74775d3a19aSMatthew G. Knepley #if 1 74875d3a19aSMatthew G. Knepley if ((newp+3 < cStartNew) || (newp+3 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+3, cStartNew, cEndNew); 74975d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 75075d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 75175d3a19aSMatthew G. Knepley } 75275d3a19aSMatthew G. Knepley #endif 75375d3a19aSMatthew G. Knepley } 75475d3a19aSMatthew G. Knepley /* Split faces have 2 vertices and the same cells as the parent */ 75575d3a19aSMatthew G. Knepley ierr = DMPlexGetMaxSizes(dm, NULL, &maxSupportSize);CHKERRQ(ierr); 75675d3a19aSMatthew G. Knepley ierr = PetscMalloc((2 + maxSupportSize*2) * sizeof(PetscInt), &supportRef);CHKERRQ(ierr); 75775d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 75875d3a19aSMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (f - fStart); 75975d3a19aSMatthew G. Knepley 76075d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 76175d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 76275d3a19aSMatthew G. Knepley const PetscInt *cone, *support; 76375d3a19aSMatthew G. Knepley PetscInt coneNew[2], coneSize, c, supportSize, s; 76475d3a19aSMatthew G. Knepley 76575d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 76675d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (cone[0] - vStart); 76775d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (cone[1] - vStart); 76875d3a19aSMatthew G. Knepley coneNew[(r+1)%2] = newv; 76975d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 77075d3a19aSMatthew G. Knepley #if 1 77175d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 77275d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 77375d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 77475d3a19aSMatthew G. Knepley } 77575d3a19aSMatthew G. Knepley #endif 77675d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 77775d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 77875d3a19aSMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 77975d3a19aSMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 78075d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 78175d3a19aSMatthew G. Knepley for (c = 0; c < coneSize; ++c) { 78275d3a19aSMatthew G. Knepley if (cone[c] == f) break; 78375d3a19aSMatthew G. Knepley } 78475d3a19aSMatthew G. Knepley supportRef[s] = cStartNew + (support[s] - cStart)*4 + (c+r)%4; 78575d3a19aSMatthew G. Knepley } 78675d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 78775d3a19aSMatthew G. Knepley #if 1 78875d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 78975d3a19aSMatthew G. Knepley for (p = 0; p < supportSize; ++p) { 79075d3a19aSMatthew G. Knepley if ((supportRef[p] < cStartNew) || (supportRef[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportRef[p], cStartNew, cEndNew); 79175d3a19aSMatthew G. Knepley } 79275d3a19aSMatthew G. Knepley #endif 79375d3a19aSMatthew G. Knepley } 79475d3a19aSMatthew G. Knepley } 79575d3a19aSMatthew G. Knepley /* Interior faces have 2 vertices and 2 cells */ 79675d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 79775d3a19aSMatthew G. Knepley const PetscInt *cone; 79875d3a19aSMatthew G. Knepley PetscInt coneNew[2], supportNew[2]; 79975d3a19aSMatthew G. Knepley 80075d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 80175d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 80275d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + r; 80375d3a19aSMatthew G. Knepley 80475d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (cone[r] - fStart); 80575d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (fEnd - fStart) + (c - cStart); 80675d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 80775d3a19aSMatthew G. Knepley #if 1 80875d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 80975d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 81075d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 81175d3a19aSMatthew G. Knepley } 81275d3a19aSMatthew G. Knepley #endif 81375d3a19aSMatthew G. Knepley supportNew[0] = (c - cStart)*4 + r; 81475d3a19aSMatthew G. Knepley supportNew[1] = (c - cStart)*4 + (r+1)%4; 81575d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 81675d3a19aSMatthew G. Knepley #if 1 81775d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 81875d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 81975d3a19aSMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 82075d3a19aSMatthew G. Knepley } 82175d3a19aSMatthew G. Knepley #endif 82275d3a19aSMatthew G. Knepley } 82375d3a19aSMatthew G. Knepley } 82475d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 82575d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 82675d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 82775d3a19aSMatthew G. Knepley const PetscInt *support, *cone; 82875d3a19aSMatthew G. Knepley PetscInt size, s; 82975d3a19aSMatthew G. Knepley 83075d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 83175d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, v, &support);CHKERRQ(ierr); 83275d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 83375d3a19aSMatthew G. Knepley PetscInt r = 0; 83475d3a19aSMatthew G. Knepley 83575d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 83675d3a19aSMatthew G. Knepley if (cone[1] == v) r = 1; 83775d3a19aSMatthew G. Knepley supportRef[s] = fStartNew + (support[s] - fStart)*2 + r; 83875d3a19aSMatthew G. Knepley } 83975d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 84075d3a19aSMatthew G. Knepley #if 1 84175d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 84275d3a19aSMatthew G. Knepley for (p = 0; p < size; ++p) { 84375d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 84475d3a19aSMatthew G. Knepley } 84575d3a19aSMatthew G. Knepley #endif 84675d3a19aSMatthew G. Knepley } 84775d3a19aSMatthew G. Knepley /* Face vertices have 2 + cells supports */ 84875d3a19aSMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 84975d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 85075d3a19aSMatthew G. Knepley const PetscInt *cone, *support; 85175d3a19aSMatthew G. Knepley PetscInt size, s; 85275d3a19aSMatthew G. Knepley 85375d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 85475d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 85575d3a19aSMatthew G. Knepley supportRef[0] = fStartNew + (f - fStart)*2 + 0; 85675d3a19aSMatthew G. Knepley supportRef[1] = fStartNew + (f - fStart)*2 + 1; 85775d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 85875d3a19aSMatthew G. Knepley PetscInt r = 0; 85975d3a19aSMatthew G. Knepley 86075d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 86175d3a19aSMatthew G. Knepley if (cone[1] == f) r = 1; 86275d3a19aSMatthew G. Knepley else if (cone[2] == f) r = 2; 86375d3a19aSMatthew G. Knepley else if (cone[3] == f) r = 3; 86475d3a19aSMatthew G. Knepley supportRef[2+s] = fStartNew + (fEnd - fStart)*2 + (support[s] - cStart)*4 + r; 86575d3a19aSMatthew G. Knepley } 86675d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 86775d3a19aSMatthew G. Knepley #if 1 86875d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 86975d3a19aSMatthew G. Knepley for (p = 0; p < 2+size; ++p) { 87075d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 87175d3a19aSMatthew G. Knepley } 87275d3a19aSMatthew G. Knepley #endif 87375d3a19aSMatthew G. Knepley } 87475d3a19aSMatthew G. Knepley /* Cell vertices have 4 supports */ 87575d3a19aSMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 87675d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (fEnd - fStart) + (c - cStart); 87775d3a19aSMatthew G. Knepley PetscInt supportNew[4]; 87875d3a19aSMatthew G. Knepley 87975d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 88075d3a19aSMatthew G. Knepley supportNew[r] = fStartNew + (fEnd - fStart)*2 + (c - cStart)*4 + r; 88175d3a19aSMatthew G. Knepley } 88275d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 88375d3a19aSMatthew G. Knepley } 88475d3a19aSMatthew G. Knepley break; 88575d3a19aSMatthew G. Knepley case 3: 88675d3a19aSMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 88775d3a19aSMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 88875d3a19aSMatthew G. Knepley if (fMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No face maximum specified in hybrid mesh"); 88975d3a19aSMatthew G. Knepley fMax = PetscMin(fEnd, fMax); 89075d3a19aSMatthew G. Knepley /* Interior cells have 3 faces */ 89175d3a19aSMatthew G. Knepley for (c = cStart; c < cMax; ++c) { 89275d3a19aSMatthew G. Knepley const PetscInt newp = cStartNew + (c - cStart)*4; 89375d3a19aSMatthew G. Knepley const PetscInt *cone, *ornt; 89475d3a19aSMatthew G. Knepley PetscInt coneNew[3], orntNew[3]; 89575d3a19aSMatthew G. Knepley 89675d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 89775d3a19aSMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 89875d3a19aSMatthew G. Knepley /* A triangle */ 89975d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 1 : 0); 90075d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 90175d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 2; 90275d3a19aSMatthew G. Knepley orntNew[1] = -2; 90375d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 0 : 1); 90475d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 90575d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 90675d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 90775d3a19aSMatthew G. Knepley #if 1 90875d3a19aSMatthew G. Knepley if ((newp+0 < cStartNew) || (newp+0 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+0, cStartNew, cEndNew); 90975d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 91075d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 91175d3a19aSMatthew G. Knepley } 91275d3a19aSMatthew G. Knepley #endif 91375d3a19aSMatthew G. Knepley /* B triangle */ 91475d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 0 : 1); 91575d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 91675d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 1 : 0); 91775d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 91875d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 0; 91975d3a19aSMatthew G. Knepley orntNew[2] = -2; 92075d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 92175d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 92275d3a19aSMatthew G. Knepley #if 1 92375d3a19aSMatthew G. Knepley if ((newp+1 < cStartNew) || (newp+1 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+1, cStartNew, cEndNew); 92475d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 92575d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 92675d3a19aSMatthew G. Knepley } 92775d3a19aSMatthew G. Knepley #endif 92875d3a19aSMatthew G. Knepley /* C triangle */ 92975d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 1; 93075d3a19aSMatthew G. Knepley orntNew[0] = -2; 93175d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 0 : 1); 93275d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 93375d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*2 + (ornt[2] < 0 ? 1 : 0); 93475d3a19aSMatthew G. Knepley orntNew[2] = ornt[2]; 93575d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+2, coneNew);CHKERRQ(ierr); 93675d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+2, orntNew);CHKERRQ(ierr); 93775d3a19aSMatthew G. Knepley #if 1 93875d3a19aSMatthew G. Knepley if ((newp+2 < cStartNew) || (newp+2 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+2, cStartNew, cEndNew); 93975d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 94075d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 94175d3a19aSMatthew G. Knepley } 94275d3a19aSMatthew G. Knepley #endif 94375d3a19aSMatthew G. Knepley /* D triangle */ 94475d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 0; 94575d3a19aSMatthew G. Knepley orntNew[0] = 0; 94675d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 1; 94775d3a19aSMatthew G. Knepley orntNew[1] = 0; 94875d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + 2; 94975d3a19aSMatthew G. Knepley orntNew[2] = 0; 95075d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+3, coneNew);CHKERRQ(ierr); 95175d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+3, orntNew);CHKERRQ(ierr); 95275d3a19aSMatthew G. Knepley #if 1 95375d3a19aSMatthew G. Knepley if ((newp+3 < cStartNew) || (newp+3 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+3, cStartNew, cEndNew); 95475d3a19aSMatthew G. Knepley for (p = 0; p < 3; ++p) { 95575d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 95675d3a19aSMatthew G. Knepley } 95775d3a19aSMatthew G. Knepley #endif 95875d3a19aSMatthew G. Knepley } 95975d3a19aSMatthew G. Knepley /* 96075d3a19aSMatthew G. Knepley 2----3----3 96175d3a19aSMatthew G. Knepley | | 96275d3a19aSMatthew G. Knepley | B | 96375d3a19aSMatthew G. Knepley | | 96475d3a19aSMatthew G. Knepley 0----4--- 1 96575d3a19aSMatthew G. Knepley | | 96675d3a19aSMatthew G. Knepley | A | 96775d3a19aSMatthew G. Knepley | | 96875d3a19aSMatthew G. Knepley 0----2----1 96975d3a19aSMatthew G. Knepley */ 97075d3a19aSMatthew G. Knepley /* Hybrid cells have 4 faces */ 97175d3a19aSMatthew G. Knepley for (c = cMax; c < cEnd; ++c) { 97275d3a19aSMatthew G. Knepley const PetscInt newp = cStartNew + (cMax - cStart)*4 + (c - cMax)*2; 97375d3a19aSMatthew G. Knepley const PetscInt *cone, *ornt; 97475d3a19aSMatthew G. Knepley PetscInt coneNew[4], orntNew[4]; 97575d3a19aSMatthew G. Knepley 97675d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 97775d3a19aSMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 97875d3a19aSMatthew G. Knepley /* A quad */ 97975d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 1 : 0); 98075d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 98175d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 1 : 0); 98275d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 98375d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (cone[2] - fMax); 98475d3a19aSMatthew G. Knepley orntNew[2] = 0; 98575d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (fEnd - fMax) + (c - cMax); 98675d3a19aSMatthew G. Knepley orntNew[3] = 0; 98775d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 98875d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 98975d3a19aSMatthew G. Knepley #if 1 99075d3a19aSMatthew G. Knepley if ((newp+0 < cStartNew) || (newp+0 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+0, cStartNew, cEndNew); 99175d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 99275d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 99375d3a19aSMatthew G. Knepley } 99475d3a19aSMatthew G. Knepley #endif 99575d3a19aSMatthew G. Knepley /* B quad */ 99675d3a19aSMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*2 + (ornt[0] < 0 ? 0 : 1); 99775d3a19aSMatthew G. Knepley orntNew[0] = ornt[0]; 99875d3a19aSMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*2 + (ornt[1] < 0 ? 0 : 1); 99975d3a19aSMatthew G. Knepley orntNew[1] = ornt[1]; 100075d3a19aSMatthew G. Knepley coneNew[2] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (fEnd - fMax) + (c - cMax); 100175d3a19aSMatthew G. Knepley orntNew[2] = 0; 100275d3a19aSMatthew G. Knepley coneNew[3] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (cone[3] - fMax); 100375d3a19aSMatthew G. Knepley orntNew[3] = 0; 100475d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 100575d3a19aSMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 100675d3a19aSMatthew G. Knepley #if 1 100775d3a19aSMatthew G. Knepley if ((newp+1 < cStartNew) || (newp+1 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+1, cStartNew, cEndNew); 100875d3a19aSMatthew G. Knepley for (p = 0; p < 4; ++p) { 100975d3a19aSMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 101075d3a19aSMatthew G. Knepley } 101175d3a19aSMatthew G. Knepley #endif 101275d3a19aSMatthew G. Knepley } 101375d3a19aSMatthew G. Knepley /* Interior split faces have 2 vertices and the same cells as the parent */ 101475d3a19aSMatthew G. Knepley ierr = DMPlexGetMaxSizes(dm, NULL, &maxSupportSize);CHKERRQ(ierr); 101575d3a19aSMatthew G. Knepley ierr = PetscMalloc((2 + maxSupportSize*2) * sizeof(PetscInt), &supportRef);CHKERRQ(ierr); 101675d3a19aSMatthew G. Knepley for (f = fStart; f < fMax; ++f) { 101775d3a19aSMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (f - fStart); 101875d3a19aSMatthew G. Knepley 101975d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 102075d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*2 + r; 1021*297d2bf4SMatthew G. Knepley const PetscInt *cone, *ornt, *support; 102275d3a19aSMatthew G. Knepley PetscInt coneNew[2], coneSize, c, supportSize, s; 102375d3a19aSMatthew G. Knepley 102475d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 102575d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (cone[0] - vStart); 102675d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (cone[1] - vStart); 102775d3a19aSMatthew G. Knepley coneNew[(r+1)%2] = newv; 102875d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 102975d3a19aSMatthew G. Knepley #if 1 103075d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 103175d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 103275d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 103375d3a19aSMatthew G. Knepley } 103475d3a19aSMatthew G. Knepley #endif 103575d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 103675d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 103775d3a19aSMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 103875d3a19aSMatthew G. Knepley if (support[s] >= cMax) { 103975d3a19aSMatthew G. Knepley supportRef[s] = cStartNew + (cMax - cStart)*4 + (support[s] - cMax)*2 + r; 104075d3a19aSMatthew G. Knepley } else { 104175d3a19aSMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 104275d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1043*297d2bf4SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 104475d3a19aSMatthew G. Knepley for (c = 0; c < coneSize; ++c) { 104575d3a19aSMatthew G. Knepley if (cone[c] == f) break; 104675d3a19aSMatthew G. Knepley } 1047*297d2bf4SMatthew G. Knepley supportRef[s] = cStartNew + (support[s] - cStart)*4 + (ornt[c] < 0 ? (c+1-r)%3 : (c+r)%3); 104875d3a19aSMatthew G. Knepley } 104975d3a19aSMatthew G. Knepley } 105075d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 105175d3a19aSMatthew G. Knepley #if 1 105275d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 105375d3a19aSMatthew G. Knepley for (p = 0; p < supportSize; ++p) { 105475d3a19aSMatthew G. Knepley if ((supportRef[p] < cStartNew) || (supportRef[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportRef[p], cStartNew, cEndNew); 105575d3a19aSMatthew G. Knepley } 105675d3a19aSMatthew G. Knepley #endif 105775d3a19aSMatthew G. Knepley } 105875d3a19aSMatthew G. Knepley } 105975d3a19aSMatthew G. Knepley /* Interior cell faces have 2 vertices and 2 cells */ 106075d3a19aSMatthew G. Knepley for (c = cStart; c < cMax; ++c) { 106175d3a19aSMatthew G. Knepley const PetscInt *cone; 106275d3a19aSMatthew G. Knepley 106375d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 106475d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 106575d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (c - cStart)*3 + r; 106675d3a19aSMatthew G. Knepley PetscInt coneNew[2]; 106775d3a19aSMatthew G. Knepley PetscInt supportNew[2]; 106875d3a19aSMatthew G. Knepley 106975d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (cone[r] - fStart); 107075d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (cone[(r+1)%3] - fStart); 107175d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 107275d3a19aSMatthew G. Knepley #if 1 107375d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 107475d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 107575d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 107675d3a19aSMatthew G. Knepley } 107775d3a19aSMatthew G. Knepley #endif 107875d3a19aSMatthew G. Knepley supportNew[0] = (c - cStart)*4 + (r+1)%3; 107975d3a19aSMatthew G. Knepley supportNew[1] = (c - cStart)*4 + 3; 108075d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 108175d3a19aSMatthew G. Knepley #if 1 108275d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 108375d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 108475d3a19aSMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 108575d3a19aSMatthew G. Knepley } 108675d3a19aSMatthew G. Knepley #endif 108775d3a19aSMatthew G. Knepley } 108875d3a19aSMatthew G. Knepley } 108975d3a19aSMatthew G. Knepley /* Interior hybrid faces have 2 vertices and the same cells */ 109075d3a19aSMatthew G. Knepley for (f = fMax; f < fEnd; ++f) { 109175d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (f - fMax); 109275d3a19aSMatthew G. Knepley const PetscInt *cone; 109375d3a19aSMatthew G. Knepley const PetscInt *support; 109475d3a19aSMatthew G. Knepley PetscInt coneNew[2]; 109575d3a19aSMatthew G. Knepley PetscInt supportNew[2]; 109675d3a19aSMatthew G. Knepley PetscInt size, s, r; 109775d3a19aSMatthew G. Knepley 109875d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 109975d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (cone[0] - vStart); 110075d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (cone[1] - vStart); 110175d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 110275d3a19aSMatthew G. Knepley #if 1 110375d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 110475d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 110575d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 110675d3a19aSMatthew G. Knepley } 110775d3a19aSMatthew G. Knepley #endif 110875d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 110975d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 111075d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 111175d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 111275d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 111375d3a19aSMatthew G. Knepley if (cone[r+2] == f) break; 111475d3a19aSMatthew G. Knepley } 111575d3a19aSMatthew G. Knepley supportNew[s] = (cMax - cStart)*4 + (support[s] - cMax)*2 + r; 111675d3a19aSMatthew G. Knepley } 111775d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 111875d3a19aSMatthew G. Knepley #if 1 111975d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 112075d3a19aSMatthew G. Knepley for (p = 0; p < size; ++p) { 112175d3a19aSMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 112275d3a19aSMatthew G. Knepley } 112375d3a19aSMatthew G. Knepley #endif 112475d3a19aSMatthew G. Knepley } 112575d3a19aSMatthew G. Knepley /* Cell hybrid faces have 2 vertices and 2 cells */ 112675d3a19aSMatthew G. Knepley for (c = cMax; c < cEnd; ++c) { 112775d3a19aSMatthew G. Knepley const PetscInt newp = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (fEnd - fMax) + (c - cMax); 112875d3a19aSMatthew G. Knepley const PetscInt *cone; 112975d3a19aSMatthew G. Knepley PetscInt coneNew[2]; 113075d3a19aSMatthew G. Knepley PetscInt supportNew[2]; 113175d3a19aSMatthew G. Knepley 113275d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 113375d3a19aSMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (cone[0] - fStart); 113475d3a19aSMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (cone[1] - fStart); 113575d3a19aSMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 113675d3a19aSMatthew G. Knepley #if 1 113775d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 113875d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 113975d3a19aSMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 114075d3a19aSMatthew G. Knepley } 114175d3a19aSMatthew G. Knepley #endif 114275d3a19aSMatthew G. Knepley supportNew[0] = (cMax - cStart)*4 + (c - cMax)*2 + 0; 114375d3a19aSMatthew G. Knepley supportNew[1] = (cMax - cStart)*4 + (c - cMax)*2 + 1; 114475d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 114575d3a19aSMatthew G. Knepley #if 1 114675d3a19aSMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 114775d3a19aSMatthew G. Knepley for (p = 0; p < 2; ++p) { 114875d3a19aSMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 114975d3a19aSMatthew G. Knepley } 115075d3a19aSMatthew G. Knepley #endif 115175d3a19aSMatthew G. Knepley } 115275d3a19aSMatthew G. Knepley /* Old vertices have identical supports */ 115375d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 115475d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 115575d3a19aSMatthew G. Knepley const PetscInt *support, *cone; 115675d3a19aSMatthew G. Knepley PetscInt size, s; 115775d3a19aSMatthew G. Knepley 115875d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 115975d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, v, &support);CHKERRQ(ierr); 116075d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 116175d3a19aSMatthew G. Knepley if (support[s] >= fMax) { 116275d3a19aSMatthew G. Knepley supportRef[s] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (support[s] - fMax); 116375d3a19aSMatthew G. Knepley } else { 116475d3a19aSMatthew G. Knepley PetscInt r = 0; 116575d3a19aSMatthew G. Knepley 116675d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 116775d3a19aSMatthew G. Knepley if (cone[1] == v) r = 1; 116875d3a19aSMatthew G. Knepley supportRef[s] = fStartNew + (support[s] - fStart)*2 + r; 116975d3a19aSMatthew G. Knepley } 117075d3a19aSMatthew G. Knepley } 117175d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 117275d3a19aSMatthew G. Knepley #if 1 117375d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 117475d3a19aSMatthew G. Knepley for (p = 0; p < size; ++p) { 117575d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 117675d3a19aSMatthew G. Knepley } 117775d3a19aSMatthew G. Knepley #endif 117875d3a19aSMatthew G. Knepley } 117975d3a19aSMatthew G. Knepley /* Face vertices have 2 + (2 interior, 1 hybrid) supports */ 118075d3a19aSMatthew G. Knepley for (f = fStart; f < fMax; ++f) { 118175d3a19aSMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (f - fStart); 118275d3a19aSMatthew G. Knepley const PetscInt *cone, *support; 118375d3a19aSMatthew G. Knepley PetscInt size, newSize = 2, s; 118475d3a19aSMatthew G. Knepley 118575d3a19aSMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &size);CHKERRQ(ierr); 118675d3a19aSMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 118775d3a19aSMatthew G. Knepley supportRef[0] = fStartNew + (f - fStart)*2 + 0; 118875d3a19aSMatthew G. Knepley supportRef[1] = fStartNew + (f - fStart)*2 + 1; 118975d3a19aSMatthew G. Knepley for (s = 0; s < size; ++s) { 119075d3a19aSMatthew G. Knepley PetscInt r = 0; 119175d3a19aSMatthew G. Knepley 119275d3a19aSMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 119375d3a19aSMatthew G. Knepley if (support[s] >= cMax) { 119475d3a19aSMatthew G. Knepley supportRef[newSize+0] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (fEnd - fMax) + (support[s] - cMax); 119575d3a19aSMatthew G. Knepley 119675d3a19aSMatthew G. Knepley newSize += 1; 119775d3a19aSMatthew G. Knepley } else { 119875d3a19aSMatthew G. Knepley if (cone[1] == f) r = 1; 119975d3a19aSMatthew G. Knepley else if (cone[2] == f) r = 2; 120075d3a19aSMatthew G. Knepley supportRef[newSize+0] = fStartNew + (fMax - fStart)*2 + (support[s] - cStart)*3 + (r+2)%3; 120175d3a19aSMatthew G. Knepley supportRef[newSize+1] = fStartNew + (fMax - fStart)*2 + (support[s] - cStart)*3 + r; 120275d3a19aSMatthew G. Knepley 120375d3a19aSMatthew G. Knepley newSize += 2; 120475d3a19aSMatthew G. Knepley } 120575d3a19aSMatthew G. Knepley } 120675d3a19aSMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 120775d3a19aSMatthew G. Knepley #if 1 120875d3a19aSMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 120975d3a19aSMatthew G. Knepley for (p = 0; p < newSize; ++p) { 121075d3a19aSMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 121175d3a19aSMatthew G. Knepley } 121275d3a19aSMatthew G. Knepley #endif 121375d3a19aSMatthew G. Knepley } 121475d3a19aSMatthew G. Knepley ierr = PetscFree(supportRef);CHKERRQ(ierr); 121575d3a19aSMatthew G. Knepley break; 1216b5da9499SMatthew G. Knepley case 5: 1217b5da9499SMatthew G. Knepley /* Simplicial 3D */ 1218b5da9499SMatthew G. Knepley /* All cells have 4 faces: Tet face order is prescribed in DMPlexGetFaces_Internal() */ 1219b5da9499SMatthew G. Knepley ierr = DMPlexGetRawFaces_Internal(dm, 3, 4, cellInd, NULL, NULL, &faces);CHKERRQ(ierr); 1220b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 1221b5da9499SMatthew G. Knepley const PetscInt newp = cStartNew + (c - cStart)*8; 1222b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt; 1223b5da9499SMatthew G. Knepley PetscInt coneNew[4], orntNew[4]; 1224b5da9499SMatthew G. Knepley 1225b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 1226b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 1227b5da9499SMatthew G. Knepley /* A tetrahedron: {0, a, c, d} */ 1228b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*4 + (ornt[0] < 0 ? (-(ornt[0]+1)+1)%3 : ornt[0]); /* A */ 1229b5da9499SMatthew G. Knepley orntNew[0] = ornt[0]; 1230b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*4 + (ornt[1] < 0 ? (-(ornt[1]+1)+1)%3 : ornt[1]); /* A */ 1231b5da9499SMatthew G. Knepley orntNew[1] = ornt[1]; 1232b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*4 + (ornt[2] < 0 ? (-(ornt[2]+1)+1)%3 : ornt[2]); /* A */ 1233b5da9499SMatthew G. Knepley orntNew[2] = ornt[2]; 1234b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 0; 1235b5da9499SMatthew G. Knepley orntNew[3] = 0; 1236b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 1237b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 1238b5da9499SMatthew G. Knepley #if 1 1239b5da9499SMatthew G. Knepley if ((newp+0 < cStartNew) || (newp+0 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+0, cStartNew, cEndNew); 1240b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1241b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1242b5da9499SMatthew G. Knepley } 1243b5da9499SMatthew G. Knepley #endif 1244b5da9499SMatthew G. Knepley /* B tetrahedron: {a, 1, b, e} */ 1245b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*4 + (ornt[0] < 0 ? (-(ornt[0]+1)+0)%3 : (ornt[0]+1)%3); /* B */ 1246b5da9499SMatthew G. Knepley orntNew[0] = ornt[0]; 1247b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*4 + (ornt[1] < 0 ? (-(ornt[1]+1)+2)%3 : (ornt[1]+2)%3); /* C */ 1248b5da9499SMatthew G. Knepley orntNew[1] = ornt[1]; 1249b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 1; 1250b5da9499SMatthew G. Knepley orntNew[2] = 0; 1251b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (cone[3] - fStart)*4 + (ornt[3] < 0 ? (-(ornt[3]+1)+0)%3 : (ornt[3]+1)%3); /* B */ 1252b5da9499SMatthew G. Knepley orntNew[3] = ornt[3]; 1253b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 1254b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 1255b5da9499SMatthew G. Knepley #if 1 1256b5da9499SMatthew G. Knepley if ((newp+1 < cStartNew) || (newp+1 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+1, cStartNew, cEndNew); 1257b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1258b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1259b5da9499SMatthew G. Knepley } 1260b5da9499SMatthew G. Knepley #endif 1261b5da9499SMatthew G. Knepley /* C tetrahedron: {c, b, 2, f} */ 1262b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (cone[0] - fStart)*4 + (ornt[0] < 0 ? (-(ornt[0]+1)+2)%3 : (ornt[0]+2)%3); /* C */ 1263b5da9499SMatthew G. Knepley orntNew[0] = ornt[0]; 1264b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 2; 1265b5da9499SMatthew G. Knepley orntNew[1] = 0; 1266b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*4 + (ornt[2] < 0 ? (-(ornt[2]+1)+0)%3 : (ornt[2]+1)%3); /* B */ 1267b5da9499SMatthew G. Knepley orntNew[2] = ornt[2]; 1268b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (cone[3] - fStart)*4 + (ornt[3] < 0 ? (-(ornt[3]+1)+1)%3 : (ornt[3]+0)%3); /* A */ 1269b5da9499SMatthew G. Knepley orntNew[3] = ornt[3]; 1270b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+2, coneNew);CHKERRQ(ierr); 1271b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+2, orntNew);CHKERRQ(ierr); 1272b5da9499SMatthew G. Knepley #if 1 1273b5da9499SMatthew G. Knepley if ((newp+2 < cStartNew) || (newp+2 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+2, cStartNew, cEndNew); 1274b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1275b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1276b5da9499SMatthew G. Knepley } 1277b5da9499SMatthew G. Knepley #endif 1278b5da9499SMatthew G. Knepley /* D tetrahedron: {d, e, f, 3} */ 1279b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 3; 1280b5da9499SMatthew G. Knepley orntNew[0] = 0; 1281b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (cone[1] - fStart)*4 + (ornt[1] < 0 ? (-(ornt[1]+1)+0)%3 : (ornt[1]+1)%3); /* B */ 1282b5da9499SMatthew G. Knepley orntNew[1] = ornt[1]; 1283b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*4 + (ornt[2] < 0 ? (-(ornt[2]+1)+2)%3 : (ornt[2]+2)%3); /* C */ 1284b5da9499SMatthew G. Knepley orntNew[2] = ornt[2]; 1285b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (cone[3] - fStart)*4 + (ornt[3] < 0 ? (-(ornt[3]+1)+2)%3 : (ornt[3]+2)%3); /* C */ 1286b5da9499SMatthew G. Knepley orntNew[3] = ornt[3]; 1287b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+3, coneNew);CHKERRQ(ierr); 1288b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+3, orntNew);CHKERRQ(ierr); 1289b5da9499SMatthew G. Knepley #if 1 1290b5da9499SMatthew G. Knepley if ((newp+3 < cStartNew) || (newp+3 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+3, cStartNew, cEndNew); 1291b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1292b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1293b5da9499SMatthew G. Knepley } 1294b5da9499SMatthew G. Knepley #endif 1295b5da9499SMatthew G. Knepley /* A' tetrahedron: {d, a, c, f} */ 1296b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 0; 1297b5da9499SMatthew G. Knepley orntNew[0] = -3; 1298b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 4; 1299b5da9499SMatthew G. Knepley orntNew[1] = 0; 1300b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (cone[2] - fStart)*4 + 3; 1301b5da9499SMatthew G. Knepley orntNew[2] = ornt[2] < 0 ? -((-(ornt[2]+1)+2)%3+1) : (ornt[2]+2)%3; 1302b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 5; 1303b5da9499SMatthew G. Knepley orntNew[3] = 0; 1304b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+4, coneNew);CHKERRQ(ierr); 1305b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+4, orntNew);CHKERRQ(ierr); 1306b5da9499SMatthew G. Knepley #if 1 1307b5da9499SMatthew G. Knepley if ((newp+4 < cStartNew) || (newp+4 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+4, cStartNew, cEndNew); 1308b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1309b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1310b5da9499SMatthew G. Knepley } 1311b5da9499SMatthew G. Knepley #endif 1312b5da9499SMatthew G. Knepley /* B' tetrahedron: {e, b, a, f} */ 1313b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 1; 1314b5da9499SMatthew G. Knepley orntNew[0] = -3; 1315b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (cone[3] - fStart)*4 + 3; 1316b5da9499SMatthew G. Knepley orntNew[1] = ornt[3] < 0 ? -((-(ornt[3]+1)+1)%3+1) : (ornt[3]+1)%3; 1317b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 6; 1318b5da9499SMatthew G. Knepley orntNew[2] = 0; 1319b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 7; 1320b5da9499SMatthew G. Knepley orntNew[3] = 0; 1321b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+5, coneNew);CHKERRQ(ierr); 1322b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+5, orntNew);CHKERRQ(ierr); 1323b5da9499SMatthew G. Knepley #if 1 1324b5da9499SMatthew G. Knepley if ((newp+5 < cStartNew) || (newp+5 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+5, cStartNew, cEndNew); 1325b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1326b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1327b5da9499SMatthew G. Knepley } 1328b5da9499SMatthew G. Knepley #endif 1329b5da9499SMatthew G. Knepley /* C' tetrahedron: {b, f, c, a} */ 1330b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 2; 1331b5da9499SMatthew G. Knepley orntNew[0] = -3; 1332b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 7; 1333b5da9499SMatthew G. Knepley orntNew[1] = -2; 1334b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (cone[0] - fStart)*4 + 3; 1335b5da9499SMatthew G. Knepley orntNew[2] = ornt[0] < 0 ? (-(ornt[0]+1)+1)%3 : -((ornt[0]+1)%3+1); 1336b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 5; 1337b5da9499SMatthew G. Knepley orntNew[3] = -1; 1338b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+6, coneNew);CHKERRQ(ierr); 1339b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+6, orntNew);CHKERRQ(ierr); 1340b5da9499SMatthew G. Knepley #if 1 1341b5da9499SMatthew G. Knepley if ((newp+6 < cStartNew) || (newp+6 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+6, cStartNew, cEndNew); 1342b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1343b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1344b5da9499SMatthew G. Knepley } 1345b5da9499SMatthew G. Knepley #endif 1346b5da9499SMatthew G. Knepley /* D' tetrahedron: {f, e, d, a} */ 1347b5da9499SMatthew G. Knepley coneNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 3; 1348b5da9499SMatthew G. Knepley orntNew[0] = -3; 1349b5da9499SMatthew G. Knepley coneNew[1] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 6; 1350b5da9499SMatthew G. Knepley orntNew[1] = -3; 1351b5da9499SMatthew G. Knepley coneNew[2] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 4; 1352b5da9499SMatthew G. Knepley orntNew[2] = -2; 1353b5da9499SMatthew G. Knepley coneNew[3] = fStartNew + (cone[1] - fStart)*4 + 3; 1354b5da9499SMatthew G. Knepley orntNew[3] = ornt[2]; 1355b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+7, coneNew);CHKERRQ(ierr); 1356b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+7, orntNew);CHKERRQ(ierr); 1357b5da9499SMatthew G. Knepley #if 1 1358b5da9499SMatthew G. Knepley if ((newp+7 < cStartNew) || (newp+7 >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", newp+7, cStartNew, cEndNew); 1359b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1360b5da9499SMatthew G. Knepley if ((coneNew[p] < fStartNew) || (coneNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", coneNew[p], fStartNew, fEndNew); 1361b5da9499SMatthew G. Knepley } 1362b5da9499SMatthew G. Knepley #endif 1363b5da9499SMatthew G. Knepley } 1364b5da9499SMatthew G. Knepley /* Split faces have 3 edges and the same cells as the parent */ 1365b5da9499SMatthew G. Knepley ierr = DMPlexGetMaxSizes(dm, NULL, &maxSupportSize);CHKERRQ(ierr); 1366b5da9499SMatthew G. Knepley ierr = PetscMalloc((2 + maxSupportSize*2) * sizeof(PetscInt), &supportRef);CHKERRQ(ierr); 1367b5da9499SMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 1368b5da9499SMatthew G. Knepley const PetscInt newp = fStartNew + (f - fStart)*4; 1369b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt, *support; 1370b5da9499SMatthew G. Knepley PetscInt coneNew[3], orntNew[3], coneSize, supportSize, s; 1371b5da9499SMatthew G. Knepley 1372b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 1373b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, f, &ornt);CHKERRQ(ierr); 1374b5da9499SMatthew G. Knepley /* A triangle */ 1375b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (cone[0] - eStart)*2 + (ornt[0] < 0 ? 1 : 0); 1376b5da9499SMatthew G. Knepley orntNew[0] = ornt[0]; 1377b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 2; 1378b5da9499SMatthew G. Knepley orntNew[1] = -2; 1379b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (cone[2] - eStart)*2 + (ornt[2] < 0 ? 0 : 1); 1380b5da9499SMatthew G. Knepley orntNew[2] = ornt[2]; 1381b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+0, coneNew);CHKERRQ(ierr); 1382b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+0, orntNew);CHKERRQ(ierr); 1383b5da9499SMatthew G. Knepley #if 1 1384b5da9499SMatthew G. Knepley if ((newp+0 < fStartNew) || (newp+0 >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp+0, fStartNew, fEndNew); 1385b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1386b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1387b5da9499SMatthew G. Knepley } 1388b5da9499SMatthew G. Knepley #endif 1389b5da9499SMatthew G. Knepley /* B triangle */ 1390b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (cone[0] - eStart)*2 + (ornt[0] < 0 ? 0 : 1); 1391b5da9499SMatthew G. Knepley orntNew[0] = ornt[0]; 1392b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (cone[1] - eStart)*2 + (ornt[1] < 0 ? 1 : 0); 1393b5da9499SMatthew G. Knepley orntNew[1] = ornt[1]; 1394b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 0; 1395b5da9499SMatthew G. Knepley orntNew[2] = -2; 1396b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+1, coneNew);CHKERRQ(ierr); 1397b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+1, orntNew);CHKERRQ(ierr); 1398b5da9499SMatthew G. Knepley #if 1 1399b5da9499SMatthew G. Knepley if ((newp+1 < fStartNew) || (newp+1 >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp+1, fStartNew, fEndNew); 1400b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1401b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1402b5da9499SMatthew G. Knepley } 1403b5da9499SMatthew G. Knepley #endif 1404b5da9499SMatthew G. Knepley /* C triangle */ 1405b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 1; 1406b5da9499SMatthew G. Knepley orntNew[0] = -2; 1407b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (cone[1] - eStart)*2 + (ornt[1] < 0 ? 0 : 1); 1408b5da9499SMatthew G. Knepley orntNew[1] = ornt[1]; 1409b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (cone[2] - eStart)*2 + (ornt[2] < 0 ? 1 : 0); 1410b5da9499SMatthew G. Knepley orntNew[2] = ornt[2]; 1411b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+2, coneNew);CHKERRQ(ierr); 1412b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+2, orntNew);CHKERRQ(ierr); 1413b5da9499SMatthew G. Knepley #if 1 1414b5da9499SMatthew G. Knepley if ((newp+2 < fStartNew) || (newp+2 >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp+2, fStartNew, fEndNew); 1415b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1416b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1417b5da9499SMatthew G. Knepley } 1418b5da9499SMatthew G. Knepley #endif 1419b5da9499SMatthew G. Knepley /* D triangle */ 1420b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 0; 1421b5da9499SMatthew G. Knepley orntNew[0] = 0; 1422b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 1; 1423b5da9499SMatthew G. Knepley orntNew[1] = 0; 1424b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + 2; 1425b5da9499SMatthew G. Knepley orntNew[2] = 0; 1426b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp+3, coneNew);CHKERRQ(ierr); 1427b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp+3, orntNew);CHKERRQ(ierr); 1428b5da9499SMatthew G. Knepley #if 1 1429b5da9499SMatthew G. Knepley if ((newp+3 < fStartNew) || (newp+3 >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp+3, fStartNew, fEndNew); 1430b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1431b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1432b5da9499SMatthew G. Knepley } 1433b5da9499SMatthew G. Knepley #endif 1434b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 1435b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 1436b5da9499SMatthew G. Knepley for (r = 0; r < 4; ++r) { 1437b5da9499SMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 1438b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 1439b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1440b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 1441b5da9499SMatthew G. Knepley for (c = 0; c < coneSize; ++c) { 1442b5da9499SMatthew G. Knepley if (cone[c] == f) break; 1443b5da9499SMatthew G. Knepley } 1444b5da9499SMatthew G. Knepley supportRef[s] = cStartNew + (support[s] - cStart)*8 + (r==3 ? (c+2)%4 + 4 : (ornt[c] < 0 ? faces[c*3+(-(ornt[c]+1)+1+3-r)%3] : faces[c*3+r])); 1445b5da9499SMatthew G. Knepley } 1446b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp+r, supportRef);CHKERRQ(ierr); 1447b5da9499SMatthew G. Knepley #if 1 1448b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1449b5da9499SMatthew G. Knepley for (p = 0; p < supportSize; ++p) { 1450b5da9499SMatthew G. Knepley if ((supportRef[p] < cStartNew) || (supportRef[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportRef[p], cStartNew, cEndNew); 1451b5da9499SMatthew G. Knepley } 1452b5da9499SMatthew G. Knepley #endif 1453b5da9499SMatthew G. Knepley } 1454b5da9499SMatthew G. Knepley } 1455b5da9499SMatthew G. Knepley /* Interior faces have 3 edges and 2 cells */ 1456b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 1457b5da9499SMatthew G. Knepley PetscInt newp = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8; 1458b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt; 1459b5da9499SMatthew G. Knepley PetscInt coneNew[3], orntNew[3]; 1460b5da9499SMatthew G. Knepley PetscInt supportNew[2]; 1461b5da9499SMatthew G. Knepley 1462b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 1463b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 1464b5da9499SMatthew G. Knepley /* Face A: {c, a, d} */ 1465b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[0] - fStart)*3 + (ornt[0] < 0 ? (-(ornt[0]+1)+0)%3 : (ornt[0]+2)%3); 1466b5da9499SMatthew G. Knepley orntNew[0] = ornt[0] < 0 ? -2 : 0; 1467b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (cone[1] - fStart)*3 + (ornt[1] < 0 ? (-(ornt[1]+1)+0)%3 : (ornt[1]+2)%3); 1468b5da9499SMatthew G. Knepley orntNew[1] = ornt[1] < 0 ? -2 : 0; 1469b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[2] - fStart)*3 + (ornt[2] < 0 ? (-(ornt[2]+1)+0)%3 : (ornt[2]+2)%3); 1470b5da9499SMatthew G. Knepley orntNew[2] = ornt[2] < 0 ? -2 : 0; 1471b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1472b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1473b5da9499SMatthew G. Knepley #if 1 1474b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1475b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1476b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1477b5da9499SMatthew G. Knepley } 1478b5da9499SMatthew G. Knepley #endif 1479b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 0; 1480b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 0+4; 1481b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1482b5da9499SMatthew G. Knepley #if 1 1483b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1484b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1485b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1486b5da9499SMatthew G. Knepley } 1487b5da9499SMatthew G. Knepley #endif 1488b5da9499SMatthew G. Knepley ++newp; 1489b5da9499SMatthew G. Knepley /* Face B: {a, b, e} */ 1490b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[0] - fStart)*3 + (ornt[0] < 0 ? (-(ornt[0]+1)+2)%3 : (ornt[0]+0)%3); 1491b5da9499SMatthew G. Knepley orntNew[0] = ornt[0] < 0 ? -2 : 0; 1492b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (cone[3] - fStart)*3 + (ornt[3] < 0 ? (-(ornt[3]+1)+2)%3 : (ornt[3]+0)%3); 1493b5da9499SMatthew G. Knepley orntNew[1] = ornt[3] < 0 ? -2 : 0; 1494b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[1] - fStart)*3 + (ornt[1] < 0 ? (-(ornt[1]+1)+1)%3 : (ornt[1]+1)%3); 1495b5da9499SMatthew G. Knepley orntNew[2] = ornt[1] < 0 ? -2 : 0; 1496b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1497b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1498b5da9499SMatthew G. Knepley #if 1 1499b5da9499SMatthew G. Knepley if ((newp+1 < fStartNew) || (newp+1 >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp+1, fStartNew, fEndNew); 1500b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1501b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1502b5da9499SMatthew G. Knepley } 1503b5da9499SMatthew G. Knepley #endif 1504b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 1; 1505b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 1+4; 1506b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1507b5da9499SMatthew G. Knepley #if 1 1508b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1509b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1510b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1511b5da9499SMatthew G. Knepley } 1512b5da9499SMatthew G. Knepley #endif 1513b5da9499SMatthew G. Knepley ++newp; 1514b5da9499SMatthew G. Knepley /* Face C: {c, f, b} */ 1515b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[2] - fStart)*3 + (ornt[2] < 0 ? (-(ornt[2]+1)+2)%3 : (ornt[2]+0)%3); 1516b5da9499SMatthew G. Knepley orntNew[0] = ornt[2] < 0 ? -2 : 0; 1517b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (cone[3] - fStart)*3 + (ornt[3] < 0 ? (-(ornt[3]+1)+0)%3 : (ornt[3]+2)%3); 1518b5da9499SMatthew G. Knepley orntNew[1] = ornt[3] < 0 ? -2 : 0; 1519b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[0] - fStart)*3 + (ornt[0] < 0 ? (-(ornt[0]+1)+1)%3 : (ornt[0]+1)%3); 1520b5da9499SMatthew G. Knepley orntNew[2] = ornt[0] < 0 ? -2 : 0; 1521b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1522b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1523b5da9499SMatthew G. Knepley #if 1 1524b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1525b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1526b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1527b5da9499SMatthew G. Knepley } 1528b5da9499SMatthew G. Knepley #endif 1529b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 2; 1530b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 2+4; 1531b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1532b5da9499SMatthew G. Knepley #if 1 1533b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1534b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1535b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1536b5da9499SMatthew G. Knepley } 1537b5da9499SMatthew G. Knepley #endif 1538b5da9499SMatthew G. Knepley ++newp; 1539b5da9499SMatthew G. Knepley /* Face D: {d, e, f} */ 1540b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[1] - fStart)*3 + (ornt[1] < 0 ? (-(ornt[1]+1)+2)%3 : (ornt[1]+0)%3); 1541b5da9499SMatthew G. Knepley orntNew[0] = ornt[1] < 0 ? -2 : 0; 1542b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (cone[3] - fStart)*3 + (ornt[3] < 0 ? (-(ornt[3]+1)+1)%3 : (ornt[3]+1)%3); 1543b5da9499SMatthew G. Knepley orntNew[1] = ornt[3] < 0 ? -2 : 0; 1544b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[2] - fStart)*3 + (ornt[2] < 0 ? (-(ornt[2]+1)+1)%3 : (ornt[2]+1)%3); 1545b5da9499SMatthew G. Knepley orntNew[2] = ornt[2] < 0 ? -2 : 0; 1546b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1547b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1548b5da9499SMatthew G. Knepley #if 1 1549b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1550b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1551b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1552b5da9499SMatthew G. Knepley } 1553b5da9499SMatthew G. Knepley #endif 1554b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 3; 1555b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 3+4; 1556b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1557b5da9499SMatthew G. Knepley #if 1 1558b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1559b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1560b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1561b5da9499SMatthew G. Knepley } 1562b5da9499SMatthew G. Knepley #endif 1563b5da9499SMatthew G. Knepley ++newp; 1564b5da9499SMatthew G. Knepley /* Face E: {d, f, a} */ 1565b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[2] - fStart)*3 + (ornt[2] < 0 ? (-(ornt[2]+1)+1)%3 : (ornt[2]+1)%3); 1566b5da9499SMatthew G. Knepley orntNew[0] = ornt[2] < 0 ? 0 : -2; 1567b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 1568b5da9499SMatthew G. Knepley orntNew[1] = 0; 1569b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[1] - fStart)*3 + (ornt[1] < 0 ? (-(ornt[1]+1)+0)%3 : (ornt[1]+2)%3); 1570b5da9499SMatthew G. Knepley orntNew[2] = ornt[1] < 0 ? -2 : 0; 1571b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1572b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1573b5da9499SMatthew G. Knepley #if 1 1574b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1575b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1576b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1577b5da9499SMatthew G. Knepley } 1578b5da9499SMatthew G. Knepley #endif 1579b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 0+4; 1580b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 3+4; 1581b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1582b5da9499SMatthew G. Knepley #if 1 1583b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1584b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1585b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1586b5da9499SMatthew G. Knepley } 1587b5da9499SMatthew G. Knepley #endif 1588b5da9499SMatthew G. Knepley ++newp; 1589b5da9499SMatthew G. Knepley /* Face F: {c, a, f} */ 1590b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[0] - fStart)*3 + (ornt[0] < 0 ? (-(ornt[0]+1)+0)%3 : (ornt[0]+2)%3); 1591b5da9499SMatthew G. Knepley orntNew[0] = ornt[0] < 0 ? -2 : 0; 1592b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 1593b5da9499SMatthew G. Knepley orntNew[1] = -2; 1594b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[2] - fStart)*3 + (ornt[2] < 0 ? (-(ornt[2]+1)+2)%3 : (ornt[2]+0)%3); 1595b5da9499SMatthew G. Knepley orntNew[2] = ornt[1] < 0 ? 0 : -2; 1596b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1597b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1598b5da9499SMatthew G. Knepley #if 1 1599b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1600b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1601b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1602b5da9499SMatthew G. Knepley } 1603b5da9499SMatthew G. Knepley #endif 1604b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 0+4; 1605b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 2+4; 1606b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1607b5da9499SMatthew G. Knepley #if 1 1608b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1609b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1610b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1611b5da9499SMatthew G. Knepley } 1612b5da9499SMatthew G. Knepley #endif 1613b5da9499SMatthew G. Knepley ++newp; 1614b5da9499SMatthew G. Knepley /* Face G: {e, a, f} */ 1615b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[1] - fStart)*3 + (ornt[1] < 0 ? (-(ornt[1]+1)+1)%3 : (ornt[1]+1)%3); 1616b5da9499SMatthew G. Knepley orntNew[0] = ornt[1] < 0 ? -2 : 0; 1617b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 1618b5da9499SMatthew G. Knepley orntNew[1] = -2; 1619b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (cone[3] - fStart)*3 + (ornt[3] < 0 ? (-(ornt[3]+1)+1)%3 : (ornt[3]+1)%3); 1620b5da9499SMatthew G. Knepley orntNew[2] = ornt[3] < 0 ? 0 : -2; 1621b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1622b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1623b5da9499SMatthew G. Knepley #if 1 1624b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1625b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1626b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1627b5da9499SMatthew G. Knepley } 1628b5da9499SMatthew G. Knepley #endif 1629b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 1+4; 1630b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 3+4; 1631b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1632b5da9499SMatthew G. Knepley #if 1 1633b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1634b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1635b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1636b5da9499SMatthew G. Knepley } 1637b5da9499SMatthew G. Knepley #endif 1638b5da9499SMatthew G. Knepley ++newp; 1639b5da9499SMatthew G. Knepley /* Face H: {a, b, f} */ 1640b5da9499SMatthew G. Knepley coneNew[0] = eStartNew + (eEnd - eStart)*2 + (cone[0] - fStart)*3 + (ornt[0] < 0 ? (-(ornt[0]+1)+2)%3 : (ornt[0]+0)%3); 1641b5da9499SMatthew G. Knepley orntNew[0] = ornt[0] < 0 ? -2 : 0; 1642b5da9499SMatthew G. Knepley coneNew[1] = eStartNew + (eEnd - eStart)*2 + (cone[3] - fStart)*3 + (ornt[3] < 0 ? (-(ornt[3]+1)+0)%3 : (ornt[3]+2)%3); 1643b5da9499SMatthew G. Knepley orntNew[1] = ornt[3] < 0 ? 0 : -2; 1644b5da9499SMatthew G. Knepley coneNew[2] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 1645b5da9499SMatthew G. Knepley orntNew[2] = 0; 1646b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1647b5da9499SMatthew G. Knepley ierr = DMPlexSetConeOrientation(rdm, newp, orntNew);CHKERRQ(ierr); 1648b5da9499SMatthew G. Knepley #if 1 1649b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1650b5da9499SMatthew G. Knepley for (p = 0; p < 3; ++p) { 1651b5da9499SMatthew G. Knepley if ((coneNew[p] < eStartNew) || (coneNew[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", coneNew[p], eStartNew, eEndNew); 1652b5da9499SMatthew G. Knepley } 1653b5da9499SMatthew G. Knepley #endif 1654b5da9499SMatthew G. Knepley supportNew[0] = (c - cStart)*8 + 1+4; 1655b5da9499SMatthew G. Knepley supportNew[1] = (c - cStart)*8 + 2+4; 1656b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1657b5da9499SMatthew G. Knepley #if 1 1658b5da9499SMatthew G. Knepley if ((newp < fStartNew) || (newp >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", newp, fStartNew, fEndNew); 1659b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1660b5da9499SMatthew G. Knepley if ((supportNew[p] < cStartNew) || (supportNew[p] >= cEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a cell [%d, %d)", supportNew[p], cStartNew, cEndNew); 1661b5da9499SMatthew G. Knepley } 1662b5da9499SMatthew G. Knepley #endif 1663b5da9499SMatthew G. Knepley ++newp; 1664b5da9499SMatthew G. Knepley } 1665b5da9499SMatthew G. Knepley /* Split Edges have 2 vertices and the same faces as the parent */ 1666b5da9499SMatthew G. Knepley for (e = eStart; e < eEnd; ++e) { 1667b5da9499SMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (e - eStart); 1668b5da9499SMatthew G. Knepley 1669b5da9499SMatthew G. Knepley for (r = 0; r < 2; ++r) { 1670b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (e - eStart)*2 + r; 1671b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt, *support; 1672b5da9499SMatthew G. Knepley PetscInt coneNew[2], coneSize, c, supportSize, s; 1673b5da9499SMatthew G. Knepley 1674b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, e, &cone);CHKERRQ(ierr); 1675b5da9499SMatthew G. Knepley coneNew[0] = vStartNew + (cone[0] - vStart); 1676b5da9499SMatthew G. Knepley coneNew[1] = vStartNew + (cone[1] - vStart); 1677b5da9499SMatthew G. Knepley coneNew[(r+1)%2] = newv; 1678b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1679b5da9499SMatthew G. Knepley #if 1 1680b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1681b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1682b5da9499SMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 1683b5da9499SMatthew G. Knepley } 1684b5da9499SMatthew G. Knepley #endif 1685b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, e, &supportSize);CHKERRQ(ierr); 1686b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, e, &support);CHKERRQ(ierr); 1687b5da9499SMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 1688b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 1689b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1690b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 1691b5da9499SMatthew G. Knepley for (c = 0; c < coneSize; ++c) { 1692b5da9499SMatthew G. Knepley if (cone[c] == e) break; 1693b5da9499SMatthew G. Knepley } 1694b5da9499SMatthew G. Knepley supportRef[s] = fStartNew + (support[s] - fStart)*4 + (c + (ornt[c] < 0 ? 1-r : r))%3; 1695b5da9499SMatthew G. Knepley } 1696b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 1697b5da9499SMatthew G. Knepley #if 1 1698b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1699b5da9499SMatthew G. Knepley for (p = 0; p < supportSize; ++p) { 1700b5da9499SMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 1701b5da9499SMatthew G. Knepley } 1702b5da9499SMatthew G. Knepley #endif 1703b5da9499SMatthew G. Knepley } 1704b5da9499SMatthew G. Knepley } 170586f0afeeSMatthew G. Knepley /* Face edges have 2 vertices and 2+cells*(1/2) faces */ 1706b5da9499SMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 1707b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt, *support; 1708b5da9499SMatthew G. Knepley PetscInt coneSize, supportSize, s; 1709b5da9499SMatthew G. Knepley 1710b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, f, &supportSize);CHKERRQ(ierr); 1711b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, f, &support);CHKERRQ(ierr); 1712b5da9499SMatthew G. Knepley for (r = 0; r < 3; ++r) { 1713b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (eEnd - eStart)*2 + (f - fStart)*3 + r; 1714b5da9499SMatthew G. Knepley PetscInt coneNew[2], intFaces = 0, er, eint[4] = {1, 0, 2, 0}; 1715b5da9499SMatthew G. Knepley PetscInt fint[24] = { 1, 7, -1, -1, 0, 5, 1716b5da9499SMatthew G. Knepley -1, -1, 1, 6, 0, 4, 1717b5da9499SMatthew G. Knepley 2, 5, 3, 4, -1, -1, 1718b5da9499SMatthew G. Knepley -1, -1, 3, 6, 2, 7}; 1719b5da9499SMatthew G. Knepley 1720b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, f, &cone);CHKERRQ(ierr); 1721b5da9499SMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (cone[(r+0)%3] - eStart); 1722b5da9499SMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (cone[(r+1)%3] - eStart); 1723b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1724b5da9499SMatthew G. Knepley #if 1 1725b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1726b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1727b5da9499SMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 1728b5da9499SMatthew G. Knepley } 1729b5da9499SMatthew G. Knepley #endif 1730b5da9499SMatthew G. Knepley supportRef[0] = fStartNew + (f - fStart)*4 + (r+1)%3; 1731b5da9499SMatthew G. Knepley supportRef[1] = fStartNew + (f - fStart)*4 + 3; 1732b5da9499SMatthew G. Knepley for (s = 0; s < supportSize; ++s) { 1733b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 1734b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1735b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, support[s], &ornt);CHKERRQ(ierr); 1736b5da9499SMatthew G. Knepley for (c = 0; c < coneSize; ++c) {if (cone[c] == f) break;} 173786f0afeeSMatthew G. Knepley /* Here we want to determine whether edge newp contains a vertex which is part of the cross-tet edge */ 173886f0afeeSMatthew G. Knepley er = ornt[c] < 0 ? (-(ornt[c]+1) + 2-r)%3 : (ornt[c] + r)%3; 1739b5da9499SMatthew G. Knepley if (er == eint[c]) { 1740b5da9499SMatthew G. Knepley supportRef[2+intFaces++] = fStartNew + (fEnd - fStart)*4 + (support[s] - cStart)*8 + (c + 2)%4; 1741b5da9499SMatthew G. Knepley } else { 1742b5da9499SMatthew G. Knepley supportRef[2+intFaces++] = fStartNew + (fEnd - fStart)*4 + (support[s] - cStart)*8 + fint[(c*3 + er)*2 + 0]; 1743b5da9499SMatthew G. Knepley supportRef[2+intFaces++] = fStartNew + (fEnd - fStart)*4 + (support[s] - cStart)*8 + fint[(c*3 + er)*2 + 1]; 1744b5da9499SMatthew G. Knepley } 1745b5da9499SMatthew G. Knepley } 1746b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 1747b5da9499SMatthew G. Knepley #if 1 1748b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1749b5da9499SMatthew G. Knepley for (p = 0; p < intFaces; ++p) { 1750b5da9499SMatthew G. Knepley if ((supportRef[p] < fStartNew) || (supportRef[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportRef[p], fStartNew, fEndNew); 1751b5da9499SMatthew G. Knepley } 1752b5da9499SMatthew G. Knepley #endif 1753b5da9499SMatthew G. Knepley } 1754b5da9499SMatthew G. Knepley } 1755b5da9499SMatthew G. Knepley /* Interior edges have 2 vertices and 4 faces */ 1756b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 1757b5da9499SMatthew G. Knepley const PetscInt newp = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (c - cStart); 1758b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt, *fcone; 17594a40f731SMatthew G. Knepley PetscInt coneNew[2], supportNew[4], find; 1760b5da9499SMatthew G. Knepley 1761b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, c, &cone);CHKERRQ(ierr); 1762b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, c, &ornt);CHKERRQ(ierr); 1763b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[0], &fcone);CHKERRQ(ierr); 1764b5da9499SMatthew G. Knepley find = ornt[0] < 0 ? (-(ornt[0]+1) + 0)%3 : ornt[0]; 1765b5da9499SMatthew G. Knepley coneNew[0] = vStartNew + (vEnd - vStart) + (fcone[find] - eStart); 1766b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[2], &fcone);CHKERRQ(ierr); 1767b5da9499SMatthew G. Knepley find = ornt[2] < 0 ? (-(ornt[2]+1) + 1)%3 : (ornt[2]+1)%3; 1768b5da9499SMatthew G. Knepley coneNew[1] = vStartNew + (vEnd - vStart) + (fcone[find] - eStart); 1769b5da9499SMatthew G. Knepley ierr = DMPlexSetCone(rdm, newp, coneNew);CHKERRQ(ierr); 1770b5da9499SMatthew G. Knepley #if 1 1771b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1772b5da9499SMatthew G. Knepley for (p = 0; p < 2; ++p) { 1773b5da9499SMatthew G. Knepley if ((coneNew[p] < vStartNew) || (coneNew[p] >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", coneNew[p], vStartNew, vEndNew); 1774b5da9499SMatthew G. Knepley } 1775b5da9499SMatthew G. Knepley #endif 1776b5da9499SMatthew G. Knepley supportNew[0] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 4; 1777b5da9499SMatthew G. Knepley supportNew[1] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 5; 1778b5da9499SMatthew G. Knepley supportNew[2] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 6; 1779b5da9499SMatthew G. Knepley supportNew[3] = fStartNew + (fEnd - fStart)*4 + (c - cStart)*8 + 7; 1780b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportNew);CHKERRQ(ierr); 1781b5da9499SMatthew G. Knepley #if 1 1782b5da9499SMatthew G. Knepley if ((newp < eStartNew) || (newp >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", newp, eStartNew, eEndNew); 1783b5da9499SMatthew G. Knepley for (p = 0; p < 4; ++p) { 1784b5da9499SMatthew G. Knepley if ((supportNew[p] < fStartNew) || (supportNew[p] >= fEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a face [%d, %d)", supportNew[p], fStartNew, fEndNew); 1785b5da9499SMatthew G. Knepley } 1786b5da9499SMatthew G. Knepley #endif 1787b5da9499SMatthew G. Knepley } 1788b5da9499SMatthew G. Knepley /* Old vertices have identical supports */ 1789b5da9499SMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 1790b5da9499SMatthew G. Knepley const PetscInt newp = vStartNew + (v - vStart); 1791b5da9499SMatthew G. Knepley const PetscInt *support, *cone; 1792b5da9499SMatthew G. Knepley PetscInt size, s; 1793b5da9499SMatthew G. Knepley 1794b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, v, &size);CHKERRQ(ierr); 1795b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, v, &support);CHKERRQ(ierr); 1796b5da9499SMatthew G. Knepley for (s = 0; s < size; ++s) { 1797b5da9499SMatthew G. Knepley PetscInt r = 0; 1798b5da9499SMatthew G. Knepley 1799b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1800b5da9499SMatthew G. Knepley if (cone[1] == v) r = 1; 1801b5da9499SMatthew G. Knepley supportRef[s] = eStartNew + (support[s] - eStart)*2 + r; 1802b5da9499SMatthew G. Knepley } 1803b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 1804b5da9499SMatthew G. Knepley #if 1 1805b5da9499SMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 1806b5da9499SMatthew G. Knepley for (p = 0; p < size; ++p) { 1807b5da9499SMatthew G. Knepley if ((supportRef[p] < eStartNew) || (supportRef[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", supportRef[p], eStartNew, eEndNew); 1808b5da9499SMatthew G. Knepley } 1809b5da9499SMatthew G. Knepley #endif 1810b5da9499SMatthew G. Knepley } 1811b5da9499SMatthew G. Knepley /* Edge vertices have 2 + face*2 + 0/1 supports */ 1812b5da9499SMatthew G. Knepley for (e = eStart; e < eEnd; ++e) { 1813b5da9499SMatthew G. Knepley const PetscInt newp = vStartNew + (vEnd - vStart) + (e - eStart); 1814b5da9499SMatthew G. Knepley const PetscInt *cone, *support; 1815b5da9499SMatthew G. Knepley PetscInt *star = NULL, starSize, cellSize = 0, coneSize, size, s; 1816b5da9499SMatthew G. Knepley 1817b5da9499SMatthew G. Knepley ierr = DMPlexGetSupportSize(dm, e, &size);CHKERRQ(ierr); 1818b5da9499SMatthew G. Knepley ierr = DMPlexGetSupport(dm, e, &support);CHKERRQ(ierr); 1819b5da9499SMatthew G. Knepley supportRef[0] = eStartNew + (e - eStart)*2 + 0; 1820b5da9499SMatthew G. Knepley supportRef[1] = eStartNew + (e - eStart)*2 + 1; 1821b5da9499SMatthew G. Knepley for (s = 0; s < size; ++s) { 1822b5da9499SMatthew G. Knepley PetscInt r = 0; 1823b5da9499SMatthew G. Knepley 1824b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, support[s], &coneSize);CHKERRQ(ierr); 1825b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, support[s], &cone);CHKERRQ(ierr); 1826b5da9499SMatthew G. Knepley for (r = 0; r < coneSize; ++r) {if (cone[r] == e) break;} 1827b5da9499SMatthew G. Knepley supportRef[2+s*2+0] = eStartNew + (eEnd - eStart)*2 + (support[s] - fStart)*3 + (r+0)%3; 1828b5da9499SMatthew G. Knepley supportRef[2+s*2+1] = eStartNew + (eEnd - eStart)*2 + (support[s] - fStart)*3 + (r+2)%3; 1829b5da9499SMatthew G. Knepley } 1830b5da9499SMatthew G. Knepley ierr = DMPlexGetTransitiveClosure(dm, e, PETSC_FALSE, &starSize, &star);CHKERRQ(ierr); 1831b5da9499SMatthew G. Knepley for (s = 0; s < starSize*2; s += 2) { 1832b5da9499SMatthew G. Knepley const PetscInt *cone, *ornt; 1833b5da9499SMatthew G. Knepley PetscInt e01, e23; 1834b5da9499SMatthew G. Knepley 1835b5da9499SMatthew G. Knepley if ((star[s] >= cStart) && (star[s] < cEnd)) { 1836b5da9499SMatthew G. Knepley /* Check edge 0-1 */ 1837b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, star[s], &cone);CHKERRQ(ierr); 1838b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, star[s], &ornt);CHKERRQ(ierr); 1839b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[0], &cone);CHKERRQ(ierr); 1840b5da9499SMatthew G. Knepley e01 = cone[ornt[0] < 0 ? (-(ornt[0]+1) + 0)%3 : ornt[0]]; 1841b5da9499SMatthew G. Knepley /* Check edge 2-3 */ 1842b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, star[s], &cone);CHKERRQ(ierr); 1843b5da9499SMatthew G. Knepley ierr = DMPlexGetConeOrientation(dm, star[s], &ornt);CHKERRQ(ierr); 1844b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, cone[3], &cone);CHKERRQ(ierr); 1845b5da9499SMatthew G. Knepley e23 = cone[ornt[3] < 0 ? (-(ornt[3]+1) + 2)%3 : (ornt[3] + 2)%3]; 1846b5da9499SMatthew G. Knepley if ((e01 == e) || (e23 == e)) {supportRef[2+size*2+cellSize++] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (star[s] - cStart);} 1847b5da9499SMatthew G. Knepley } 1848b5da9499SMatthew G. Knepley } 1849b5da9499SMatthew G. Knepley ierr = DMPlexRestoreTransitiveClosure(dm, e, PETSC_FALSE, &starSize, &star);CHKERRQ(ierr); 1850b5da9499SMatthew G. Knepley ierr = DMPlexSetSupport(rdm, newp, supportRef);CHKERRQ(ierr); 1851b5da9499SMatthew G. Knepley #if 1 1852b5da9499SMatthew G. Knepley if ((newp < vStartNew) || (newp >= vEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not a vertex [%d, %d)", newp, vStartNew, vEndNew); 1853b5da9499SMatthew G. Knepley for (p = 0; p < 2+size*2+cellSize; ++p) { 1854b5da9499SMatthew G. Knepley if ((supportRef[p] < eStartNew) || (supportRef[p] >= eEndNew)) SETERRQ3(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Point %d is not an edge [%d, %d)", supportRef[p], eStartNew, eEndNew); 1855b5da9499SMatthew G. Knepley } 1856b5da9499SMatthew G. Knepley #endif 1857b5da9499SMatthew G. Knepley } 1858b5da9499SMatthew G. Knepley ierr = PetscFree(supportRef);CHKERRQ(ierr); 1859b5da9499SMatthew G. Knepley ierr = DMPlexRestoreFaces_Internal(dm, 3, cStart, NULL, NULL, &faces);CHKERRQ(ierr); 1860b5da9499SMatthew G. Knepley break; 186175d3a19aSMatthew G. Knepley default: 186275d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 186375d3a19aSMatthew G. Knepley } 186475d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 186575d3a19aSMatthew G. Knepley } 186675d3a19aSMatthew G. Knepley 186775d3a19aSMatthew G. Knepley #undef __FUNCT__ 186875d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerSetCoordinates" 186975d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerSetCoordinates(CellRefiner refiner, DM dm, PetscInt depthSize[], DM rdm) 187075d3a19aSMatthew G. Knepley { 187175d3a19aSMatthew G. Knepley PetscSection coordSection, coordSectionNew; 187275d3a19aSMatthew G. Knepley Vec coordinates, coordinatesNew; 187375d3a19aSMatthew G. Knepley PetscScalar *coords, *coordsNew; 1874b5da9499SMatthew G. Knepley PetscInt dim, depth, coordSizeNew, cStart, cEnd, c, vStart, vStartNew, vEnd, v, eStart, eEnd, eMax, e, fStart, fEnd, fMax, f; 187575d3a19aSMatthew G. Knepley PetscErrorCode ierr; 187675d3a19aSMatthew G. Knepley 187775d3a19aSMatthew G. Knepley PetscFunctionBegin; 187875d3a19aSMatthew G. Knepley ierr = DMPlexGetDimension(dm, &dim);CHKERRQ(ierr); 187975d3a19aSMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 188075d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 1881b5da9499SMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 188275d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 188375d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 1884b5da9499SMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, NULL, &fMax, &eMax, NULL);CHKERRQ(ierr); 188575d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, depthSize, NULL, NULL, NULL, &vStartNew);CHKERRQ(ierr); 188675d3a19aSMatthew G. Knepley ierr = DMPlexGetCoordinateSection(dm, &coordSection);CHKERRQ(ierr); 188775d3a19aSMatthew G. Knepley ierr = PetscSectionCreate(PetscObjectComm((PetscObject)dm), &coordSectionNew);CHKERRQ(ierr); 188875d3a19aSMatthew G. Knepley ierr = PetscSectionSetNumFields(coordSectionNew, 1);CHKERRQ(ierr); 188975d3a19aSMatthew G. Knepley ierr = PetscSectionSetFieldComponents(coordSectionNew, 0, dim);CHKERRQ(ierr); 189075d3a19aSMatthew G. Knepley ierr = PetscSectionSetChart(coordSectionNew, vStartNew, vStartNew+depthSize[0]);CHKERRQ(ierr); 189175d3a19aSMatthew G. Knepley if (fMax < 0) fMax = fEnd; 1892b5da9499SMatthew G. Knepley if (eMax < 0) eMax = eEnd; 189375d3a19aSMatthew G. Knepley /* All vertices have the dim coordinates */ 189475d3a19aSMatthew G. Knepley for (v = vStartNew; v < vStartNew+depthSize[0]; ++v) { 189575d3a19aSMatthew G. Knepley ierr = PetscSectionSetDof(coordSectionNew, v, dim);CHKERRQ(ierr); 189675d3a19aSMatthew G. Knepley ierr = PetscSectionSetFieldDof(coordSectionNew, v, 0, dim);CHKERRQ(ierr); 189775d3a19aSMatthew G. Knepley } 189875d3a19aSMatthew G. Knepley ierr = PetscSectionSetUp(coordSectionNew);CHKERRQ(ierr); 189975d3a19aSMatthew G. Knepley ierr = DMPlexSetCoordinateSection(rdm, coordSectionNew);CHKERRQ(ierr); 190075d3a19aSMatthew G. Knepley ierr = DMGetCoordinatesLocal(dm, &coordinates);CHKERRQ(ierr); 190175d3a19aSMatthew G. Knepley ierr = PetscSectionGetStorageSize(coordSectionNew, &coordSizeNew);CHKERRQ(ierr); 190275d3a19aSMatthew G. Knepley ierr = VecCreate(PetscObjectComm((PetscObject)dm), &coordinatesNew);CHKERRQ(ierr); 190375d3a19aSMatthew G. Knepley ierr = PetscObjectSetName((PetscObject) coordinatesNew, "coordinates");CHKERRQ(ierr); 190475d3a19aSMatthew G. Knepley ierr = VecSetSizes(coordinatesNew, coordSizeNew, PETSC_DETERMINE);CHKERRQ(ierr); 190575d3a19aSMatthew G. Knepley ierr = VecSetFromOptions(coordinatesNew);CHKERRQ(ierr); 190675d3a19aSMatthew G. Knepley ierr = VecGetArray(coordinates, &coords);CHKERRQ(ierr); 190775d3a19aSMatthew G. Knepley ierr = VecGetArray(coordinatesNew, &coordsNew);CHKERRQ(ierr); 1908b5da9499SMatthew G. Knepley switch (refiner) { 1909b5da9499SMatthew G. Knepley case 6: /* Hex 3D */ 1910b5da9499SMatthew G. Knepley /* Face vertices have the average of corner coordinates */ 1911b5da9499SMatthew G. Knepley for (f = fStart; f < fEnd; ++f) { 1912b5da9499SMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (eEnd - eStart) + (cEnd - cStart) + (f - fStart); 1913b5da9499SMatthew G. Knepley PetscInt *cone = NULL; 1914b5da9499SMatthew G. Knepley PetscInt closureSize, coneSize = 0, off[8], offnew, p, d; 1915b5da9499SMatthew G. Knepley 1916b5da9499SMatthew G. Knepley ierr = DMPlexGetTransitiveClosure(dm, f, PETSC_TRUE, &closureSize, &cone);CHKERRQ(ierr); 1917b5da9499SMatthew G. Knepley for (p = 0; p < closureSize*2; p += 2) { 1918b5da9499SMatthew G. Knepley const PetscInt point = cone[p]; 1919b5da9499SMatthew G. Knepley if ((point >= vStart) && (point < vEnd)) cone[coneSize++] = point; 1920b5da9499SMatthew G. Knepley } 1921b5da9499SMatthew G. Knepley for (v = 0; v < coneSize; ++v) { 1922b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSection, cone[v], &off[v]);CHKERRQ(ierr); 1923b5da9499SMatthew G. Knepley } 1924b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSectionNew, newv, &offnew);CHKERRQ(ierr); 1925b5da9499SMatthew G. Knepley for (d = 0; d < dim; ++d) { 1926b5da9499SMatthew G. Knepley coordsNew[offnew+d] = 0.0; 1927b5da9499SMatthew G. Knepley for (v = 0; v < coneSize; ++v) coordsNew[offnew+d] += coords[off[v]+d]; 1928b5da9499SMatthew G. Knepley coordsNew[offnew+d] /= coneSize; 1929b5da9499SMatthew G. Knepley } 1930b5da9499SMatthew G. Knepley ierr = DMPlexRestoreTransitiveClosure(dm, f, PETSC_TRUE, &closureSize, &cone);CHKERRQ(ierr); 1931b5da9499SMatthew G. Knepley } 1932b5da9499SMatthew G. Knepley case 2: /* Hex 2D */ 1933b5da9499SMatthew G. Knepley /* Cell vertices have the average of corner coordinates */ 1934b5da9499SMatthew G. Knepley for (c = cStart; c < cEnd; ++c) { 1935b5da9499SMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (eEnd - eStart) + (c - cStart); 1936b5da9499SMatthew G. Knepley PetscInt *cone = NULL; 1937b5da9499SMatthew G. Knepley PetscInt closureSize, coneSize = 0, off[8], offnew, p, d; 1938b5da9499SMatthew G. Knepley 1939b5da9499SMatthew G. Knepley ierr = DMPlexGetTransitiveClosure(dm, c, PETSC_TRUE, &closureSize, &cone);CHKERRQ(ierr); 1940b5da9499SMatthew G. Knepley for (p = 0; p < closureSize*2; p += 2) { 1941b5da9499SMatthew G. Knepley const PetscInt point = cone[p]; 1942b5da9499SMatthew G. Knepley if ((point >= vStart) && (point < vEnd)) cone[coneSize++] = point; 1943b5da9499SMatthew G. Knepley } 1944b5da9499SMatthew G. Knepley for (v = 0; v < coneSize; ++v) { 1945b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSection, cone[v], &off[v]);CHKERRQ(ierr); 1946b5da9499SMatthew G. Knepley } 1947b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSectionNew, newv, &offnew);CHKERRQ(ierr); 1948b5da9499SMatthew G. Knepley for (d = 0; d < dim; ++d) { 1949b5da9499SMatthew G. Knepley coordsNew[offnew+d] = 0.0; 1950b5da9499SMatthew G. Knepley for (v = 0; v < coneSize; ++v) coordsNew[offnew+d] += coords[off[v]+d]; 1951b5da9499SMatthew G. Knepley coordsNew[offnew+d] /= coneSize; 1952b5da9499SMatthew G. Knepley } 1953b5da9499SMatthew G. Knepley ierr = DMPlexRestoreTransitiveClosure(dm, c, PETSC_TRUE, &closureSize, &cone);CHKERRQ(ierr); 1954b5da9499SMatthew G. Knepley } 1955b5da9499SMatthew G. Knepley case 1: /* Simplicial 2D */ 1956b5da9499SMatthew G. Knepley case 3: /* Hybrid Simplicial 2D */ 1957b5da9499SMatthew G. Knepley case 5: /* Simplicial 3D */ 1958b5da9499SMatthew G. Knepley /* Edge vertices have the average of endpoint coordinates */ 1959b5da9499SMatthew G. Knepley for (e = eStart; e < eMax; ++e) { 1960b5da9499SMatthew G. Knepley const PetscInt newv = vStartNew + (vEnd - vStart) + (e - eStart); 1961b5da9499SMatthew G. Knepley const PetscInt *cone; 1962b5da9499SMatthew G. Knepley PetscInt coneSize, offA, offB, offnew, d; 1963b5da9499SMatthew G. Knepley 1964b5da9499SMatthew G. Knepley ierr = DMPlexGetConeSize(dm, e, &coneSize);CHKERRQ(ierr); 1965b5da9499SMatthew G. Knepley if (coneSize != 2) SETERRQ2(PetscObjectComm((PetscObject)dm), PETSC_ERR_ARG_WRONG, "Edge %d cone should have two vertices, not %d", e, coneSize); 1966b5da9499SMatthew G. Knepley ierr = DMPlexGetCone(dm, e, &cone);CHKERRQ(ierr); 1967b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSection, cone[0], &offA);CHKERRQ(ierr); 1968b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSection, cone[1], &offB);CHKERRQ(ierr); 1969b5da9499SMatthew G. Knepley ierr = PetscSectionGetOffset(coordSectionNew, newv, &offnew);CHKERRQ(ierr); 1970b5da9499SMatthew G. Knepley for (d = 0; d < dim; ++d) { 1971b5da9499SMatthew G. Knepley coordsNew[offnew+d] = 0.5*(coords[offA+d] + coords[offB+d]); 1972b5da9499SMatthew G. Knepley } 1973b5da9499SMatthew G. Knepley } 197475d3a19aSMatthew G. Knepley /* Old vertices have the same coordinates */ 197575d3a19aSMatthew G. Knepley for (v = vStart; v < vEnd; ++v) { 197675d3a19aSMatthew G. Knepley const PetscInt newv = vStartNew + (v - vStart); 197775d3a19aSMatthew G. Knepley PetscInt off, offnew, d; 197875d3a19aSMatthew G. Knepley 197975d3a19aSMatthew G. Knepley ierr = PetscSectionGetOffset(coordSection, v, &off);CHKERRQ(ierr); 198075d3a19aSMatthew G. Knepley ierr = PetscSectionGetOffset(coordSectionNew, newv, &offnew);CHKERRQ(ierr); 198175d3a19aSMatthew G. Knepley for (d = 0; d < dim; ++d) { 198275d3a19aSMatthew G. Knepley coordsNew[offnew+d] = coords[off+d]; 198375d3a19aSMatthew G. Knepley } 198475d3a19aSMatthew G. Knepley } 1985b5da9499SMatthew G. Knepley break; 1986b5da9499SMatthew G. Knepley default: 1987b5da9499SMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 198875d3a19aSMatthew G. Knepley } 198975d3a19aSMatthew G. Knepley ierr = VecRestoreArray(coordinates, &coords);CHKERRQ(ierr); 199075d3a19aSMatthew G. Knepley ierr = VecRestoreArray(coordinatesNew, &coordsNew);CHKERRQ(ierr); 199175d3a19aSMatthew G. Knepley ierr = DMSetCoordinatesLocal(rdm, coordinatesNew);CHKERRQ(ierr); 199275d3a19aSMatthew G. Knepley ierr = VecDestroy(&coordinatesNew);CHKERRQ(ierr); 199375d3a19aSMatthew G. Knepley ierr = PetscSectionDestroy(&coordSectionNew);CHKERRQ(ierr); 199475d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 199575d3a19aSMatthew G. Knepley } 199675d3a19aSMatthew G. Knepley 199775d3a19aSMatthew G. Knepley #undef __FUNCT__ 199875d3a19aSMatthew G. Knepley #define __FUNCT__ "DMPlexCreateProcessSF" 199975d3a19aSMatthew G. Knepley PetscErrorCode DMPlexCreateProcessSF(DM dm, PetscSF sfPoint, IS *processRanks, PetscSF *sfProcess) 200075d3a19aSMatthew G. Knepley { 200175d3a19aSMatthew G. Knepley PetscInt numRoots, numLeaves, l; 200275d3a19aSMatthew G. Knepley const PetscInt *localPoints; 200375d3a19aSMatthew G. Knepley const PetscSFNode *remotePoints; 200475d3a19aSMatthew G. Knepley PetscInt *localPointsNew; 200575d3a19aSMatthew G. Knepley PetscSFNode *remotePointsNew; 200675d3a19aSMatthew G. Knepley PetscInt *ranks, *ranksNew; 200775d3a19aSMatthew G. Knepley PetscErrorCode ierr; 200875d3a19aSMatthew G. Knepley 200975d3a19aSMatthew G. Knepley PetscFunctionBegin; 201075d3a19aSMatthew G. Knepley ierr = PetscSFGetGraph(sfPoint, &numRoots, &numLeaves, &localPoints, &remotePoints);CHKERRQ(ierr); 201175d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeaves * sizeof(PetscInt), &ranks);CHKERRQ(ierr); 201275d3a19aSMatthew G. Knepley for (l = 0; l < numLeaves; ++l) { 201375d3a19aSMatthew G. Knepley ranks[l] = remotePoints[l].rank; 201475d3a19aSMatthew G. Knepley } 201575d3a19aSMatthew G. Knepley ierr = PetscSortRemoveDupsInt(&numLeaves, ranks);CHKERRQ(ierr); 201675d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeaves * sizeof(PetscInt), &ranksNew);CHKERRQ(ierr); 201775d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeaves * sizeof(PetscInt), &localPointsNew);CHKERRQ(ierr); 201875d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeaves * sizeof(PetscSFNode), &remotePointsNew);CHKERRQ(ierr); 201975d3a19aSMatthew G. Knepley for (l = 0; l < numLeaves; ++l) { 202075d3a19aSMatthew G. Knepley ranksNew[l] = ranks[l]; 202175d3a19aSMatthew G. Knepley localPointsNew[l] = l; 202275d3a19aSMatthew G. Knepley remotePointsNew[l].index = 0; 202375d3a19aSMatthew G. Knepley remotePointsNew[l].rank = ranksNew[l]; 202475d3a19aSMatthew G. Knepley } 202575d3a19aSMatthew G. Knepley ierr = PetscFree(ranks);CHKERRQ(ierr); 202675d3a19aSMatthew G. Knepley ierr = ISCreateGeneral(PetscObjectComm((PetscObject)dm), numLeaves, ranksNew, PETSC_OWN_POINTER, processRanks);CHKERRQ(ierr); 202775d3a19aSMatthew G. Knepley ierr = PetscSFCreate(PetscObjectComm((PetscObject)dm), sfProcess);CHKERRQ(ierr); 202875d3a19aSMatthew G. Knepley ierr = PetscSFSetFromOptions(*sfProcess);CHKERRQ(ierr); 202975d3a19aSMatthew G. Knepley ierr = PetscSFSetGraph(*sfProcess, 1, numLeaves, localPointsNew, PETSC_OWN_POINTER, remotePointsNew, PETSC_OWN_POINTER);CHKERRQ(ierr); 203075d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 203175d3a19aSMatthew G. Knepley } 203275d3a19aSMatthew G. Knepley 203375d3a19aSMatthew G. Knepley #undef __FUNCT__ 203475d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerCreateSF" 203575d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerCreateSF(CellRefiner refiner, DM dm, PetscInt depthSize[], DM rdm) 203675d3a19aSMatthew G. Knepley { 203775d3a19aSMatthew G. Knepley PetscSF sf, sfNew, sfProcess; 203875d3a19aSMatthew G. Knepley IS processRanks; 203975d3a19aSMatthew G. Knepley MPI_Datatype depthType; 204075d3a19aSMatthew G. Knepley PetscInt numRoots, numLeaves, numLeavesNew = 0, l, m; 204175d3a19aSMatthew G. Knepley const PetscInt *localPoints, *neighbors; 204275d3a19aSMatthew G. Knepley const PetscSFNode *remotePoints; 204375d3a19aSMatthew G. Knepley PetscInt *localPointsNew; 204475d3a19aSMatthew G. Knepley PetscSFNode *remotePointsNew; 204575d3a19aSMatthew G. Knepley PetscInt *depthSizeOld, *rdepthSize, *rdepthSizeOld, *rdepthMaxOld, *rvStart, *rvStartNew, *reStart, *reStartNew, *rfStart, *rfStartNew, *rcStart, *rcStartNew; 204675d3a19aSMatthew G. Knepley PetscInt depth, numNeighbors, pStartNew, pEndNew, cStart, cStartNew, cEnd, cMax, vStart, vStartNew, vEnd, vMax, fStart, fStartNew, fEnd, fMax, eStart, eStartNew, eEnd, eMax, r, n; 204775d3a19aSMatthew G. Knepley PetscErrorCode ierr; 204875d3a19aSMatthew G. Knepley 204975d3a19aSMatthew G. Knepley PetscFunctionBegin; 205075d3a19aSMatthew G. Knepley ierr = DMPlexGetChart(rdm, &pStartNew, &pEndNew);CHKERRQ(ierr); 205175d3a19aSMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 205275d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 205375d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 205475d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 205575d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 205675d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, &fMax, &eMax, &vMax);CHKERRQ(ierr); 205775d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, depthSize, &cStartNew, &fStartNew, &eStartNew, &vStartNew);CHKERRQ(ierr); 205875d3a19aSMatthew G. Knepley switch (refiner) { 205975d3a19aSMatthew G. Knepley case 3: 206075d3a19aSMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 206175d3a19aSMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 206275d3a19aSMatthew G. Knepley if (fMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No face maximum specified in hybrid mesh"); 206375d3a19aSMatthew G. Knepley fMax = PetscMin(fEnd, fMax); 206475d3a19aSMatthew G. Knepley } 206575d3a19aSMatthew G. Knepley ierr = DMGetPointSF(dm, &sf);CHKERRQ(ierr); 206675d3a19aSMatthew G. Knepley ierr = DMGetPointSF(rdm, &sfNew);CHKERRQ(ierr); 206775d3a19aSMatthew G. Knepley /* Caculate size of new SF */ 206875d3a19aSMatthew G. Knepley ierr = PetscSFGetGraph(sf, &numRoots, &numLeaves, &localPoints, &remotePoints);CHKERRQ(ierr); 206975d3a19aSMatthew G. Knepley if (numRoots < 0) PetscFunctionReturn(0); 207075d3a19aSMatthew G. Knepley for (l = 0; l < numLeaves; ++l) { 207175d3a19aSMatthew G. Knepley const PetscInt p = localPoints[l]; 207275d3a19aSMatthew G. Knepley 207375d3a19aSMatthew G. Knepley switch (refiner) { 207475d3a19aSMatthew G. Knepley case 1: 207575d3a19aSMatthew G. Knepley /* Simplicial 2D */ 207675d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 207775d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 207875d3a19aSMatthew G. Knepley ++numLeavesNew; 207975d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 208075d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 2081d963de37SMatthew G. Knepley numLeavesNew += 2 + 1; 208275d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 208375d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces */ 208475d3a19aSMatthew G. Knepley numLeavesNew += 4 + 3; 208575d3a19aSMatthew G. Knepley } 208675d3a19aSMatthew G. Knepley break; 208775d3a19aSMatthew G. Knepley case 2: 208875d3a19aSMatthew G. Knepley /* Hex 2D */ 208975d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 209075d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 209175d3a19aSMatthew G. Knepley ++numLeavesNew; 209275d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 209375d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 2094d963de37SMatthew G. Knepley numLeavesNew += 2 + 1; 209575d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 209675d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces */ 209775d3a19aSMatthew G. Knepley numLeavesNew += 4 + 4; 209875d3a19aSMatthew G. Knepley } 209975d3a19aSMatthew G. Knepley break; 2100b5da9499SMatthew G. Knepley case 5: 2101b5da9499SMatthew G. Knepley /* Simplicial 3D */ 2102b5da9499SMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 2103b5da9499SMatthew G. Knepley /* Old vertices stay the same */ 2104b5da9499SMatthew G. Knepley ++numLeavesNew; 2105b5da9499SMatthew G. Knepley } else if ((p >= eStart) && (p < eEnd)) { 2106b5da9499SMatthew G. Knepley /* Old edges add new edges and vertex */ 2107b5da9499SMatthew G. Knepley numLeavesNew += 2 + 1; 2108b5da9499SMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 2109b5da9499SMatthew G. Knepley /* Old faces add new faces and face edges */ 2110b5da9499SMatthew G. Knepley numLeavesNew += 4 + 3; 2111b5da9499SMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 2112b5da9499SMatthew G. Knepley /* Old cells add new cells and interior faces and edges */ 2113b5da9499SMatthew G. Knepley numLeavesNew += 8 + 8 + 1; 2114b5da9499SMatthew G. Knepley } 2115b5da9499SMatthew G. Knepley break; 211675d3a19aSMatthew G. Knepley default: 211775d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 211875d3a19aSMatthew G. Knepley } 211975d3a19aSMatthew G. Knepley } 212075d3a19aSMatthew G. Knepley /* Communicate depthSizes for each remote rank */ 212175d3a19aSMatthew G. Knepley ierr = DMPlexCreateProcessSF(dm, sf, &processRanks, &sfProcess);CHKERRQ(ierr); 212275d3a19aSMatthew G. Knepley ierr = ISGetLocalSize(processRanks, &numNeighbors);CHKERRQ(ierr); 212375d3a19aSMatthew G. Knepley ierr = PetscMalloc5((depth+1)*numNeighbors,PetscInt,&rdepthSize,numNeighbors,PetscInt,&rvStartNew,numNeighbors,PetscInt,&reStartNew,numNeighbors,PetscInt,&rfStartNew,numNeighbors,PetscInt,&rcStartNew);CHKERRQ(ierr); 212475d3a19aSMatthew G. Knepley ierr = PetscMalloc7(depth+1,PetscInt,&depthSizeOld,(depth+1)*numNeighbors,PetscInt,&rdepthSizeOld,(depth+1)*numNeighbors,PetscInt,&rdepthMaxOld,numNeighbors,PetscInt,&rvStart,numNeighbors,PetscInt,&reStart,numNeighbors,PetscInt,&rfStart,numNeighbors,PetscInt,&rcStart);CHKERRQ(ierr); 212575d3a19aSMatthew G. Knepley ierr = MPI_Type_contiguous(depth+1, MPIU_INT, &depthType);CHKERRQ(ierr); 212675d3a19aSMatthew G. Knepley ierr = MPI_Type_commit(&depthType);CHKERRQ(ierr); 212775d3a19aSMatthew G. Knepley ierr = PetscSFBcastBegin(sfProcess, depthType, depthSize, rdepthSize);CHKERRQ(ierr); 212875d3a19aSMatthew G. Knepley ierr = PetscSFBcastEnd(sfProcess, depthType, depthSize, rdepthSize);CHKERRQ(ierr); 212975d3a19aSMatthew G. Knepley for (n = 0; n < numNeighbors; ++n) { 213075d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, &rdepthSize[n*(depth+1)], &rcStartNew[n], &rfStartNew[n], &reStartNew[n], &rvStartNew[n]);CHKERRQ(ierr); 213175d3a19aSMatthew G. Knepley } 213275d3a19aSMatthew G. Knepley depthSizeOld[depth] = cMax; 213375d3a19aSMatthew G. Knepley depthSizeOld[0] = vMax; 213475d3a19aSMatthew G. Knepley depthSizeOld[depth-1] = fMax; 213575d3a19aSMatthew G. Knepley depthSizeOld[1] = eMax; 213675d3a19aSMatthew G. Knepley 213775d3a19aSMatthew G. Knepley ierr = PetscSFBcastBegin(sfProcess, depthType, depthSizeOld, rdepthMaxOld);CHKERRQ(ierr); 213875d3a19aSMatthew G. Knepley ierr = PetscSFBcastEnd(sfProcess, depthType, depthSizeOld, rdepthMaxOld);CHKERRQ(ierr); 213975d3a19aSMatthew G. Knepley 214075d3a19aSMatthew G. Knepley depthSizeOld[depth] = cEnd - cStart; 214175d3a19aSMatthew G. Knepley depthSizeOld[0] = vEnd - vStart; 214275d3a19aSMatthew G. Knepley depthSizeOld[depth-1] = fEnd - fStart; 214375d3a19aSMatthew G. Knepley depthSizeOld[1] = eEnd - eStart; 214475d3a19aSMatthew G. Knepley 214575d3a19aSMatthew G. Knepley ierr = PetscSFBcastBegin(sfProcess, depthType, depthSizeOld, rdepthSizeOld);CHKERRQ(ierr); 214675d3a19aSMatthew G. Knepley ierr = PetscSFBcastEnd(sfProcess, depthType, depthSizeOld, rdepthSizeOld);CHKERRQ(ierr); 214775d3a19aSMatthew G. Knepley for (n = 0; n < numNeighbors; ++n) { 214875d3a19aSMatthew G. Knepley ierr = GetDepthStart_Private(depth, &rdepthSizeOld[n*(depth+1)], &rcStart[n], &rfStart[n], &reStart[n], &rvStart[n]);CHKERRQ(ierr); 214975d3a19aSMatthew G. Knepley } 215075d3a19aSMatthew G. Knepley ierr = MPI_Type_free(&depthType);CHKERRQ(ierr); 215175d3a19aSMatthew G. Knepley ierr = PetscSFDestroy(&sfProcess);CHKERRQ(ierr); 215275d3a19aSMatthew G. Knepley /* Calculate new point SF */ 215375d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeavesNew * sizeof(PetscInt), &localPointsNew);CHKERRQ(ierr); 215475d3a19aSMatthew G. Knepley ierr = PetscMalloc(numLeavesNew * sizeof(PetscSFNode), &remotePointsNew);CHKERRQ(ierr); 215575d3a19aSMatthew G. Knepley ierr = ISGetIndices(processRanks, &neighbors);CHKERRQ(ierr); 215675d3a19aSMatthew G. Knepley for (l = 0, m = 0; l < numLeaves; ++l) { 215775d3a19aSMatthew G. Knepley PetscInt p = localPoints[l]; 215875d3a19aSMatthew G. Knepley PetscInt rp = remotePoints[l].index, n; 215975d3a19aSMatthew G. Knepley PetscMPIInt rrank = remotePoints[l].rank; 216075d3a19aSMatthew G. Knepley 216175d3a19aSMatthew G. Knepley ierr = PetscFindInt(rrank, numNeighbors, neighbors, &n);CHKERRQ(ierr); 216275d3a19aSMatthew G. Knepley if (n < 0) SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "Could not locate remote rank %d", rrank); 216375d3a19aSMatthew G. Knepley switch (refiner) { 216475d3a19aSMatthew G. Knepley case 1: 216575d3a19aSMatthew G. Knepley /* Simplicial 2D */ 216675d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 216775d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 216875d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (p - vStart); 216975d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + (rp - rvStart[n]); 217075d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 217175d3a19aSMatthew G. Knepley ++m; 217275d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 217375d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 217475d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (vEnd - vStart) + (p - fStart); 217575d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + rdepthSizeOld[n*(depth+1)+0] + (rp - rfStart[n]); 217675d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 217775d3a19aSMatthew G. Knepley ++m; 217875d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r, ++m) { 217975d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (p - fStart)*2 + r; 218075d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rp - rfStart[n])*2 + r; 218175d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 218275d3a19aSMatthew G. Knepley } 218375d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 218475d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces */ 218575d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r, ++m) { 218675d3a19aSMatthew G. Knepley localPointsNew[m] = cStartNew + (p - cStart)*4 + r; 218775d3a19aSMatthew G. Knepley remotePointsNew[m].index = rcStartNew[n] + (rp - rcStart[n])*4 + r; 218875d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 218975d3a19aSMatthew G. Knepley } 219075d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r, ++m) { 219175d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (fEnd - fStart)*2 + (p - cStart)*3 + r; 219275d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + rdepthSizeOld[n*(depth+1)+depth-1]*2 + (rp - rcStart[n])*3 + r; 219375d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 219475d3a19aSMatthew G. Knepley } 219575d3a19aSMatthew G. Knepley } 219675d3a19aSMatthew G. Knepley break; 219775d3a19aSMatthew G. Knepley case 2: 219875d3a19aSMatthew G. Knepley /* Hex 2D */ 219975d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 220075d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 220175d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (p - vStart); 220275d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + (rp - rvStart[n]); 220375d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 220475d3a19aSMatthew G. Knepley ++m; 220575d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 220675d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 220775d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (vEnd - vStart) + (p - fStart); 220875d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + rdepthSizeOld[n*(depth+1)+0] + (rp - rfStart[n]); 220975d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 221075d3a19aSMatthew G. Knepley ++m; 221175d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r, ++m) { 221275d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (p - fStart)*2 + r; 221375d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rp - rfStart[n])*2 + r; 221475d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 221575d3a19aSMatthew G. Knepley } 221675d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 221775d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces */ 221875d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r, ++m) { 221975d3a19aSMatthew G. Knepley localPointsNew[m] = cStartNew + (p - cStart)*4 + r; 222075d3a19aSMatthew G. Knepley remotePointsNew[m].index = rcStartNew[n] + (rp - rcStart[n])*4 + r; 222175d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 222275d3a19aSMatthew G. Knepley } 222375d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r, ++m) { 222475d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (fEnd - fStart)*2 + (p - cStart)*4 + r; 222575d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + rdepthSizeOld[n*(depth+1)+depth-1]*2 + (rp - rcStart[n])*4 + r; 222675d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 222775d3a19aSMatthew G. Knepley } 222875d3a19aSMatthew G. Knepley } 222975d3a19aSMatthew G. Knepley break; 223075d3a19aSMatthew G. Knepley case 3: 223175d3a19aSMatthew G. Knepley /* Hybrid simplicial 2D */ 223275d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 223375d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 223475d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (p - vStart); 223575d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + (rp - rvStart[n]); 223675d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 223775d3a19aSMatthew G. Knepley ++m; 223875d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fMax)) { 223975d3a19aSMatthew G. Knepley /* Old interior faces add new faces and vertex */ 224075d3a19aSMatthew G. Knepley localPointsNew[m] = vStartNew + (vEnd - vStart) + (p - fStart); 224175d3a19aSMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + rdepthSizeOld[n*(depth+1)+0] + (rp - rfStart[n]); 224275d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 224375d3a19aSMatthew G. Knepley ++m; 224475d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r, ++m) { 224575d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (p - fStart)*2 + r; 224675d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rp - rfStart[n])*2 + r; 224775d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 224875d3a19aSMatthew G. Knepley } 224975d3a19aSMatthew G. Knepley } else if ((p >= fMax) && (p < fEnd)) { 225075d3a19aSMatthew G. Knepley /* Old hybrid faces stay the same */ 225175d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (fMax - fStart)*2 + (p - fMax); 225275d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rdepthMaxOld[n*(depth+1)+depth-1] - rfStart[n])*2 + (rp - rdepthMaxOld[n*(depth+1)+depth-1]); 225375d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 225475d3a19aSMatthew G. Knepley ++m; 225575d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cMax)) { 225675d3a19aSMatthew G. Knepley /* Old interior cells add new cells and interior faces */ 225775d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r, ++m) { 225875d3a19aSMatthew G. Knepley localPointsNew[m] = cStartNew + (p - cStart)*4 + r; 225975d3a19aSMatthew G. Knepley remotePointsNew[m].index = rcStartNew[n] + (rp - rcStart[n])*4 + r; 226075d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 226175d3a19aSMatthew G. Knepley } 226275d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r, ++m) { 226375d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (fMax - fStart)*2 + (p - cStart)*3 + r; 226475d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rdepthMaxOld[n*(depth+1)+depth-1] - rfStart[n])*2 + (rp - rcStart[n])*3 + r; 226575d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 226675d3a19aSMatthew G. Knepley } 226775d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cMax)) { 226875d3a19aSMatthew G. Knepley /* Old hybrid cells add new cells and hybrid face */ 226975d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r, ++m) { 227075d3a19aSMatthew G. Knepley localPointsNew[m] = cStartNew + (p - cStart)*4 + r; 227175d3a19aSMatthew G. Knepley remotePointsNew[m].index = rcStartNew[n] + (rp - rcStart[n])*4 + r; 227275d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 227375d3a19aSMatthew G. Knepley } 227475d3a19aSMatthew G. Knepley localPointsNew[m] = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (p - cMax); 227575d3a19aSMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rdepthMaxOld[n*(depth+1)+depth-1] - rfStart[n])*2 + (rdepthMaxOld[n*(depth+1)+depth] - rcStart[n])*3 + (rp - rdepthMaxOld[n*(depth+1)+depth]); 227675d3a19aSMatthew G. Knepley remotePointsNew[m].rank = rrank; 227775d3a19aSMatthew G. Knepley ++m; 227875d3a19aSMatthew G. Knepley } 227975d3a19aSMatthew G. Knepley break; 2280b5da9499SMatthew G. Knepley case 5: 2281b5da9499SMatthew G. Knepley /* Simplicial 3D */ 2282b5da9499SMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 2283b5da9499SMatthew G. Knepley /* Old vertices stay the same */ 2284b5da9499SMatthew G. Knepley localPointsNew[m] = vStartNew + (p - vStart); 2285b5da9499SMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + (rp - rvStart[n]); 2286b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2287b5da9499SMatthew G. Knepley ++m; 2288b5da9499SMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 2289b5da9499SMatthew G. Knepley /* Old edges add new edges and vertex */ 2290b5da9499SMatthew G. Knepley for (r = 0; r < 2; ++r, ++m) { 2291b5da9499SMatthew G. Knepley localPointsNew[m] = eStartNew + (p - eStart)*2 + r; 2292b5da9499SMatthew G. Knepley remotePointsNew[m].index = reStartNew[n] + (rp - reStart[n])*2 + r; 2293b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2294b5da9499SMatthew G. Knepley } 2295b5da9499SMatthew G. Knepley localPointsNew[m] = vStartNew + (vEnd - vStart) + (p - eStart); 2296b5da9499SMatthew G. Knepley remotePointsNew[m].index = rvStartNew[n] + rdepthSizeOld[n*(depth+1)+0] + (rp - reStart[n]); 2297b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2298b5da9499SMatthew G. Knepley ++m; 2299b5da9499SMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 2300b5da9499SMatthew G. Knepley /* Old faces add new faces and face edges */ 2301b5da9499SMatthew G. Knepley for (r = 0; r < 4; ++r, ++m) { 2302b5da9499SMatthew G. Knepley localPointsNew[m] = fStartNew + (p - fStart)*4 + r; 2303b5da9499SMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + (rp - rfStart[n])*4 + r; 2304b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2305b5da9499SMatthew G. Knepley } 2306b5da9499SMatthew G. Knepley for (r = 0; r < 3; ++r, ++m) { 2307b5da9499SMatthew G. Knepley localPointsNew[m] = eStartNew + (eEnd - eStart)*2 + (p - fStart)*3 + r; 2308b5da9499SMatthew G. Knepley remotePointsNew[m].index = reStartNew[n] + rdepthSizeOld[n*(depth+1)+1]*2 + (rp - rfStart[n])*3 + r; 2309b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2310b5da9499SMatthew G. Knepley } 2311b5da9499SMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 2312b5da9499SMatthew G. Knepley /* Old cells add new cells and interior faces and edges */ 2313b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r, ++m) { 2314b5da9499SMatthew G. Knepley localPointsNew[m] = cStartNew + (p - cStart)*8 + r; 2315b5da9499SMatthew G. Knepley remotePointsNew[m].index = rcStartNew[n] + (rp - rcStart[n])*8 + r; 2316b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2317b5da9499SMatthew G. Knepley } 2318b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r, ++m) { 2319b5da9499SMatthew G. Knepley localPointsNew[m] = fStartNew + (fEnd - fStart)*4 + (p - cStart)*8 + r; 2320b5da9499SMatthew G. Knepley remotePointsNew[m].index = rfStartNew[n] + rdepthSizeOld[n*(depth+1)+depth-1]*4 + (rp - rcStart[n])*8 + r; 2321b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2322b5da9499SMatthew G. Knepley } 2323b5da9499SMatthew G. Knepley for (r = 0; r < 1; ++r, ++m) { 2324b5da9499SMatthew G. Knepley localPointsNew[m] = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (p - cStart)*1 + r; 2325b5da9499SMatthew G. Knepley remotePointsNew[m].index = reStartNew[n] + rdepthSizeOld[n*(depth+1)+1]*2 + rdepthSizeOld[n*(depth+1)+depth-1]*3 + (rp - rcStart[n])*1 + r; 2326b5da9499SMatthew G. Knepley remotePointsNew[m].rank = rrank; 2327b5da9499SMatthew G. Knepley } 2328b5da9499SMatthew G. Knepley } 2329b5da9499SMatthew G. Knepley break; 233075d3a19aSMatthew G. Knepley default: 233175d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 233275d3a19aSMatthew G. Knepley } 233375d3a19aSMatthew G. Knepley } 233475d3a19aSMatthew G. Knepley ierr = ISRestoreIndices(processRanks, &neighbors);CHKERRQ(ierr); 233575d3a19aSMatthew G. Knepley ierr = ISDestroy(&processRanks);CHKERRQ(ierr); 233675d3a19aSMatthew G. Knepley ierr = PetscSFSetGraph(sfNew, pEndNew-pStartNew, numLeavesNew, localPointsNew, PETSC_OWN_POINTER, remotePointsNew, PETSC_OWN_POINTER);CHKERRQ(ierr); 233775d3a19aSMatthew G. Knepley ierr = PetscFree5(rdepthSize,rvStartNew,reStartNew,rfStartNew,rcStartNew);CHKERRQ(ierr); 233875d3a19aSMatthew G. Knepley ierr = PetscFree6(depthSizeOld,rdepthSizeOld,rvStart,reStart,rfStart,rcStart);CHKERRQ(ierr); 233975d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 234075d3a19aSMatthew G. Knepley } 234175d3a19aSMatthew G. Knepley 234275d3a19aSMatthew G. Knepley #undef __FUNCT__ 234375d3a19aSMatthew G. Knepley #define __FUNCT__ "CellRefinerCreateLabels" 234475d3a19aSMatthew G. Knepley PetscErrorCode CellRefinerCreateLabels(CellRefiner refiner, DM dm, PetscInt depthSize[], DM rdm) 234575d3a19aSMatthew G. Knepley { 234675d3a19aSMatthew G. Knepley PetscInt numLabels, l; 2347b5da9499SMatthew G. Knepley PetscInt depth, newp, cStart, cStartNew, cEnd, cMax, vStart, vStartNew, vEnd, vMax, fStart, fStartNew, fEnd, fMax, eStart, eStartNew, eEnd, eMax, r; 234875d3a19aSMatthew G. Knepley PetscErrorCode ierr; 234975d3a19aSMatthew G. Knepley 235075d3a19aSMatthew G. Knepley PetscFunctionBegin; 235175d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 0, &vStart, &vEnd);CHKERRQ(ierr); 235275d3a19aSMatthew G. Knepley ierr = DMPlexGetDepthStratum(dm, 1, &eStart, &eEnd);CHKERRQ(ierr); 235375d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 235475d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 2355d963de37SMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 2356d963de37SMatthew G. Knepley ierr = GetDepthStart_Private(depth, depthSize, &cStartNew, &fStartNew, &eStartNew, &vStartNew);CHKERRQ(ierr); 235775d3a19aSMatthew G. Knepley ierr = DMPlexGetNumLabels(dm, &numLabels);CHKERRQ(ierr); 235875d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, &fMax, &eMax, &vMax);CHKERRQ(ierr); 235975d3a19aSMatthew G. Knepley switch (refiner) { 236075d3a19aSMatthew G. Knepley case 3: 236175d3a19aSMatthew G. Knepley if (cMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No cell maximum specified in hybrid mesh"); 236275d3a19aSMatthew G. Knepley cMax = PetscMin(cEnd, cMax); 236375d3a19aSMatthew G. Knepley if (fMax < 0) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "No face maximum specified in hybrid mesh"); 236475d3a19aSMatthew G. Knepley fMax = PetscMin(fEnd, fMax); 236575d3a19aSMatthew G. Knepley } 236675d3a19aSMatthew G. Knepley for (l = 0; l < numLabels; ++l) { 236775d3a19aSMatthew G. Knepley DMLabel label, labelNew; 236875d3a19aSMatthew G. Knepley const char *lname; 236975d3a19aSMatthew G. Knepley PetscBool isDepth; 237075d3a19aSMatthew G. Knepley IS valueIS; 237175d3a19aSMatthew G. Knepley const PetscInt *values; 237275d3a19aSMatthew G. Knepley PetscInt numValues, val; 237375d3a19aSMatthew G. Knepley 237475d3a19aSMatthew G. Knepley ierr = DMPlexGetLabelName(dm, l, &lname);CHKERRQ(ierr); 237575d3a19aSMatthew G. Knepley ierr = PetscStrcmp(lname, "depth", &isDepth);CHKERRQ(ierr); 237675d3a19aSMatthew G. Knepley if (isDepth) continue; 237775d3a19aSMatthew G. Knepley ierr = DMPlexCreateLabel(rdm, lname);CHKERRQ(ierr); 237875d3a19aSMatthew G. Knepley ierr = DMPlexGetLabel(dm, lname, &label);CHKERRQ(ierr); 237975d3a19aSMatthew G. Knepley ierr = DMPlexGetLabel(rdm, lname, &labelNew);CHKERRQ(ierr); 238075d3a19aSMatthew G. Knepley ierr = DMLabelGetValueIS(label, &valueIS);CHKERRQ(ierr); 238175d3a19aSMatthew G. Knepley ierr = ISGetLocalSize(valueIS, &numValues);CHKERRQ(ierr); 238275d3a19aSMatthew G. Knepley ierr = ISGetIndices(valueIS, &values);CHKERRQ(ierr); 238375d3a19aSMatthew G. Knepley for (val = 0; val < numValues; ++val) { 238475d3a19aSMatthew G. Knepley IS pointIS; 238575d3a19aSMatthew G. Knepley const PetscInt *points; 238675d3a19aSMatthew G. Knepley PetscInt numPoints, n; 238775d3a19aSMatthew G. Knepley 238875d3a19aSMatthew G. Knepley ierr = DMLabelGetStratumIS(label, values[val], &pointIS);CHKERRQ(ierr); 238975d3a19aSMatthew G. Knepley ierr = ISGetLocalSize(pointIS, &numPoints);CHKERRQ(ierr); 239075d3a19aSMatthew G. Knepley ierr = ISGetIndices(pointIS, &points);CHKERRQ(ierr); 239175d3a19aSMatthew G. Knepley for (n = 0; n < numPoints; ++n) { 239275d3a19aSMatthew G. Knepley const PetscInt p = points[n]; 239375d3a19aSMatthew G. Knepley switch (refiner) { 239475d3a19aSMatthew G. Knepley case 1: 239575d3a19aSMatthew G. Knepley /* Simplicial 2D */ 239675d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 239775d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 239875d3a19aSMatthew G. Knepley newp = vStartNew + (p - vStart); 239975d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 240075d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 240175d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 240275d3a19aSMatthew G. Knepley newp = vStartNew + (vEnd - vStart) + (p - fStart); 240375d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 240475d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 240575d3a19aSMatthew G. Knepley newp = fStartNew + (p - fStart)*2 + r; 240675d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 240775d3a19aSMatthew G. Knepley } 240875d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 240975d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces */ 241075d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 241175d3a19aSMatthew G. Knepley newp = cStartNew + (p - cStart)*4 + r; 241275d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 241375d3a19aSMatthew G. Knepley } 241475d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 241575d3a19aSMatthew G. Knepley newp = fStartNew + (fEnd - fStart)*2 + (p - cStart)*3 + r; 241675d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 241775d3a19aSMatthew G. Knepley } 241875d3a19aSMatthew G. Knepley } 241975d3a19aSMatthew G. Knepley break; 242075d3a19aSMatthew G. Knepley case 2: 242175d3a19aSMatthew G. Knepley /* Hex 2D */ 242275d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 242375d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 242475d3a19aSMatthew G. Knepley newp = vStartNew + (p - vStart); 242575d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 242675d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 242775d3a19aSMatthew G. Knepley /* Old faces add new faces and vertex */ 242875d3a19aSMatthew G. Knepley newp = vStartNew + (vEnd - vStart) + (p - fStart); 242975d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 243075d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 243175d3a19aSMatthew G. Knepley newp = fStartNew + (p - fStart)*2 + r; 243275d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 243375d3a19aSMatthew G. Knepley } 243475d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 243575d3a19aSMatthew G. Knepley /* Old cells add new cells and interior faces and vertex */ 243675d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 243775d3a19aSMatthew G. Knepley newp = cStartNew + (p - cStart)*4 + r; 243875d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 243975d3a19aSMatthew G. Knepley } 244075d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 244175d3a19aSMatthew G. Knepley newp = fStartNew + (fEnd - fStart)*2 + (p - cStart)*4 + r; 244275d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 244375d3a19aSMatthew G. Knepley } 244475d3a19aSMatthew G. Knepley newp = vStartNew + (vEnd - vStart) + (fEnd - fStart) + (p - cStart); 244575d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 244675d3a19aSMatthew G. Knepley } 244775d3a19aSMatthew G. Knepley break; 244875d3a19aSMatthew G. Knepley case 3: 244975d3a19aSMatthew G. Knepley /* Hybrid simplicial 2D */ 245075d3a19aSMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 245175d3a19aSMatthew G. Knepley /* Old vertices stay the same */ 245275d3a19aSMatthew G. Knepley newp = vStartNew + (p - vStart); 245375d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 245475d3a19aSMatthew G. Knepley } else if ((p >= fStart) && (p < fMax)) { 245575d3a19aSMatthew G. Knepley /* Old interior faces add new faces and vertex */ 245675d3a19aSMatthew G. Knepley newp = vStartNew + (vEnd - vStart) + (p - fStart); 245775d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 245875d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 245975d3a19aSMatthew G. Knepley newp = fStartNew + (p - fStart)*2 + r; 246075d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 246175d3a19aSMatthew G. Knepley } 246275d3a19aSMatthew G. Knepley } else if ((p >= fMax) && (p < fEnd)) { 246375d3a19aSMatthew G. Knepley /* Old hybrid faces stay the same */ 246475d3a19aSMatthew G. Knepley newp = fStartNew + (fMax - fStart)*2 + (p - fMax); 246575d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 246675d3a19aSMatthew G. Knepley } else if ((p >= cStart) && (p < cMax)) { 246775d3a19aSMatthew G. Knepley /* Old interior cells add new cells and interior faces */ 246875d3a19aSMatthew G. Knepley for (r = 0; r < 4; ++r) { 246975d3a19aSMatthew G. Knepley newp = cStartNew + (p - cStart)*4 + r; 247075d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 247175d3a19aSMatthew G. Knepley } 247275d3a19aSMatthew G. Knepley for (r = 0; r < 3; ++r) { 247375d3a19aSMatthew G. Knepley newp = fStartNew + (fEnd - fStart)*2 + (p - cStart)*3 + r; 247475d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 247575d3a19aSMatthew G. Knepley } 247675d3a19aSMatthew G. Knepley } else if ((p >= cMax) && (p < cEnd)) { 247775d3a19aSMatthew G. Knepley /* Old hybrid cells add new cells and hybrid face */ 247875d3a19aSMatthew G. Knepley for (r = 0; r < 2; ++r) { 247975d3a19aSMatthew G. Knepley newp = cStartNew + (cMax - cStart)*4 + (p - cMax)*2 + r; 248075d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 248175d3a19aSMatthew G. Knepley } 248275d3a19aSMatthew G. Knepley newp = fStartNew + (fMax - fStart)*2 + (cMax - cStart)*3 + (p - cMax); 248375d3a19aSMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 248475d3a19aSMatthew G. Knepley } 248575d3a19aSMatthew G. Knepley break; 2486b5da9499SMatthew G. Knepley case 5: 2487b5da9499SMatthew G. Knepley /* Simplicial 3D */ 2488b5da9499SMatthew G. Knepley if ((p >= vStart) && (p < vEnd)) { 2489b5da9499SMatthew G. Knepley /* Old vertices stay the same */ 2490b5da9499SMatthew G. Knepley newp = vStartNew + (p - vStart); 2491b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2492b5da9499SMatthew G. Knepley } else if ((p >= eStart) && (p < eEnd)) { 2493b5da9499SMatthew G. Knepley /* Old edges add new edges and vertex */ 2494b5da9499SMatthew G. Knepley for (r = 0; r < 2; ++r) { 2495b5da9499SMatthew G. Knepley newp = eStartNew + (p - eStart)*2 + r; 2496b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2497b5da9499SMatthew G. Knepley } 2498b5da9499SMatthew G. Knepley newp = vStartNew + (vEnd - vStart) + (p - eStart); 2499b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2500b5da9499SMatthew G. Knepley } else if ((p >= fStart) && (p < fEnd)) { 2501b5da9499SMatthew G. Knepley /* Old faces add new faces and edges */ 2502b5da9499SMatthew G. Knepley for (r = 0; r < 4; ++r) { 2503b5da9499SMatthew G. Knepley newp = fStartNew + (p - fStart)*4 + r; 2504b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2505b5da9499SMatthew G. Knepley } 2506b5da9499SMatthew G. Knepley for (r = 0; r < 3; ++r) { 2507b5da9499SMatthew G. Knepley newp = eStartNew + (eEnd - eStart)*2 + (p - fStart)*3 + r; 2508b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2509b5da9499SMatthew G. Knepley } 2510b5da9499SMatthew G. Knepley } else if ((p >= cStart) && (p < cEnd)) { 2511b5da9499SMatthew G. Knepley /* Old cells add new cells and interior faces and edges */ 2512b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r) { 2513b5da9499SMatthew G. Knepley newp = cStartNew + (p - cStart)*8 + r; 2514b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2515b5da9499SMatthew G. Knepley } 2516b5da9499SMatthew G. Knepley for (r = 0; r < 8; ++r) { 2517b5da9499SMatthew G. Knepley newp = fStartNew + (fEnd - fStart)*4 + (p - cStart)*8 + r; 2518b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2519b5da9499SMatthew G. Knepley } 2520b5da9499SMatthew G. Knepley for (r = 0; r < 1; ++r) { 2521b5da9499SMatthew G. Knepley newp = eStartNew + (eEnd - eStart)*2 + (fEnd - fStart)*3 + (p - cStart)*1 + r; 2522b5da9499SMatthew G. Knepley ierr = DMLabelSetValue(labelNew, newp, values[val]);CHKERRQ(ierr); 2523b5da9499SMatthew G. Knepley } 2524b5da9499SMatthew G. Knepley } 2525b5da9499SMatthew G. Knepley break; 252675d3a19aSMatthew G. Knepley default: 252775d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown cell refiner %d", refiner); 252875d3a19aSMatthew G. Knepley } 252975d3a19aSMatthew G. Knepley } 253075d3a19aSMatthew G. Knepley ierr = ISRestoreIndices(pointIS, &points);CHKERRQ(ierr); 253175d3a19aSMatthew G. Knepley ierr = ISDestroy(&pointIS);CHKERRQ(ierr); 253275d3a19aSMatthew G. Knepley } 253375d3a19aSMatthew G. Knepley ierr = ISRestoreIndices(valueIS, &values);CHKERRQ(ierr); 253475d3a19aSMatthew G. Knepley ierr = ISDestroy(&valueIS);CHKERRQ(ierr); 253575d3a19aSMatthew G. Knepley if (0) { 253675d3a19aSMatthew G. Knepley ierr = PetscViewerASCIISynchronizedAllow(PETSC_VIEWER_STDOUT_WORLD, PETSC_TRUE);CHKERRQ(ierr); 253775d3a19aSMatthew G. Knepley ierr = DMLabelView(labelNew, PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); 253875d3a19aSMatthew G. Knepley ierr = PetscViewerFlush(PETSC_VIEWER_STDOUT_WORLD);CHKERRQ(ierr); 253975d3a19aSMatthew G. Knepley } 254075d3a19aSMatthew G. Knepley } 254175d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 254275d3a19aSMatthew G. Knepley } 254375d3a19aSMatthew G. Knepley 254475d3a19aSMatthew G. Knepley #undef __FUNCT__ 2545509c9b89SMatthew G. Knepley #define __FUNCT__ "DMPlexRefineUniform_Internal" 254675d3a19aSMatthew G. Knepley /* This will only work for interpolated meshes */ 2547509c9b89SMatthew G. Knepley PetscErrorCode DMPlexRefineUniform_Internal(DM dm, CellRefiner cellRefiner, DM *dmRefined) 254875d3a19aSMatthew G. Knepley { 254975d3a19aSMatthew G. Knepley DM rdm; 255075d3a19aSMatthew G. Knepley PetscInt *depthSize; 255175d3a19aSMatthew G. Knepley PetscInt dim, depth = 0, d, pStart = 0, pEnd = 0; 255275d3a19aSMatthew G. Knepley PetscErrorCode ierr; 255375d3a19aSMatthew G. Knepley 255475d3a19aSMatthew G. Knepley PetscFunctionBegin; 255575d3a19aSMatthew G. Knepley ierr = DMCreate(PetscObjectComm((PetscObject)dm), &rdm);CHKERRQ(ierr); 255675d3a19aSMatthew G. Knepley ierr = DMSetType(rdm, DMPLEX);CHKERRQ(ierr); 255775d3a19aSMatthew G. Knepley ierr = DMPlexGetDimension(dm, &dim);CHKERRQ(ierr); 255875d3a19aSMatthew G. Knepley ierr = DMPlexSetDimension(rdm, dim);CHKERRQ(ierr); 255975d3a19aSMatthew G. Knepley /* Calculate number of new points of each depth */ 256075d3a19aSMatthew G. Knepley ierr = DMPlexGetDepth(dm, &depth);CHKERRQ(ierr); 256175d3a19aSMatthew G. Knepley ierr = PetscMalloc((depth+1) * sizeof(PetscInt), &depthSize);CHKERRQ(ierr); 256275d3a19aSMatthew G. Knepley ierr = PetscMemzero(depthSize, (depth+1) * sizeof(PetscInt));CHKERRQ(ierr); 256375d3a19aSMatthew G. Knepley ierr = CellRefinerGetSizes(cellRefiner, dm, depthSize);CHKERRQ(ierr); 256475d3a19aSMatthew G. Knepley /* Step 1: Set chart */ 256575d3a19aSMatthew G. Knepley for (d = 0; d <= depth; ++d) pEnd += depthSize[d]; 256675d3a19aSMatthew G. Knepley ierr = DMPlexSetChart(rdm, pStart, pEnd);CHKERRQ(ierr); 256775d3a19aSMatthew G. Knepley /* Step 2: Set cone/support sizes */ 256875d3a19aSMatthew G. Knepley ierr = CellRefinerSetConeSizes(cellRefiner, dm, depthSize, rdm);CHKERRQ(ierr); 256975d3a19aSMatthew G. Knepley /* Step 3: Setup refined DM */ 257075d3a19aSMatthew G. Knepley ierr = DMSetUp(rdm);CHKERRQ(ierr); 257175d3a19aSMatthew G. Knepley /* Step 4: Set cones and supports */ 257275d3a19aSMatthew G. Knepley ierr = CellRefinerSetCones(cellRefiner, dm, depthSize, rdm);CHKERRQ(ierr); 257375d3a19aSMatthew G. Knepley /* Step 5: Stratify */ 257475d3a19aSMatthew G. Knepley ierr = DMPlexStratify(rdm);CHKERRQ(ierr); 257575d3a19aSMatthew G. Knepley /* Step 6: Set coordinates for vertices */ 257675d3a19aSMatthew G. Knepley ierr = CellRefinerSetCoordinates(cellRefiner, dm, depthSize, rdm);CHKERRQ(ierr); 257775d3a19aSMatthew G. Knepley /* Step 7: Create pointSF */ 257875d3a19aSMatthew G. Knepley ierr = CellRefinerCreateSF(cellRefiner, dm, depthSize, rdm);CHKERRQ(ierr); 257975d3a19aSMatthew G. Knepley /* Step 8: Create labels */ 258075d3a19aSMatthew G. Knepley ierr = CellRefinerCreateLabels(cellRefiner, dm, depthSize, rdm);CHKERRQ(ierr); 258175d3a19aSMatthew G. Knepley ierr = PetscFree(depthSize);CHKERRQ(ierr); 258275d3a19aSMatthew G. Knepley 258375d3a19aSMatthew G. Knepley *dmRefined = rdm; 258475d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 258575d3a19aSMatthew G. Knepley } 258675d3a19aSMatthew G. Knepley 258775d3a19aSMatthew G. Knepley #undef __FUNCT__ 258875d3a19aSMatthew G. Knepley #define __FUNCT__ "DMPlexSetRefinementUniform" 258975d3a19aSMatthew G. Knepley PetscErrorCode DMPlexSetRefinementUniform(DM dm, PetscBool refinementUniform) 259075d3a19aSMatthew G. Knepley { 259175d3a19aSMatthew G. Knepley DM_Plex *mesh = (DM_Plex*) dm->data; 259275d3a19aSMatthew G. Knepley 259375d3a19aSMatthew G. Knepley PetscFunctionBegin; 259475d3a19aSMatthew G. Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 259575d3a19aSMatthew G. Knepley mesh->refinementUniform = refinementUniform; 259675d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 259775d3a19aSMatthew G. Knepley } 259875d3a19aSMatthew G. Knepley 259975d3a19aSMatthew G. Knepley #undef __FUNCT__ 260075d3a19aSMatthew G. Knepley #define __FUNCT__ "DMPlexGetRefinementUniform" 260175d3a19aSMatthew G. Knepley PetscErrorCode DMPlexGetRefinementUniform(DM dm, PetscBool *refinementUniform) 260275d3a19aSMatthew G. Knepley { 260375d3a19aSMatthew G. Knepley DM_Plex *mesh = (DM_Plex*) dm->data; 260475d3a19aSMatthew G. Knepley 260575d3a19aSMatthew G. Knepley PetscFunctionBegin; 260675d3a19aSMatthew G. Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 260775d3a19aSMatthew G. Knepley PetscValidPointer(refinementUniform, 2); 260875d3a19aSMatthew G. Knepley *refinementUniform = mesh->refinementUniform; 260975d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 261075d3a19aSMatthew G. Knepley } 261175d3a19aSMatthew G. Knepley 261275d3a19aSMatthew G. Knepley #undef __FUNCT__ 261375d3a19aSMatthew G. Knepley #define __FUNCT__ "DMPlexSetRefinementLimit" 261475d3a19aSMatthew G. Knepley PetscErrorCode DMPlexSetRefinementLimit(DM dm, PetscReal refinementLimit) 261575d3a19aSMatthew G. Knepley { 261675d3a19aSMatthew G. Knepley DM_Plex *mesh = (DM_Plex*) dm->data; 261775d3a19aSMatthew G. Knepley 261875d3a19aSMatthew G. Knepley PetscFunctionBegin; 261975d3a19aSMatthew G. Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 262075d3a19aSMatthew G. Knepley mesh->refinementLimit = refinementLimit; 262175d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 262275d3a19aSMatthew G. Knepley } 262375d3a19aSMatthew G. Knepley 262475d3a19aSMatthew G. Knepley #undef __FUNCT__ 262575d3a19aSMatthew G. Knepley #define __FUNCT__ "DMPlexGetRefinementLimit" 262675d3a19aSMatthew G. Knepley PetscErrorCode DMPlexGetRefinementLimit(DM dm, PetscReal *refinementLimit) 262775d3a19aSMatthew G. Knepley { 262875d3a19aSMatthew G. Knepley DM_Plex *mesh = (DM_Plex*) dm->data; 262975d3a19aSMatthew G. Knepley 263075d3a19aSMatthew G. Knepley PetscFunctionBegin; 263175d3a19aSMatthew G. Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 263275d3a19aSMatthew G. Knepley PetscValidPointer(refinementLimit, 2); 263375d3a19aSMatthew G. Knepley /* if (mesh->refinementLimit < 0) = getMaxVolume()/2.0; */ 263475d3a19aSMatthew G. Knepley *refinementLimit = mesh->refinementLimit; 263575d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 263675d3a19aSMatthew G. Knepley } 263775d3a19aSMatthew G. Knepley 263875d3a19aSMatthew G. Knepley #undef __FUNCT__ 2639509c9b89SMatthew G. Knepley #define __FUNCT__ "DMPlexGetCellRefiner_Internal" 2640509c9b89SMatthew G. Knepley PetscErrorCode DMPlexGetCellRefiner_Internal(DM dm, CellRefiner *cellRefiner) 264175d3a19aSMatthew G. Knepley { 264275d3a19aSMatthew G. Knepley PetscInt dim, cStart, coneSize, cMax; 264375d3a19aSMatthew G. Knepley PetscErrorCode ierr; 264475d3a19aSMatthew G. Knepley 264575d3a19aSMatthew G. Knepley PetscFunctionBegin; 264675d3a19aSMatthew G. Knepley ierr = DMPlexGetDimension(dm, &dim);CHKERRQ(ierr); 264775d3a19aSMatthew G. Knepley ierr = DMPlexGetHeightStratum(dm, 0, &cStart, NULL);CHKERRQ(ierr); 264875d3a19aSMatthew G. Knepley ierr = DMPlexGetConeSize(dm, cStart, &coneSize);CHKERRQ(ierr); 264975d3a19aSMatthew G. Knepley ierr = DMPlexGetHybridBounds(dm, &cMax, NULL, NULL, NULL);CHKERRQ(ierr); 265075d3a19aSMatthew G. Knepley switch (dim) { 265175d3a19aSMatthew G. Knepley case 2: 265275d3a19aSMatthew G. Knepley switch (coneSize) { 265375d3a19aSMatthew G. Knepley case 3: 265475d3a19aSMatthew G. Knepley if (cMax >= 0) *cellRefiner = 3; /* Hybrid */ 265575d3a19aSMatthew G. Knepley else *cellRefiner = 1; /* Triangular */ 265675d3a19aSMatthew G. Knepley break; 265775d3a19aSMatthew G. Knepley case 4: 265875d3a19aSMatthew G. Knepley if (cMax >= 0) *cellRefiner = 4; /* Hybrid */ 265975d3a19aSMatthew G. Knepley else *cellRefiner = 2; /* Quadrilateral */ 266075d3a19aSMatthew G. Knepley break; 266175d3a19aSMatthew G. Knepley default: 266275d3a19aSMatthew G. Knepley SETERRQ2(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown coneSize %d in dimension %d for cell refiner", coneSize, dim); 266375d3a19aSMatthew G. Knepley } 266475d3a19aSMatthew G. Knepley break; 2665b5da9499SMatthew G. Knepley case 3: 2666b5da9499SMatthew G. Knepley switch (coneSize) { 2667b5da9499SMatthew G. Knepley case 4: 2668b5da9499SMatthew G. Knepley if (cMax >= 0) *cellRefiner = 7; /* Hybrid */ 2669b5da9499SMatthew G. Knepley else *cellRefiner = 5; /* Tetrahedral */ 2670b5da9499SMatthew G. Knepley break; 2671b5da9499SMatthew G. Knepley default: 2672b5da9499SMatthew G. Knepley SETERRQ2(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown coneSize %d in dimension %d for cell refiner", coneSize, dim); 2673b5da9499SMatthew G. Knepley } 2674b5da9499SMatthew G. Knepley break; 267575d3a19aSMatthew G. Knepley default: 267675d3a19aSMatthew G. Knepley SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Unknown dimension %d for cell refiner", dim); 267775d3a19aSMatthew G. Knepley } 267875d3a19aSMatthew G. Knepley PetscFunctionReturn(0); 267975d3a19aSMatthew G. Knepley } 2680