147c6ae99SBarry Smith 247c6ae99SBarry Smith /* 347c6ae99SBarry Smith Code for manipulating distributed regular arrays in parallel. 447c6ae99SBarry Smith */ 547c6ae99SBarry Smith 64035e84dSBarry Smith #include <petsc-private/dmdaimpl.h> /*I "petscdmda.h" I*/ 7b2fff234SMatthew G. Knepley #include <petscbt.h> 80c312b8eSJed Brown #include <petscsf.h> 947c6ae99SBarry Smith 1047c6ae99SBarry Smith /* 11e3c5b3baSBarry Smith This allows the DMDA vectors to properly tell MATLAB their dimensions 1247c6ae99SBarry Smith */ 1347c6ae99SBarry Smith #if defined(PETSC_HAVE_MATLAB_ENGINE) 14c6db04a5SJed Brown #include <engine.h> /* MATLAB include file */ 15c6db04a5SJed Brown #include <mex.h> /* MATLAB include file */ 1647c6ae99SBarry Smith #undef __FUNCT__ 1747c6ae99SBarry Smith #define __FUNCT__ "VecMatlabEnginePut_DA2d" 181e6b0712SBarry Smith static PetscErrorCode VecMatlabEnginePut_DA2d(PetscObject obj,void *mengine) 1947c6ae99SBarry Smith { 2047c6ae99SBarry Smith PetscErrorCode ierr; 2147c6ae99SBarry Smith PetscInt n,m; 2247c6ae99SBarry Smith Vec vec = (Vec)obj; 2347c6ae99SBarry Smith PetscScalar *array; 2447c6ae99SBarry Smith mxArray *mat; 259a42bb27SBarry Smith DM da; 2647c6ae99SBarry Smith 2747c6ae99SBarry Smith PetscFunctionBegin; 28c688c046SMatthew G Knepley ierr = VecGetDM(vec, &da);CHKERRQ(ierr); 29ce94432eSBarry Smith if (!da) SETERRQ(PetscObjectComm((PetscObject)vec),PETSC_ERR_ARG_WRONGSTATE,"Vector not associated with a DMDA"); 30aa219208SBarry Smith ierr = DMDAGetGhostCorners(da,0,0,0,&m,&n,0);CHKERRQ(ierr); 3147c6ae99SBarry Smith 3247c6ae99SBarry Smith ierr = VecGetArray(vec,&array);CHKERRQ(ierr); 3347c6ae99SBarry Smith #if !defined(PETSC_USE_COMPLEX) 3447c6ae99SBarry Smith mat = mxCreateDoubleMatrix(m,n,mxREAL); 3547c6ae99SBarry Smith #else 3647c6ae99SBarry Smith mat = mxCreateDoubleMatrix(m,n,mxCOMPLEX); 3747c6ae99SBarry Smith #endif 3847c6ae99SBarry Smith ierr = PetscMemcpy(mxGetPr(mat),array,n*m*sizeof(PetscScalar));CHKERRQ(ierr); 3947c6ae99SBarry Smith ierr = PetscObjectName(obj);CHKERRQ(ierr); 4047c6ae99SBarry Smith engPutVariable((Engine*)mengine,obj->name,mat); 4147c6ae99SBarry Smith 4247c6ae99SBarry Smith ierr = VecRestoreArray(vec,&array);CHKERRQ(ierr); 4347c6ae99SBarry Smith PetscFunctionReturn(0); 4447c6ae99SBarry Smith } 4547c6ae99SBarry Smith #endif 4647c6ae99SBarry Smith 4747c6ae99SBarry Smith 4847c6ae99SBarry Smith #undef __FUNCT__ 49564755cdSBarry Smith #define __FUNCT__ "DMCreateLocalVector_DA" 507087cfbeSBarry Smith PetscErrorCode DMCreateLocalVector_DA(DM da,Vec *g) 5147c6ae99SBarry Smith { 5247c6ae99SBarry Smith PetscErrorCode ierr; 5347c6ae99SBarry Smith DM_DA *dd = (DM_DA*)da->data; 5447c6ae99SBarry Smith 5547c6ae99SBarry Smith PetscFunctionBegin; 5647c6ae99SBarry Smith PetscValidHeaderSpecific(da,DM_CLASSID,1); 5747c6ae99SBarry Smith PetscValidPointer(g,2); 5811689aebSJed Brown if (da->defaultSection) { 5911689aebSJed Brown ierr = DMCreateLocalVector_Section_Private(da,g);CHKERRQ(ierr); 6011689aebSJed Brown } else { 6147c6ae99SBarry Smith ierr = VecCreate(PETSC_COMM_SELF,g);CHKERRQ(ierr); 6247c6ae99SBarry Smith ierr = VecSetSizes(*g,dd->nlocal,PETSC_DETERMINE);CHKERRQ(ierr); 6347c6ae99SBarry Smith ierr = VecSetBlockSize(*g,dd->w);CHKERRQ(ierr); 64401ddaa8SBarry Smith ierr = VecSetType(*g,da->vectype);CHKERRQ(ierr); 65c688c046SMatthew G Knepley ierr = VecSetDM(*g, da);CHKERRQ(ierr); 6647c6ae99SBarry Smith #if defined(PETSC_HAVE_MATLAB_ENGINE) 6747c6ae99SBarry Smith if (dd->w == 1 && dd->dim == 2) { 68bdf89e91SBarry Smith ierr = PetscObjectComposeFunction((PetscObject)*g,"PetscMatlabEnginePut_C",VecMatlabEnginePut_DA2d);CHKERRQ(ierr); 6947c6ae99SBarry Smith } 7047c6ae99SBarry Smith #endif 7111689aebSJed Brown } 7247c6ae99SBarry Smith PetscFunctionReturn(0); 7347c6ae99SBarry Smith } 7447c6ae99SBarry Smith 75a66d4d66SMatthew G Knepley #undef __FUNCT__ 7657459e9aSMatthew G Knepley #define __FUNCT__ "DMDAGetNumCells" 77*e42e3c58SMatthew G. Knepley PetscErrorCode DMDAGetNumCells(DM dm, PetscInt *numCellsX, PetscInt *numCellsY, PetscInt *numCellsZ, PetscInt *numCells) 7857459e9aSMatthew G Knepley { 7957459e9aSMatthew G Knepley DM_DA *da = (DM_DA*) dm->data; 8057459e9aSMatthew G Knepley const PetscInt dim = da->dim; 8157459e9aSMatthew G Knepley const PetscInt mx = (da->Xe - da->Xs)/da->w, my = da->Ye - da->Ys, mz = da->Ze - da->Zs; 8257459e9aSMatthew G Knepley const PetscInt nC = (mx)*(dim > 1 ? (my)*(dim > 2 ? (mz) : 1) : 1); 8357459e9aSMatthew G Knepley 8457459e9aSMatthew G Knepley PetscFunctionBegin; 85*e42e3c58SMatthew G. Knepley if (numCellsX) { 86*e42e3c58SMatthew G. Knepley PetscValidIntPointer(numCellsX,2); 87*e42e3c58SMatthew G. Knepley *numCellsX = mx; 88*e42e3c58SMatthew G. Knepley } 89*e42e3c58SMatthew G. Knepley if (numCellsY) { 90*e42e3c58SMatthew G. Knepley PetscValidIntPointer(numCellsX,3); 91*e42e3c58SMatthew G. Knepley *numCellsY = my; 92*e42e3c58SMatthew G. Knepley } 93*e42e3c58SMatthew G. Knepley if (numCellsZ) { 94*e42e3c58SMatthew G. Knepley PetscValidIntPointer(numCellsX,4); 95*e42e3c58SMatthew G. Knepley *numCellsZ = mz; 96*e42e3c58SMatthew G. Knepley } 9757459e9aSMatthew G Knepley if (numCells) { 98*e42e3c58SMatthew G. Knepley PetscValidIntPointer(numCells,5); 9957459e9aSMatthew G Knepley *numCells = nC; 10057459e9aSMatthew G Knepley } 10157459e9aSMatthew G Knepley PetscFunctionReturn(0); 10257459e9aSMatthew G Knepley } 10357459e9aSMatthew G Knepley 10457459e9aSMatthew G Knepley #undef __FUNCT__ 10557459e9aSMatthew G Knepley #define __FUNCT__ "DMDAGetNumVertices" 10657459e9aSMatthew G Knepley PetscErrorCode DMDAGetNumVertices(DM dm, PetscInt *numVerticesX, PetscInt *numVerticesY, PetscInt *numVerticesZ, PetscInt *numVertices) 10757459e9aSMatthew G Knepley { 10857459e9aSMatthew G Knepley DM_DA *da = (DM_DA*) dm->data; 10957459e9aSMatthew G Knepley const PetscInt dim = da->dim; 11057459e9aSMatthew G Knepley const PetscInt mx = (da->Xe - da->Xs)/da->w, my = da->Ye - da->Ys, mz = da->Ze - da->Zs; 11157459e9aSMatthew G Knepley const PetscInt nVx = mx+1; 11257459e9aSMatthew G Knepley const PetscInt nVy = dim > 1 ? (my+1) : 1; 11357459e9aSMatthew G Knepley const PetscInt nVz = dim > 2 ? (mz+1) : 1; 11457459e9aSMatthew G Knepley const PetscInt nV = nVx*nVy*nVz; 11557459e9aSMatthew G Knepley 11657459e9aSMatthew G Knepley PetscFunctionBegin; 11757459e9aSMatthew G Knepley if (numVerticesX) { 11857459e9aSMatthew G Knepley PetscValidIntPointer(numVerticesX,2); 11957459e9aSMatthew G Knepley *numVerticesX = nVx; 12057459e9aSMatthew G Knepley } 12157459e9aSMatthew G Knepley if (numVerticesY) { 12257459e9aSMatthew G Knepley PetscValidIntPointer(numVerticesY,3); 12357459e9aSMatthew G Knepley *numVerticesY = nVy; 12457459e9aSMatthew G Knepley } 12557459e9aSMatthew G Knepley if (numVerticesZ) { 12657459e9aSMatthew G Knepley PetscValidIntPointer(numVerticesZ,4); 12757459e9aSMatthew G Knepley *numVerticesZ = nVz; 12857459e9aSMatthew G Knepley } 12957459e9aSMatthew G Knepley if (numVertices) { 13057459e9aSMatthew G Knepley PetscValidIntPointer(numVertices,5); 13157459e9aSMatthew G Knepley *numVertices = nV; 13257459e9aSMatthew G Knepley } 13357459e9aSMatthew G Knepley PetscFunctionReturn(0); 13457459e9aSMatthew G Knepley } 13557459e9aSMatthew G Knepley 13657459e9aSMatthew G Knepley #undef __FUNCT__ 13757459e9aSMatthew G Knepley #define __FUNCT__ "DMDAGetNumFaces" 13857459e9aSMatthew G Knepley PetscErrorCode DMDAGetNumFaces(DM dm, PetscInt *numXFacesX, PetscInt *numXFaces, PetscInt *numYFacesY, PetscInt *numYFaces, PetscInt *numZFacesZ, PetscInt *numZFaces) 13957459e9aSMatthew G Knepley { 14057459e9aSMatthew G Knepley DM_DA *da = (DM_DA*) dm->data; 14157459e9aSMatthew G Knepley const PetscInt dim = da->dim; 14257459e9aSMatthew G Knepley const PetscInt mx = (da->Xe - da->Xs)/da->w, my = da->Ye - da->Ys, mz = da->Ze - da->Zs; 14357459e9aSMatthew G Knepley const PetscInt nxF = (dim > 1 ? (my)*(dim > 2 ? (mz) : 1) : 1); 14457459e9aSMatthew G Knepley const PetscInt nXF = (mx+1)*nxF; 14557459e9aSMatthew G Knepley const PetscInt nyF = mx*(dim > 2 ? mz : 1); 14657459e9aSMatthew G Knepley const PetscInt nYF = dim > 1 ? (my+1)*nyF : 0; 14757459e9aSMatthew G Knepley const PetscInt nzF = mx*(dim > 1 ? my : 0); 14857459e9aSMatthew G Knepley const PetscInt nZF = dim > 2 ? (mz+1)*nzF : 0; 14957459e9aSMatthew G Knepley 15057459e9aSMatthew G Knepley PetscFunctionBegin; 15157459e9aSMatthew G Knepley if (numXFacesX) { 15257459e9aSMatthew G Knepley PetscValidIntPointer(numXFacesX,2); 15357459e9aSMatthew G Knepley *numXFacesX = nxF; 15457459e9aSMatthew G Knepley } 15557459e9aSMatthew G Knepley if (numXFaces) { 15657459e9aSMatthew G Knepley PetscValidIntPointer(numXFaces,3); 15757459e9aSMatthew G Knepley *numXFaces = nXF; 15857459e9aSMatthew G Knepley } 15957459e9aSMatthew G Knepley if (numYFacesY) { 16057459e9aSMatthew G Knepley PetscValidIntPointer(numYFacesY,4); 16157459e9aSMatthew G Knepley *numYFacesY = nyF; 16257459e9aSMatthew G Knepley } 16357459e9aSMatthew G Knepley if (numYFaces) { 16457459e9aSMatthew G Knepley PetscValidIntPointer(numYFaces,5); 16557459e9aSMatthew G Knepley *numYFaces = nYF; 16657459e9aSMatthew G Knepley } 16757459e9aSMatthew G Knepley if (numZFacesZ) { 16857459e9aSMatthew G Knepley PetscValidIntPointer(numZFacesZ,6); 16957459e9aSMatthew G Knepley *numZFacesZ = nzF; 17057459e9aSMatthew G Knepley } 17157459e9aSMatthew G Knepley if (numZFaces) { 17257459e9aSMatthew G Knepley PetscValidIntPointer(numZFaces,7); 17357459e9aSMatthew G Knepley *numZFaces = nZF; 17457459e9aSMatthew G Knepley } 17557459e9aSMatthew G Knepley PetscFunctionReturn(0); 17657459e9aSMatthew G Knepley } 17757459e9aSMatthew G Knepley 17857459e9aSMatthew G Knepley #undef __FUNCT__ 17957459e9aSMatthew G Knepley #define __FUNCT__ "DMDAGetHeightStratum" 18057459e9aSMatthew G Knepley PetscErrorCode DMDAGetHeightStratum(DM dm, PetscInt height, PetscInt *pStart, PetscInt *pEnd) 18157459e9aSMatthew G Knepley { 18257459e9aSMatthew G Knepley DM_DA *da = (DM_DA*) dm->data; 18357459e9aSMatthew G Knepley const PetscInt dim = da->dim; 18457459e9aSMatthew G Knepley PetscInt nC, nV, nXF, nYF, nZF; 18557459e9aSMatthew G Knepley PetscErrorCode ierr; 18657459e9aSMatthew G Knepley 18757459e9aSMatthew G Knepley PetscFunctionBegin; 1888865f1eaSKarl Rupp if (pStart) PetscValidIntPointer(pStart,3); 1898865f1eaSKarl Rupp if (pEnd) PetscValidIntPointer(pEnd,4); 190*e42e3c58SMatthew G. Knepley ierr = DMDAGetNumCells(dm, NULL, NULL, NULL, &nC);CHKERRQ(ierr); 1910298fd71SBarry Smith ierr = DMDAGetNumVertices(dm, NULL, NULL, NULL, &nV);CHKERRQ(ierr); 1920298fd71SBarry Smith ierr = DMDAGetNumFaces(dm, NULL, &nXF, NULL, &nYF, NULL, &nZF);CHKERRQ(ierr); 19357459e9aSMatthew G Knepley if (height == 0) { 19457459e9aSMatthew G Knepley /* Cells */ 1958865f1eaSKarl Rupp if (pStart) *pStart = 0; 1968865f1eaSKarl Rupp if (pEnd) *pEnd = nC; 19757459e9aSMatthew G Knepley } else if (height == 1) { 19857459e9aSMatthew G Knepley /* Faces */ 1998865f1eaSKarl Rupp if (pStart) *pStart = nC+nV; 2008865f1eaSKarl Rupp if (pEnd) *pEnd = nC+nV+nXF+nYF+nZF; 20157459e9aSMatthew G Knepley } else if (height == dim) { 20257459e9aSMatthew G Knepley /* Vertices */ 2038865f1eaSKarl Rupp if (pStart) *pStart = nC; 2048865f1eaSKarl Rupp if (pEnd) *pEnd = nC+nV; 20557459e9aSMatthew G Knepley } else if (height < 0) { 20657459e9aSMatthew G Knepley /* All points */ 2078865f1eaSKarl Rupp if (pStart) *pStart = 0; 2088865f1eaSKarl Rupp if (pEnd) *pEnd = nC+nV+nXF+nYF+nZF; 20982f516ccSBarry Smith } else SETERRQ1(PetscObjectComm((PetscObject)dm), PETSC_ERR_ARG_OUTOFRANGE, "No points of height %d in the DA", height); 21057459e9aSMatthew G Knepley PetscFunctionReturn(0); 21157459e9aSMatthew G Knepley } 21257459e9aSMatthew G Knepley 21357459e9aSMatthew G Knepley #undef __FUNCT__ 214a66d4d66SMatthew G Knepley #define __FUNCT__ "DMDACreateSection" 215a66d4d66SMatthew G Knepley /*@C 216a66d4d66SMatthew G Knepley DMDACreateSection - Create a PetscSection inside the DMDA that describes data layout. This allows multiple fields with 217a66d4d66SMatthew G Knepley different numbers of dofs on vertices, cells, and faces in each direction. 218a66d4d66SMatthew G Knepley 219a66d4d66SMatthew G Knepley Input Parameters: 220a66d4d66SMatthew G Knepley + dm- The DMDA 221a66d4d66SMatthew G Knepley . numFields - The number of fields 2220298fd71SBarry Smith . numComp - The number of components in each field, or NULL for 1 2230298fd71SBarry Smith . numVertexDof - The number of dofs per vertex for each field, or NULL 2240298fd71SBarry Smith . numFaceDof - The number of dofs per face for each field and direction, or NULL 2250298fd71SBarry Smith - numCellDof - The number of dofs per cell for each field, or NULL 226a66d4d66SMatthew G Knepley 227a66d4d66SMatthew G Knepley Level: developer 228a66d4d66SMatthew G Knepley 229a66d4d66SMatthew G Knepley Note: 230a66d4d66SMatthew G Knepley The default DMDA numbering is as follows: 231a66d4d66SMatthew G Knepley 232a66d4d66SMatthew G Knepley - Cells: [0, nC) 233a66d4d66SMatthew G Knepley - Vertices: [nC, nC+nV) 23488ed4aceSMatthew G Knepley - X-Faces: [nC+nV, nC+nV+nXF) normal is +- x-dir 23588ed4aceSMatthew G Knepley - Y-Faces: [nC+nV+nXF, nC+nV+nXF+nYF) normal is +- y-dir 23688ed4aceSMatthew G Knepley - Z-Faces: [nC+nV+nXF+nYF, nC+nV+nXF+nYF+nZF) normal is +- z-dir 237a66d4d66SMatthew G Knepley 238a66d4d66SMatthew G Knepley We interpret the default DMDA partition as a cell partition, and the data assignment as a cell assignment. 239a66d4d66SMatthew G Knepley @*/ 24080800b1aSMatthew G Knepley PetscErrorCode DMDACreateSection(DM dm, PetscInt numComp[], PetscInt numVertexDof[], PetscInt numFaceDof[], PetscInt numCellDof[]) 241a66d4d66SMatthew G Knepley { 242a66d4d66SMatthew G Knepley DM_DA *da = (DM_DA*) dm->data; 243a4b60ecfSMatthew G. Knepley PetscSection section; 24488ed4aceSMatthew G Knepley const PetscInt dim = da->dim; 24580800b1aSMatthew G Knepley PetscInt numFields, numVertexTotDof = 0, numCellTotDof = 0, numFaceTotDof[3] = {0, 0, 0}; 246b2fff234SMatthew G. Knepley PetscBT isLeaf; 24788ed4aceSMatthew G Knepley PetscSF sf; 248feafbc5cSMatthew G Knepley PetscMPIInt rank; 24988ed4aceSMatthew G Knepley const PetscMPIInt *neighbors; 25088ed4aceSMatthew G Knepley PetscInt *localPoints; 25188ed4aceSMatthew G Knepley PetscSFNode *remotePoints; 252f5eeb527SMatthew G Knepley PetscInt nleaves = 0, nleavesCheck = 0, nL = 0; 25357459e9aSMatthew G Knepley PetscInt nC, nVx, nVy, nVz, nV, nxF, nXF, nyF, nYF, nzF, nZF; 25457459e9aSMatthew G Knepley PetscInt pStart, pEnd, cStart, cEnd, vStart, vEnd, fStart, fEnd, xfStart, xfEnd, yfStart, yfEnd, zfStart, zfEnd; 25588ed4aceSMatthew G Knepley PetscInt f, v, c, xf, yf, zf, xn, yn, zn; 256a66d4d66SMatthew G Knepley PetscErrorCode ierr; 257a66d4d66SMatthew G Knepley 258a66d4d66SMatthew G Knepley PetscFunctionBegin; 259a66d4d66SMatthew G Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 260*e42e3c58SMatthew G. Knepley PetscValidPointer(s, 4); 26182f516ccSBarry Smith ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)dm), &rank);CHKERRQ(ierr); 262*e42e3c58SMatthew G. Knepley ierr = DMDAGetNumCells(dm, NULL, NULL, NULL, &nC);CHKERRQ(ierr); 26357459e9aSMatthew G Knepley ierr = DMDAGetNumVertices(dm, &nVx, &nVy, &nVz, &nV);CHKERRQ(ierr); 26457459e9aSMatthew G Knepley ierr = DMDAGetNumFaces(dm, &nxF, &nXF, &nyF, &nYF, &nzF, &nZF);CHKERRQ(ierr); 26557459e9aSMatthew G Knepley ierr = DMDAGetHeightStratum(dm, -1, &pStart, &pEnd);CHKERRQ(ierr); 26657459e9aSMatthew G Knepley ierr = DMDAGetHeightStratum(dm, 0, &cStart, &cEnd);CHKERRQ(ierr); 26757459e9aSMatthew G Knepley ierr = DMDAGetHeightStratum(dm, 1, &fStart, &fEnd);CHKERRQ(ierr); 26857459e9aSMatthew G Knepley ierr = DMDAGetHeightStratum(dm, dim, &vStart, &vEnd);CHKERRQ(ierr); 26957459e9aSMatthew G Knepley xfStart = vEnd; xfEnd = xfStart+nXF; 27057459e9aSMatthew G Knepley yfStart = xfEnd; yfEnd = yfStart+nYF; 27157459e9aSMatthew G Knepley zfStart = yfEnd; zfEnd = zfStart+nZF; 27282f516ccSBarry Smith if (zfEnd != fEnd) SETERRQ2(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "Invalid face end %d, should be %d", zfEnd, fEnd); 27388ed4aceSMatthew G Knepley /* Create local section */ 27480800b1aSMatthew G Knepley ierr = DMDAGetInfo(dm, 0,0,0,0,0,0,0, &numFields, 0,0,0,0,0);CHKERRQ(ierr); 275a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 2768865f1eaSKarl Rupp if (numVertexDof) numVertexTotDof += numVertexDof[f]; 2778865f1eaSKarl Rupp if (numCellDof) numCellTotDof += numCellDof[f]; 2788865f1eaSKarl Rupp if (numFaceDof) { 2798865f1eaSKarl Rupp numFaceTotDof[0] += numFaceDof[f*dim+0]; 28088ed4aceSMatthew G Knepley numFaceTotDof[1] += dim > 1 ? numFaceDof[f*dim+1] : 0; 2810ad7597dSKarl Rupp numFaceTotDof[2] += dim > 2 ? numFaceDof[f*dim+2] : 0; 2820ad7597dSKarl Rupp } 283a66d4d66SMatthew G Knepley } 284a4b60ecfSMatthew G. Knepley ierr = PetscSectionCreate(PetscObjectComm((PetscObject)dm), §ion);CHKERRQ(ierr); 285a66d4d66SMatthew G Knepley if (numFields > 1) { 286a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetNumFields(section, numFields);CHKERRQ(ierr); 287a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 28880800b1aSMatthew G Knepley const char *name; 28980800b1aSMatthew G Knepley 29080800b1aSMatthew G Knepley ierr = DMDAGetFieldName(dm, f, &name);CHKERRQ(ierr); 291a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldName(section, f, name);CHKERRQ(ierr); 29280800b1aSMatthew G Knepley if (numComp) { 293a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldComponents(section, f, numComp[f]);CHKERRQ(ierr); 294a66d4d66SMatthew G Knepley } 295a66d4d66SMatthew G Knepley } 296a66d4d66SMatthew G Knepley } else { 297a66d4d66SMatthew G Knepley numFields = 0; 298a66d4d66SMatthew G Knepley } 299a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetChart(section, pStart, pEnd);CHKERRQ(ierr); 300a66d4d66SMatthew G Knepley if (numVertexDof) { 301a66d4d66SMatthew G Knepley for (v = vStart; v < vEnd; ++v) { 302a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 303a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldDof(section, v, f, numVertexDof[f]);CHKERRQ(ierr); 304a66d4d66SMatthew G Knepley } 305a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetDof(section, v, numVertexTotDof);CHKERRQ(ierr); 306a66d4d66SMatthew G Knepley } 307a66d4d66SMatthew G Knepley } 308a66d4d66SMatthew G Knepley if (numFaceDof) { 309a66d4d66SMatthew G Knepley for (xf = xfStart; xf < xfEnd; ++xf) { 310a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 311a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldDof(section, xf, f, numFaceDof[f*dim+0]);CHKERRQ(ierr); 312a66d4d66SMatthew G Knepley } 313a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetDof(section, xf, numFaceTotDof[0]);CHKERRQ(ierr); 314a66d4d66SMatthew G Knepley } 315a66d4d66SMatthew G Knepley for (yf = yfStart; yf < yfEnd; ++yf) { 316a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 317a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldDof(section, yf, f, numFaceDof[f*dim+1]);CHKERRQ(ierr); 318a66d4d66SMatthew G Knepley } 319a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetDof(section, yf, numFaceTotDof[1]);CHKERRQ(ierr); 320a66d4d66SMatthew G Knepley } 321a66d4d66SMatthew G Knepley for (zf = zfStart; zf < zfEnd; ++zf) { 322a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 323a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldDof(section, zf, f, numFaceDof[f*dim+2]);CHKERRQ(ierr); 324a66d4d66SMatthew G Knepley } 325a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetDof(section, zf, numFaceTotDof[2]);CHKERRQ(ierr); 326a66d4d66SMatthew G Knepley } 327a66d4d66SMatthew G Knepley } 328a66d4d66SMatthew G Knepley if (numCellDof) { 329a66d4d66SMatthew G Knepley for (c = cStart; c < cEnd; ++c) { 330a66d4d66SMatthew G Knepley for (f = 0; f < numFields; ++f) { 331a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetFieldDof(section, c, f, numCellDof[f]);CHKERRQ(ierr); 332a66d4d66SMatthew G Knepley } 333a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetDof(section, c, numCellTotDof);CHKERRQ(ierr); 334a66d4d66SMatthew G Knepley } 335a66d4d66SMatthew G Knepley } 336a4b60ecfSMatthew G. Knepley ierr = PetscSectionSetUp(section);CHKERRQ(ierr); 33788ed4aceSMatthew G Knepley /* Create mesh point SF */ 338b2fff234SMatthew G. Knepley ierr = PetscBTCreate(pEnd-pStart, &isLeaf);CHKERRQ(ierr); 33988ed4aceSMatthew G Knepley ierr = DMDAGetNeighbors(dm, &neighbors);CHKERRQ(ierr); 34088ed4aceSMatthew G Knepley for (zn = 0; zn < (dim > 2 ? 3 : 1); ++zn) { 34188ed4aceSMatthew G Knepley for (yn = 0; yn < (dim > 1 ? 3 : 1); ++yn) { 34288ed4aceSMatthew G Knepley for (xn = 0; xn < 3; ++xn) { 3437128ae9fSMatthew G Knepley const PetscInt xp = xn-1, yp = dim > 1 ? yn-1 : 0, zp = dim > 2 ? zn-1 : 0; 34488ed4aceSMatthew G Knepley const PetscInt neighbor = neighbors[(zn*3+yn)*3+xn]; 345b2fff234SMatthew G. Knepley PetscInt xv, yv, zv; 34688ed4aceSMatthew G Knepley 3473814d604SMatthew G Knepley if (neighbor >= 0 && neighbor < rank) { 348b2fff234SMatthew G. Knepley if (xp < 0) { /* left */ 349b2fff234SMatthew G. Knepley if (yp < 0) { /* bottom */ 350b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 351b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + 0 + nC; /* left bottom back vertex */ 352b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 353b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 354b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + 0 + nC; /* left bottom front vertex */ 355b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 356b2fff234SMatthew G. Knepley } else { 357b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 358b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + 0 + nC; /* left bottom vertices */ 359b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 360b2fff234SMatthew G. Knepley } 361b2fff234SMatthew G. Knepley } 362b2fff234SMatthew G. Knepley } else if (yp > 0) { /* top */ 363b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 364b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + 0 + nC; /* left top back vertex */ 365b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 366b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 367b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + 0 + nC; /* left top front vertex */ 368b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 369b2fff234SMatthew G. Knepley } else { 370b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 371b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + 0 + nC; /* left top vertices */ 372b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 373b2fff234SMatthew G. Knepley } 374b2fff234SMatthew G. Knepley } 375b2fff234SMatthew G. Knepley } else { 376b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 377b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 378b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + 0 + nC; /* left back vertices */ 379b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 380b2fff234SMatthew G. Knepley } 381b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 382b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 383b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + 0 + nC; /* left front vertices */ 384b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 385b2fff234SMatthew G. Knepley } 386b2fff234SMatthew G. Knepley } else { 387b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 388b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 389b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + yv)*nVx + 0 + nC; /* left vertices */ 390b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 391b2fff234SMatthew G. Knepley } 392b2fff234SMatthew G. Knepley } 393b2fff234SMatthew G. Knepley #if 0 394b2fff234SMatthew G. Knepley for (xf = 0; xf < nxF; ++xf) { 395b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 396b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* left faces */ 397b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) ++nleaves; 398b2fff234SMatthew G. Knepley } 399b2fff234SMatthew G. Knepley #endif 400b2fff234SMatthew G. Knepley } 401b2fff234SMatthew G. Knepley } 402b2fff234SMatthew G. Knepley } else if (xp > 0) { /* right */ 403b2fff234SMatthew G. Knepley if (yp < 0) { /* bottom */ 404b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 405b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + nVx-1 + nC; /* right bottom back vertex */ 406b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 407b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 408b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + nVx-1 + nC; /* right bottom front vertex */ 409b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 410b2fff234SMatthew G. Knepley } else { 411b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 412b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + nVx-1 + nC; /* right bottom vertices */ 413b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 414b2fff234SMatthew G. Knepley } 415b2fff234SMatthew G. Knepley } 416b2fff234SMatthew G. Knepley } else if (yp > 0) { /* top */ 417b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 418b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top back vertex */ 419b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 420b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 421b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top front vertex */ 422b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 423b2fff234SMatthew G. Knepley } else { 424b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 425b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top vertices */ 426b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 427b2fff234SMatthew G. Knepley } 428b2fff234SMatthew G. Knepley } 429b2fff234SMatthew G. Knepley } else { 430b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 431b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 432b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + nVx-1 + nC; /* right back vertices */ 433b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 434b2fff234SMatthew G. Knepley } 435b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 436b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 437b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + nVx-1 + nC; /* right front vertices */ 438b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 439b2fff234SMatthew G. Knepley } 440b2fff234SMatthew G. Knepley } else { 441b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 442b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 443b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + yv)*nVx + nVx-1 + nC; /* right vertices */ 444b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 445b2fff234SMatthew G. Knepley } 446b2fff234SMatthew G. Knepley } 447b2fff234SMatthew G. Knepley #if 0 448b2fff234SMatthew G. Knepley for (xf = 0; xf < nxF; ++xf) { 449b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 450b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* right faces */ 451b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) ++nleaves; 452b2fff234SMatthew G. Knepley } 453b2fff234SMatthew G. Knepley #endif 454b2fff234SMatthew G. Knepley } 455b2fff234SMatthew G. Knepley } 456b2fff234SMatthew G. Knepley } else { 457b2fff234SMatthew G. Knepley if (yp < 0) { /* bottom */ 458b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 459b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 460b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + xv + nC; /* bottom back vertices */ 461b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 462b2fff234SMatthew G. Knepley } 463b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 464b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 465b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + xv + nC; /* bottom front vertices */ 466b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 467b2fff234SMatthew G. Knepley } 468b2fff234SMatthew G. Knepley } else { 469b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 470b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 471b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + xv + nC; /* bottom vertices */ 472b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 473b2fff234SMatthew G. Knepley } 474b2fff234SMatthew G. Knepley } 475b2fff234SMatthew G. Knepley #if 0 476b2fff234SMatthew G. Knepley for (yf = 0; yf < nyF; ++yf) { 477b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 478b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* bottom faces */ 479b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVFace)) ++nleaves; 480b2fff234SMatthew G. Knepley } 481b2fff234SMatthew G. Knepley #endif 482b2fff234SMatthew G. Knepley } 483b2fff234SMatthew G. Knepley } else if (yp > 0) { /* top */ 484b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 485b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 486b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + xv + nC; /* top back vertices */ 487b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 488b2fff234SMatthew G. Knepley } 489b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 490b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 491b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + xv + nC; /* top front vertices */ 492b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 493b2fff234SMatthew G. Knepley } 494b2fff234SMatthew G. Knepley } else { 495b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 496b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 497b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + xv + nC; /* top vertices */ 498b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 499b2fff234SMatthew G. Knepley } 500b2fff234SMatthew G. Knepley } 501b2fff234SMatthew G. Knepley #if 0 502b2fff234SMatthew G. Knepley for (yf = 0; yf < nyF; ++yf) { 503b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 504b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* top faces */ 505b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVFace)) ++nleaves; 506b2fff234SMatthew G. Knepley } 507b2fff234SMatthew G. Knepley #endif 508b2fff234SMatthew G. Knepley } 509b2fff234SMatthew G. Knepley } else { 510b2fff234SMatthew G. Knepley if (zp < 0) { /* back */ 511b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 512b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 513b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + xv + nC; /* back vertices */ 514b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 515b2fff234SMatthew G. Knepley } 516b2fff234SMatthew G. Knepley } 517b2fff234SMatthew G. Knepley #if 0 518b2fff234SMatthew G. Knepley for (zf = 0; zf < nzF; ++zf) { 519b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 520b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* back faces */ 521b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) ++nleaves; 522b2fff234SMatthew G. Knepley } 523b2fff234SMatthew G. Knepley #endif 524b2fff234SMatthew G. Knepley } else if (zp > 0) { /* front */ 525b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 526b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 527b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + xv + nC; /* front vertices */ 528b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) ++nleaves; 529b2fff234SMatthew G. Knepley } 530b2fff234SMatthew G. Knepley } 531b2fff234SMatthew G. Knepley #if 0 532b2fff234SMatthew G. Knepley for (zf = 0; zf < nzF; ++zf) { 533b2fff234SMatthew G. Knepley /* THIS IS WRONG */ 534b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* front faces */ 535b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) ++nleaves; 536b2fff234SMatthew G. Knepley } 537b2fff234SMatthew G. Knepley #endif 538b2fff234SMatthew G. Knepley } else { 539b2fff234SMatthew G. Knepley /* Nothing is shared from the interior */ 54088ed4aceSMatthew G Knepley } 54188ed4aceSMatthew G Knepley } 54288ed4aceSMatthew G Knepley } 54388ed4aceSMatthew G Knepley } 54488ed4aceSMatthew G Knepley } 545b2fff234SMatthew G. Knepley } 546b2fff234SMatthew G. Knepley } 547b2fff234SMatthew G. Knepley ierr = PetscBTMemzero(pEnd-pStart, isLeaf);CHKERRQ(ierr); 54888ed4aceSMatthew G Knepley ierr = PetscMalloc2(nleaves,PetscInt,&localPoints,nleaves,PetscSFNode,&remotePoints);CHKERRQ(ierr); 54988ed4aceSMatthew G Knepley for (zn = 0; zn < (dim > 2 ? 3 : 1); ++zn) { 55088ed4aceSMatthew G Knepley for (yn = 0; yn < (dim > 1 ? 3 : 1); ++yn) { 55188ed4aceSMatthew G Knepley for (xn = 0; xn < 3; ++xn) { 5527128ae9fSMatthew G Knepley const PetscInt xp = xn-1, yp = dim > 1 ? yn-1 : 0, zp = dim > 2 ? zn-1 : 0; 55388ed4aceSMatthew G Knepley const PetscInt neighbor = neighbors[(zn*3+yn)*3+xn]; 554f5eeb527SMatthew G Knepley PetscInt xv, yv, zv; 55588ed4aceSMatthew G Knepley 5563814d604SMatthew G Knepley if (neighbor >= 0 && neighbor < rank) { 55788ed4aceSMatthew G Knepley if (xp < 0) { /* left */ 55888ed4aceSMatthew G Knepley if (yp < 0) { /* bottom */ 55988ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 560b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + 0 + nC; /* left bottom back vertex */ 561f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + nVy-1)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 562f5eeb527SMatthew G Knepley 563b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 564f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 565f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 566f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 567f5eeb527SMatthew G Knepley ++nL; 568b2fff234SMatthew G. Knepley } 56988ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 570b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + 0 + nC; /* left bottom front vertex */ 571f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + nVy-1)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 572f5eeb527SMatthew G Knepley 573b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 574f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 575f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 576f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 577f5eeb527SMatthew G Knepley ++nL; 578b2fff234SMatthew G. Knepley } 57988ed4aceSMatthew G Knepley } else { 580b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 581b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + 0 + nC; /* left bottom vertices */ 582f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + nVy-1)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 583f5eeb527SMatthew G Knepley 584b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 585f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 586f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 587f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 588b2fff234SMatthew G. Knepley ++nL; 589b2fff234SMatthew G. Knepley } 590f5eeb527SMatthew G Knepley } 59188ed4aceSMatthew G Knepley } 59288ed4aceSMatthew G Knepley } else if (yp > 0) { /* top */ 59388ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 594b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + 0 + nC; /* left top back vertex */ 595f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + 0)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 596f5eeb527SMatthew G Knepley 597b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 598f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 599f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 600f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 601f5eeb527SMatthew G Knepley ++nL; 602b2fff234SMatthew G. Knepley } 60388ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 604b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + 0 + nC; /* left top front vertex */ 605f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + 0)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 606f5eeb527SMatthew G Knepley 607b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 608f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 609f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 610f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 611f5eeb527SMatthew G Knepley ++nL; 612b2fff234SMatthew G. Knepley } 61388ed4aceSMatthew G Knepley } else { 614b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 615b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + 0 + nC; /* left top vertices */ 616f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + 0)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 617f5eeb527SMatthew G Knepley 618b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 619f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 620f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 621f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 622b2fff234SMatthew G. Knepley ++nL; 623b2fff234SMatthew G. Knepley } 624f5eeb527SMatthew G Knepley } 62588ed4aceSMatthew G Knepley } 62688ed4aceSMatthew G Knepley } else { 62788ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 628b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 629b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + 0 + nC; /* left back vertices */ 630f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + yv)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 631f5eeb527SMatthew G Knepley 632b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 633f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 634f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 635f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 636b2fff234SMatthew G. Knepley ++nL; 637b2fff234SMatthew G. Knepley } 638f5eeb527SMatthew G Knepley } 63988ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 640b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 641b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + 0 + nC; /* left front vertices */ 642f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + yv)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 643f5eeb527SMatthew G Knepley 644b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 645f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 646f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 647f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 648b2fff234SMatthew G. Knepley ++nL; 649b2fff234SMatthew G. Knepley } 650f5eeb527SMatthew G Knepley } 65188ed4aceSMatthew G Knepley } else { 652f5eeb527SMatthew G Knepley for (zv = 0; zv < nVz; ++zv) { 653b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 654b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + yv)*nVx + 0 + nC; /* left vertices */ 655f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + yv)*nVx + nVx-1 + nC; /* TODO: Correct this for neighbor sizes */ 656f5eeb527SMatthew G Knepley 657b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 658f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 659f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 660f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 661b2fff234SMatthew G. Knepley ++nL; 662f5eeb527SMatthew G Knepley } 663f5eeb527SMatthew G Knepley } 664b2fff234SMatthew G. Knepley } 665b2fff234SMatthew G. Knepley #if 0 666b2fff234SMatthew G. Knepley for (xf = 0; xf < nxF; ++xf) { 667f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 668b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* left faces */ 669f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 670f5eeb527SMatthew G Knepley 671b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 672f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 673f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 674f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 675f5eeb527SMatthew G Knepley } 67688ed4aceSMatthew G Knepley } 677b2fff234SMatthew G. Knepley #endif 678b2fff234SMatthew G. Knepley } 67988ed4aceSMatthew G Knepley } 68088ed4aceSMatthew G Knepley } else if (xp > 0) { /* right */ 68188ed4aceSMatthew G Knepley if (yp < 0) { /* bottom */ 68288ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 683b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + nVx-1 + nC; /* right bottom back vertex */ 684f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + nVy-1)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 685f5eeb527SMatthew G Knepley 686b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 687f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 688f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 689f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 690f5eeb527SMatthew G Knepley ++nL; 691b2fff234SMatthew G. Knepley } 69288ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 693b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + nVx-1 + nC; /* right bottom front vertex */ 694f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + nVy-1)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 695f5eeb527SMatthew G Knepley 696b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 697f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 698f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 699f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 700f5eeb527SMatthew G Knepley ++nL; 701b2fff234SMatthew G. Knepley } 70288ed4aceSMatthew G Knepley } else { 703b2fff234SMatthew G. Knepley nleavesCheck += nVz; 704b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 705b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + nVx-1 + nC; /* right bottom vertices */ 706f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + nVy-1)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 707f5eeb527SMatthew G Knepley 708b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 709f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 710f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 711f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 712b2fff234SMatthew G. Knepley ++nL; 713b2fff234SMatthew G. Knepley } 714f5eeb527SMatthew G Knepley } 71588ed4aceSMatthew G Knepley } 71688ed4aceSMatthew G Knepley } else if (yp > 0) { /* top */ 71788ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 718b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top back vertex */ 719f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + 0)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 720f5eeb527SMatthew G Knepley 721b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 722f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 723f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 724f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 725f5eeb527SMatthew G Knepley ++nL; 726b2fff234SMatthew G. Knepley } 72788ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 728b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top front vertex */ 729f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + 0)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 730f5eeb527SMatthew G Knepley 731b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 732f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 733f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 734f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 735f5eeb527SMatthew G Knepley ++nL; 736b2fff234SMatthew G. Knepley } 73788ed4aceSMatthew G Knepley } else { 738b2fff234SMatthew G. Knepley for (zv = 0; zv < nVz; ++zv) { 739b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + nVx-1 + nC; /* right top vertices */ 740f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + 0)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 741f5eeb527SMatthew G Knepley 742b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 743f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 744f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 745f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 746b2fff234SMatthew G. Knepley ++nL; 747b2fff234SMatthew G. Knepley } 748f5eeb527SMatthew G Knepley } 74988ed4aceSMatthew G Knepley } 75088ed4aceSMatthew G Knepley } else { 75188ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 752b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 753b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + nVx-1 + nC; /* right back vertices */ 754f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + yv)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 755f5eeb527SMatthew G Knepley 756b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 757f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 758f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 759f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 760b2fff234SMatthew G. Knepley ++nL; 761b2fff234SMatthew G. Knepley } 762f5eeb527SMatthew G Knepley } 76388ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 764b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 765b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + nVx-1 + nC; /* right front vertices */ 766f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + yv)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 767f5eeb527SMatthew G Knepley 768b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 769f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 770f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 771f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 772b2fff234SMatthew G. Knepley ++nL; 773b2fff234SMatthew G. Knepley } 774f5eeb527SMatthew G Knepley } 77588ed4aceSMatthew G Knepley } else { 776f5eeb527SMatthew G Knepley for (zv = 0; zv < nVz; ++zv) { 777b2fff234SMatthew G. Knepley for (yv = 0; yv < nVy; ++yv) { 778b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + yv)*nVx + nVx-1 + nC; /* right vertices */ 779f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + yv)*nVx + 0 + nC; /* TODO: Correct this for neighbor sizes */ 780f5eeb527SMatthew G Knepley 781b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 782f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 783f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 784f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 785b2fff234SMatthew G. Knepley ++nL; 786f5eeb527SMatthew G Knepley } 787f5eeb527SMatthew G Knepley } 788b2fff234SMatthew G. Knepley } 789b2fff234SMatthew G. Knepley #if 0 790b2fff234SMatthew G. Knepley for (xf = 0; xf < nxF; ++xf) { 791f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 792b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* right faces */ 793f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 794f5eeb527SMatthew G Knepley 795b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 796f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 797f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 798f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 799b2fff234SMatthew G. Knepley ++nL; 800f5eeb527SMatthew G Knepley } 80188ed4aceSMatthew G Knepley } 802b2fff234SMatthew G. Knepley #endif 803b2fff234SMatthew G. Knepley } 80488ed4aceSMatthew G Knepley } 80588ed4aceSMatthew G Knepley } else { 80688ed4aceSMatthew G Knepley if (yp < 0) { /* bottom */ 80788ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 808b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 809b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + 0)*nVx + xv + nC; /* bottom back vertices */ 810f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + nVy-1)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 811f5eeb527SMatthew G Knepley 812b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 813f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 814f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 815f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 816b2fff234SMatthew G. Knepley ++nL; 817b2fff234SMatthew G. Knepley } 818f5eeb527SMatthew G Knepley } 81988ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 820b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 821b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + 0)*nVx + xv + nC; /* bottom front vertices */ 822f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + nVy-1)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 823f5eeb527SMatthew G Knepley 824b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 825f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 826f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 827f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 828b2fff234SMatthew G. Knepley ++nL; 829b2fff234SMatthew G. Knepley } 830f5eeb527SMatthew G Knepley } 83188ed4aceSMatthew G Knepley } else { 832f5eeb527SMatthew G Knepley for (zv = 0; zv < nVz; ++zv) { 833b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 834b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + 0)*nVx + xv + nC; /* bottom vertices */ 835f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + nVy-1)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 836f5eeb527SMatthew G Knepley 837b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 838f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 839f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 840f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 841b2fff234SMatthew G. Knepley ++nL; 842f5eeb527SMatthew G Knepley } 843f5eeb527SMatthew G Knepley } 844b2fff234SMatthew G. Knepley } 845b2fff234SMatthew G. Knepley #if 0 846b2fff234SMatthew G. Knepley for (yf = 0; yf < nyF; ++yf) { 847f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 848b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* bottom faces */ 849f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 850f5eeb527SMatthew G Knepley 851b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 852f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 853f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 854f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 855b2fff234SMatthew G. Knepley ++nL; 856f5eeb527SMatthew G Knepley } 85788ed4aceSMatthew G Knepley } 858b2fff234SMatthew G. Knepley #endif 859b2fff234SMatthew G. Knepley } 86088ed4aceSMatthew G Knepley } else if (yp > 0) { /* top */ 86188ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 862b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 863b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + nVy-1)*nVx + xv + nC; /* top back vertices */ 864f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + 0)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 865f5eeb527SMatthew G Knepley 866b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 867f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 868f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 869f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 870b2fff234SMatthew G. Knepley ++nL; 871b2fff234SMatthew G. Knepley } 872f5eeb527SMatthew G Knepley } 87388ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 874b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 875b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + nVy-1)*nVx + xv + nC; /* top front vertices */ 876f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + 0)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 877f5eeb527SMatthew G Knepley 878b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 879f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 880f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 881f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 882b2fff234SMatthew G. Knepley ++nL; 883b2fff234SMatthew G. Knepley } 884f5eeb527SMatthew G Knepley } 88588ed4aceSMatthew G Knepley } else { 886f5eeb527SMatthew G Knepley for (zv = 0; zv < nVz; ++zv) { 887b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 888b2fff234SMatthew G. Knepley const PetscInt localVertex = (zv*nVy + nVy-1)*nVx + xv + nC; /* top vertices */ 889f5eeb527SMatthew G Knepley const PetscInt remoteVertex = (zv*nVy + 0)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 890f5eeb527SMatthew G Knepley 891b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 892f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 893f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 894f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 895b2fff234SMatthew G. Knepley ++nL; 896f5eeb527SMatthew G Knepley } 897f5eeb527SMatthew G Knepley } 898b2fff234SMatthew G. Knepley } 899b2fff234SMatthew G. Knepley #if 0 900b2fff234SMatthew G. Knepley for (yf = 0; yf < nyF; ++yf) { 901f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 902b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* top faces */ 903f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 904f5eeb527SMatthew G Knepley 905b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 906f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 907f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 908f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 909b2fff234SMatthew G. Knepley ++nL; 910f5eeb527SMatthew G Knepley } 91188ed4aceSMatthew G Knepley } 912b2fff234SMatthew G. Knepley #endif 913b2fff234SMatthew G. Knepley } 91488ed4aceSMatthew G Knepley } else { 91588ed4aceSMatthew G Knepley if (zp < 0) { /* back */ 916f5eeb527SMatthew G Knepley for (yv = 0; yv < nVy; ++yv) { 917b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 918b2fff234SMatthew G. Knepley const PetscInt localVertex = ( 0*nVy + yv)*nVx + xv + nC; /* back vertices */ 919f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ((nVz-1)*nVy + yv)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 920f5eeb527SMatthew G Knepley 921b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 922f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 923f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 924f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 925b2fff234SMatthew G. Knepley ++nL; 926f5eeb527SMatthew G Knepley } 927f5eeb527SMatthew G Knepley } 928b2fff234SMatthew G. Knepley } 929b2fff234SMatthew G. Knepley #if 0 930b2fff234SMatthew G. Knepley for (zf = 0; zf < nzF; ++zf) { 931f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 932b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* back faces */ 933f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 934f5eeb527SMatthew G Knepley 935b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 936f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 937f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 938f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 939b2fff234SMatthew G. Knepley ++nL; 940f5eeb527SMatthew G Knepley } 941b2fff234SMatthew G. Knepley } 942b2fff234SMatthew G. Knepley #endif 94388ed4aceSMatthew G Knepley } else if (zp > 0) { /* front */ 944f5eeb527SMatthew G Knepley for (yv = 0; yv < nVy; ++yv) { 945b2fff234SMatthew G. Knepley for (xv = 0; xv < nVx; ++xv) { 946b2fff234SMatthew G. Knepley const PetscInt localVertex = ((nVz-1)*nVy + yv)*nVx + xv + nC; /* front vertices */ 947f5eeb527SMatthew G Knepley const PetscInt remoteVertex = ( 0*nVy + yv)*nVx + xv + nC; /* TODO: Correct this for neighbor sizes */ 948f5eeb527SMatthew G Knepley 949b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localVertex)) { 950f5eeb527SMatthew G Knepley localPoints[nL] = localVertex; 951f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 952f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteVertex; 953b2fff234SMatthew G. Knepley ++nL; 954f5eeb527SMatthew G Knepley } 955f5eeb527SMatthew G Knepley } 956b2fff234SMatthew G. Knepley } 957b2fff234SMatthew G. Knepley #if 0 958b2fff234SMatthew G. Knepley for (zf = 0; zf < nzF; ++zf) { 959f5eeb527SMatthew G Knepley /* THIS IS WRONG */ 960b2fff234SMatthew G. Knepley const PetscInt localFace = 0 + nC+nV; /* front faces */ 961f5eeb527SMatthew G Knepley const PetscInt remoteFace = 0 + nC+nV; 962f5eeb527SMatthew G Knepley 963b2fff234SMatthew G. Knepley if (!PetscBTLookupSet(isLeaf, localFace)) { 964f5eeb527SMatthew G Knepley localPoints[nL] = localFace; 965f5eeb527SMatthew G Knepley remotePoints[nL].rank = neighbor; 966f5eeb527SMatthew G Knepley remotePoints[nL].index = remoteFace; 967b2fff234SMatthew G. Knepley ++nL; 968f5eeb527SMatthew G Knepley } 969b2fff234SMatthew G. Knepley } 970b2fff234SMatthew G. Knepley #endif 97188ed4aceSMatthew G Knepley } else { 97288ed4aceSMatthew G Knepley /* Nothing is shared from the interior */ 97388ed4aceSMatthew G Knepley } 97488ed4aceSMatthew G Knepley } 97588ed4aceSMatthew G Knepley } 97688ed4aceSMatthew G Knepley } 97788ed4aceSMatthew G Knepley } 97888ed4aceSMatthew G Knepley } 97988ed4aceSMatthew G Knepley } 980b2fff234SMatthew G. Knepley ierr = PetscBTDestroy(&isLeaf);CHKERRQ(ierr); 981b2fff234SMatthew G. Knepley /* Remove duplication in leaf determination */ 982b2fff234SMatthew G. Knepley if (nleaves != nL) SETERRQ2(PetscObjectComm((PetscObject)dm), PETSC_ERR_PLIB, "The number of leaves %d did not match the number of remote leaves %d", nleaves, nleavesCheck); 98382f516ccSBarry Smith ierr = PetscSFCreate(PetscObjectComm((PetscObject)dm), &sf);CHKERRQ(ierr); 98488ed4aceSMatthew G Knepley ierr = PetscSFSetGraph(sf, pEnd, nleaves, localPoints, PETSC_OWN_POINTER, remotePoints, PETSC_OWN_POINTER);CHKERRQ(ierr); 985a4b60ecfSMatthew G. Knepley ierr = DMSetPointSF(dm, sf);CHKERRQ(ierr); 98688ed4aceSMatthew G Knepley ierr = PetscSFDestroy(&sf);CHKERRQ(ierr); 987a4b60ecfSMatthew G. Knepley ierr = DMSetDefaultSection(dm, section);CHKERRQ(ierr); 988a4b60ecfSMatthew G. Knepley ierr = PetscSectionDestroy(§ion);CHKERRQ(ierr); 989a66d4d66SMatthew G Knepley PetscFunctionReturn(0); 990a66d4d66SMatthew G Knepley } 991a66d4d66SMatthew G Knepley 99247c6ae99SBarry Smith /* ------------------------------------------------------------------- */ 99347c6ae99SBarry Smith 99447c6ae99SBarry Smith #undef __FUNCT__ 995aa219208SBarry Smith #define __FUNCT__ "DMDAGetArray" 99647c6ae99SBarry Smith /*@C 997aa219208SBarry Smith DMDAGetArray - Gets a work array for a DMDA 99847c6ae99SBarry Smith 99947c6ae99SBarry Smith Input Parameter: 100047c6ae99SBarry Smith + da - information about my local patch 100147c6ae99SBarry Smith - ghosted - do you want arrays for the ghosted or nonghosted patch 100247c6ae99SBarry Smith 100347c6ae99SBarry Smith Output Parameters: 100447c6ae99SBarry Smith . vptr - array data structured 100547c6ae99SBarry Smith 100647c6ae99SBarry Smith Note: The vector values are NOT initialized and may have garbage in them, so you may need 100747c6ae99SBarry Smith to zero them. 100847c6ae99SBarry Smith 100947c6ae99SBarry Smith Level: advanced 101047c6ae99SBarry Smith 1011bcaeba4dSBarry Smith .seealso: DMDARestoreArray() 101247c6ae99SBarry Smith 101347c6ae99SBarry Smith @*/ 10147087cfbeSBarry Smith PetscErrorCode DMDAGetArray(DM da,PetscBool ghosted,void *vptr) 101547c6ae99SBarry Smith { 101647c6ae99SBarry Smith PetscErrorCode ierr; 101747c6ae99SBarry Smith PetscInt j,i,xs,ys,xm,ym,zs,zm; 101847c6ae99SBarry Smith char *iarray_start; 101947c6ae99SBarry Smith void **iptr = (void**)vptr; 102047c6ae99SBarry Smith DM_DA *dd = (DM_DA*)da->data; 102147c6ae99SBarry Smith 102247c6ae99SBarry Smith PetscFunctionBegin; 102347c6ae99SBarry Smith PetscValidHeaderSpecific(da,DM_CLASSID,1); 102447c6ae99SBarry Smith if (ghosted) { 1025aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 102647c6ae99SBarry Smith if (dd->arrayghostedin[i]) { 102747c6ae99SBarry Smith *iptr = dd->arrayghostedin[i]; 102847c6ae99SBarry Smith iarray_start = (char*)dd->startghostedin[i]; 10290298fd71SBarry Smith dd->arrayghostedin[i] = NULL; 10300298fd71SBarry Smith dd->startghostedin[i] = NULL; 103147c6ae99SBarry Smith 103247c6ae99SBarry Smith goto done; 103347c6ae99SBarry Smith } 103447c6ae99SBarry Smith } 103547c6ae99SBarry Smith xs = dd->Xs; 103647c6ae99SBarry Smith ys = dd->Ys; 103747c6ae99SBarry Smith zs = dd->Zs; 103847c6ae99SBarry Smith xm = dd->Xe-dd->Xs; 103947c6ae99SBarry Smith ym = dd->Ye-dd->Ys; 104047c6ae99SBarry Smith zm = dd->Ze-dd->Zs; 104147c6ae99SBarry Smith } else { 1042aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 104347c6ae99SBarry Smith if (dd->arrayin[i]) { 104447c6ae99SBarry Smith *iptr = dd->arrayin[i]; 104547c6ae99SBarry Smith iarray_start = (char*)dd->startin[i]; 10460298fd71SBarry Smith dd->arrayin[i] = NULL; 10470298fd71SBarry Smith dd->startin[i] = NULL; 104847c6ae99SBarry Smith 104947c6ae99SBarry Smith goto done; 105047c6ae99SBarry Smith } 105147c6ae99SBarry Smith } 105247c6ae99SBarry Smith xs = dd->xs; 105347c6ae99SBarry Smith ys = dd->ys; 105447c6ae99SBarry Smith zs = dd->zs; 105547c6ae99SBarry Smith xm = dd->xe-dd->xs; 105647c6ae99SBarry Smith ym = dd->ye-dd->ys; 105747c6ae99SBarry Smith zm = dd->ze-dd->zs; 105847c6ae99SBarry Smith } 105947c6ae99SBarry Smith 106047c6ae99SBarry Smith switch (dd->dim) { 106147c6ae99SBarry Smith case 1: { 106247c6ae99SBarry Smith void *ptr; 106347c6ae99SBarry Smith 106447c6ae99SBarry Smith ierr = PetscMalloc(xm*sizeof(PetscScalar),&iarray_start);CHKERRQ(ierr); 106547c6ae99SBarry Smith 106647c6ae99SBarry Smith ptr = (void*)(iarray_start - xs*sizeof(PetscScalar)); 106747c6ae99SBarry Smith *iptr = (void*)ptr; 10688865f1eaSKarl Rupp break; 10698865f1eaSKarl Rupp } 107047c6ae99SBarry Smith case 2: { 107147c6ae99SBarry Smith void **ptr; 107247c6ae99SBarry Smith 107347c6ae99SBarry Smith ierr = PetscMalloc((ym+1)*sizeof(void*)+xm*ym*sizeof(PetscScalar),&iarray_start);CHKERRQ(ierr); 107447c6ae99SBarry Smith 107547c6ae99SBarry Smith ptr = (void**)(iarray_start + xm*ym*sizeof(PetscScalar) - ys*sizeof(void*)); 10768865f1eaSKarl Rupp for (j=ys; j<ys+ym; j++) ptr[j] = iarray_start + sizeof(PetscScalar)*(xm*(j-ys) - xs); 107747c6ae99SBarry Smith *iptr = (void*)ptr; 10788865f1eaSKarl Rupp break; 10798865f1eaSKarl Rupp } 108047c6ae99SBarry Smith case 3: { 108147c6ae99SBarry Smith void ***ptr,**bptr; 108247c6ae99SBarry Smith 108347c6ae99SBarry Smith ierr = PetscMalloc((zm+1)*sizeof(void**)+(ym*zm+1)*sizeof(void*)+xm*ym*zm*sizeof(PetscScalar),&iarray_start);CHKERRQ(ierr); 108447c6ae99SBarry Smith 108547c6ae99SBarry Smith ptr = (void***)(iarray_start + xm*ym*zm*sizeof(PetscScalar) - zs*sizeof(void*)); 108647c6ae99SBarry Smith bptr = (void**)(iarray_start + xm*ym*zm*sizeof(PetscScalar) + zm*sizeof(void**)); 10878865f1eaSKarl Rupp for (i=zs; i<zs+zm; i++) ptr[i] = bptr + ((i-zs)*ym - ys); 108847c6ae99SBarry Smith for (i=zs; i<zs+zm; i++) { 108947c6ae99SBarry Smith for (j=ys; j<ys+ym; j++) { 109047c6ae99SBarry Smith ptr[i][j] = iarray_start + sizeof(PetscScalar)*(xm*ym*(i-zs) + xm*(j-ys) - xs); 109147c6ae99SBarry Smith } 109247c6ae99SBarry Smith } 109347c6ae99SBarry Smith *iptr = (void*)ptr; 10948865f1eaSKarl Rupp break; 10958865f1eaSKarl Rupp } 109647c6ae99SBarry Smith default: 1097ce94432eSBarry Smith SETERRQ1(PetscObjectComm((PetscObject)da),PETSC_ERR_SUP,"Dimension %D not supported",dd->dim); 109847c6ae99SBarry Smith } 109947c6ae99SBarry Smith 110047c6ae99SBarry Smith done: 110147c6ae99SBarry Smith /* add arrays to the checked out list */ 110247c6ae99SBarry Smith if (ghosted) { 1103aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 110447c6ae99SBarry Smith if (!dd->arrayghostedout[i]) { 110547c6ae99SBarry Smith dd->arrayghostedout[i] = *iptr; 110647c6ae99SBarry Smith dd->startghostedout[i] = iarray_start; 110747c6ae99SBarry Smith break; 110847c6ae99SBarry Smith } 110947c6ae99SBarry Smith } 111047c6ae99SBarry Smith } else { 1111aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 111247c6ae99SBarry Smith if (!dd->arrayout[i]) { 111347c6ae99SBarry Smith dd->arrayout[i] = *iptr; 111447c6ae99SBarry Smith dd->startout[i] = iarray_start; 111547c6ae99SBarry Smith break; 111647c6ae99SBarry Smith } 111747c6ae99SBarry Smith } 111847c6ae99SBarry Smith } 111947c6ae99SBarry Smith PetscFunctionReturn(0); 112047c6ae99SBarry Smith } 112147c6ae99SBarry Smith 112247c6ae99SBarry Smith #undef __FUNCT__ 1123aa219208SBarry Smith #define __FUNCT__ "DMDARestoreArray" 112447c6ae99SBarry Smith /*@C 1125aa219208SBarry Smith DMDARestoreArray - Restores an array of derivative types for a DMDA 112647c6ae99SBarry Smith 112747c6ae99SBarry Smith Input Parameter: 112847c6ae99SBarry Smith + da - information about my local patch 112947c6ae99SBarry Smith . ghosted - do you want arrays for the ghosted or nonghosted patch 113047c6ae99SBarry Smith - vptr - array data structured to be passed to ad_FormFunctionLocal() 113147c6ae99SBarry Smith 113247c6ae99SBarry Smith Level: advanced 113347c6ae99SBarry Smith 1134bcaeba4dSBarry Smith .seealso: DMDAGetArray() 113547c6ae99SBarry Smith 113647c6ae99SBarry Smith @*/ 11377087cfbeSBarry Smith PetscErrorCode DMDARestoreArray(DM da,PetscBool ghosted,void *vptr) 113847c6ae99SBarry Smith { 113947c6ae99SBarry Smith PetscInt i; 114047c6ae99SBarry Smith void **iptr = (void**)vptr,*iarray_start = 0; 114147c6ae99SBarry Smith DM_DA *dd = (DM_DA*)da->data; 114247c6ae99SBarry Smith 114347c6ae99SBarry Smith PetscFunctionBegin; 114447c6ae99SBarry Smith PetscValidHeaderSpecific(da,DM_CLASSID,1); 114547c6ae99SBarry Smith if (ghosted) { 1146aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 114747c6ae99SBarry Smith if (dd->arrayghostedout[i] == *iptr) { 114847c6ae99SBarry Smith iarray_start = dd->startghostedout[i]; 11490298fd71SBarry Smith dd->arrayghostedout[i] = NULL; 11500298fd71SBarry Smith dd->startghostedout[i] = NULL; 115147c6ae99SBarry Smith break; 115247c6ae99SBarry Smith } 115347c6ae99SBarry Smith } 1154aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 115547c6ae99SBarry Smith if (!dd->arrayghostedin[i]) { 115647c6ae99SBarry Smith dd->arrayghostedin[i] = *iptr; 115747c6ae99SBarry Smith dd->startghostedin[i] = iarray_start; 115847c6ae99SBarry Smith break; 115947c6ae99SBarry Smith } 116047c6ae99SBarry Smith } 116147c6ae99SBarry Smith } else { 1162aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 116347c6ae99SBarry Smith if (dd->arrayout[i] == *iptr) { 116447c6ae99SBarry Smith iarray_start = dd->startout[i]; 11650298fd71SBarry Smith dd->arrayout[i] = NULL; 11660298fd71SBarry Smith dd->startout[i] = NULL; 116747c6ae99SBarry Smith break; 116847c6ae99SBarry Smith } 116947c6ae99SBarry Smith } 1170aa219208SBarry Smith for (i=0; i<DMDA_MAX_WORK_ARRAYS; i++) { 117147c6ae99SBarry Smith if (!dd->arrayin[i]) { 117247c6ae99SBarry Smith dd->arrayin[i] = *iptr; 117347c6ae99SBarry Smith dd->startin[i] = iarray_start; 117447c6ae99SBarry Smith break; 117547c6ae99SBarry Smith } 117647c6ae99SBarry Smith } 117747c6ae99SBarry Smith } 117847c6ae99SBarry Smith PetscFunctionReturn(0); 117947c6ae99SBarry Smith } 118047c6ae99SBarry Smith 1181