1*47c6ae99SBarry Smith #define PETSCDM_DLL 2*47c6ae99SBarry Smith /* 3*47c6ae99SBarry Smith Code for manipulating distributed regular 3d arrays in parallel. 4*47c6ae99SBarry Smith File created by Peter Mell 7/14/95 5*47c6ae99SBarry Smith */ 6*47c6ae99SBarry Smith 7*47c6ae99SBarry Smith #include "private/daimpl.h" /*I "petscda.h" I*/ 8*47c6ae99SBarry Smith 9*47c6ae99SBarry Smith #undef __FUNCT__ 10*47c6ae99SBarry Smith #define __FUNCT__ "DAView_3d" 11*47c6ae99SBarry Smith PetscErrorCode DAView_3d(DA da,PetscViewer viewer) 12*47c6ae99SBarry Smith { 13*47c6ae99SBarry Smith PetscErrorCode ierr; 14*47c6ae99SBarry Smith PetscMPIInt rank; 15*47c6ae99SBarry Smith PetscBool iascii,isdraw; 16*47c6ae99SBarry Smith DM_DA *dd = (DM_DA*)da->data; 17*47c6ae99SBarry Smith 18*47c6ae99SBarry Smith PetscFunctionBegin; 19*47c6ae99SBarry Smith ierr = MPI_Comm_rank(((PetscObject)da)->comm,&rank);CHKERRQ(ierr); 20*47c6ae99SBarry Smith 21*47c6ae99SBarry Smith ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 22*47c6ae99SBarry Smith ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERDRAW,&isdraw);CHKERRQ(ierr); 23*47c6ae99SBarry Smith if (iascii) { 24*47c6ae99SBarry Smith PetscViewerFormat format; 25*47c6ae99SBarry Smith 26*47c6ae99SBarry Smith ierr = PetscViewerGetFormat(viewer, &format);CHKERRQ(ierr); 27*47c6ae99SBarry Smith if (format != PETSC_VIEWER_ASCII_VTK && format != PETSC_VIEWER_ASCII_VTK_CELL) { 28*47c6ae99SBarry Smith DALocalInfo info; 29*47c6ae99SBarry Smith ierr = DAGetLocalInfo(da,&info);CHKERRQ(ierr); 30*47c6ae99SBarry Smith ierr = PetscViewerASCIISynchronizedPrintf(viewer,"Processor [%d] M %D N %D P %D m %D n %D p %D w %D s %D\n",rank,dd->M,dd->N,dd->P,dd->m,dd->n,dd->p,dd->w,dd->s);CHKERRQ(ierr); 31*47c6ae99SBarry Smith ierr = PetscViewerASCIISynchronizedPrintf(viewer,"X range of indices: %D %D, Y range of indices: %D %D, Z range of indices: %D %D\n", 32*47c6ae99SBarry Smith info.xs,info.xs+info.xm,info.ys,info.ys+info.ym,info.zs,info.zs+info.zm);CHKERRQ(ierr); 33*47c6ae99SBarry Smith #if !defined(PETSC_USE_COMPLEX) 34*47c6ae99SBarry Smith if (dd->coordinates) { 35*47c6ae99SBarry Smith PetscInt last; 36*47c6ae99SBarry Smith const PetscReal *coors; 37*47c6ae99SBarry Smith ierr = VecGetArrayRead(dd->coordinates,&coors);CHKERRQ(ierr); 38*47c6ae99SBarry Smith ierr = VecGetLocalSize(dd->coordinates,&last);CHKERRQ(ierr); 39*47c6ae99SBarry Smith last = last - 3; 40*47c6ae99SBarry Smith ierr = PetscViewerASCIISynchronizedPrintf(viewer,"Lower left corner %G %G %G : Upper right %G %G %G\n",coors[0],coors[1],coors[2],coors[last],coors[last+1],coors[last+2]);CHKERRQ(ierr); 41*47c6ae99SBarry Smith ierr = VecRestoreArrayRead(dd->coordinates,&coors);CHKERRQ(ierr); 42*47c6ae99SBarry Smith } 43*47c6ae99SBarry Smith #endif 44*47c6ae99SBarry Smith ierr = PetscViewerFlush(viewer);CHKERRQ(ierr); 45*47c6ae99SBarry Smith } 46*47c6ae99SBarry Smith } else if (isdraw) { 47*47c6ae99SBarry Smith PetscDraw draw; 48*47c6ae99SBarry Smith PetscReal ymin = -1.0,ymax = (PetscReal)dd->N; 49*47c6ae99SBarry Smith PetscReal xmin = -1.0,xmax = (PetscReal)((dd->M+2)*dd->P),x,y,ycoord,xcoord; 50*47c6ae99SBarry Smith PetscInt k,plane,base,*idx; 51*47c6ae99SBarry Smith char node[10]; 52*47c6ae99SBarry Smith PetscBool isnull; 53*47c6ae99SBarry Smith 54*47c6ae99SBarry Smith ierr = PetscViewerDrawGetDraw(viewer,0,&draw);CHKERRQ(ierr); 55*47c6ae99SBarry Smith ierr = PetscDrawIsNull(draw,&isnull);CHKERRQ(ierr); if (isnull) PetscFunctionReturn(0); 56*47c6ae99SBarry Smith ierr = PetscDrawSetCoordinates(draw,xmin,ymin,xmax,ymax);CHKERRQ(ierr); 57*47c6ae99SBarry Smith ierr = PetscDrawSynchronizedClear(draw);CHKERRQ(ierr); 58*47c6ae99SBarry Smith 59*47c6ae99SBarry Smith /* first processor draw all node lines */ 60*47c6ae99SBarry Smith if (!rank) { 61*47c6ae99SBarry Smith for (k=0; k<dd->P; k++) { 62*47c6ae99SBarry Smith ymin = 0.0; ymax = (PetscReal)(dd->N - 1); 63*47c6ae99SBarry Smith for (xmin=(PetscReal)(k*(dd->M+1)); xmin<(PetscReal)(dd->M+(k*(dd->M+1))); xmin++) { 64*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmin,ymin,xmin,ymax,PETSC_DRAW_BLACK);CHKERRQ(ierr); 65*47c6ae99SBarry Smith } 66*47c6ae99SBarry Smith 67*47c6ae99SBarry Smith xmin = (PetscReal)(k*(dd->M+1)); xmax = xmin + (PetscReal)(dd->M - 1); 68*47c6ae99SBarry Smith for (ymin=0; ymin<(PetscReal)dd->N; ymin++) { 69*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmin,ymin,xmax,ymin,PETSC_DRAW_BLACK);CHKERRQ(ierr); 70*47c6ae99SBarry Smith } 71*47c6ae99SBarry Smith } 72*47c6ae99SBarry Smith } 73*47c6ae99SBarry Smith ierr = PetscDrawSynchronizedFlush(draw);CHKERRQ(ierr); 74*47c6ae99SBarry Smith ierr = PetscDrawPause(draw);CHKERRQ(ierr); 75*47c6ae99SBarry Smith 76*47c6ae99SBarry Smith for (k=0; k<dd->P; k++) { /*Go through and draw for each plane*/ 77*47c6ae99SBarry Smith if ((k >= dd->zs) && (k < dd->ze)) { 78*47c6ae99SBarry Smith /* draw my box */ 79*47c6ae99SBarry Smith ymin = dd->ys; 80*47c6ae99SBarry Smith ymax = dd->ye - 1; 81*47c6ae99SBarry Smith xmin = dd->xs/dd->w + (dd->M+1)*k; 82*47c6ae99SBarry Smith xmax =(dd->xe-1)/dd->w + (dd->M+1)*k; 83*47c6ae99SBarry Smith 84*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmin,ymin,xmax,ymin,PETSC_DRAW_RED);CHKERRQ(ierr); 85*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmin,ymin,xmin,ymax,PETSC_DRAW_RED);CHKERRQ(ierr); 86*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmin,ymax,xmax,ymax,PETSC_DRAW_RED);CHKERRQ(ierr); 87*47c6ae99SBarry Smith ierr = PetscDrawLine(draw,xmax,ymin,xmax,ymax,PETSC_DRAW_RED);CHKERRQ(ierr); 88*47c6ae99SBarry Smith 89*47c6ae99SBarry Smith xmin = dd->xs/dd->w; 90*47c6ae99SBarry Smith xmax =(dd->xe-1)/dd->w; 91*47c6ae99SBarry Smith 92*47c6ae99SBarry Smith /* put in numbers*/ 93*47c6ae99SBarry Smith base = (dd->base+(dd->xe-dd->xs)*(dd->ye-dd->ys)*(k-dd->zs))/dd->w; 94*47c6ae99SBarry Smith 95*47c6ae99SBarry Smith /* Identify which processor owns the box */ 96*47c6ae99SBarry Smith sprintf(node,"%d",rank); 97*47c6ae99SBarry Smith ierr = PetscDrawString(draw,xmin+(dd->M+1)*k+.2,ymin+.3,PETSC_DRAW_RED,node);CHKERRQ(ierr); 98*47c6ae99SBarry Smith 99*47c6ae99SBarry Smith for (y=ymin; y<=ymax; y++) { 100*47c6ae99SBarry Smith for (x=xmin+(dd->M+1)*k; x<=xmax+(dd->M+1)*k; x++) { 101*47c6ae99SBarry Smith sprintf(node,"%d",(int)base++); 102*47c6ae99SBarry Smith ierr = PetscDrawString(draw,x,y,PETSC_DRAW_BLACK,node);CHKERRQ(ierr); 103*47c6ae99SBarry Smith } 104*47c6ae99SBarry Smith } 105*47c6ae99SBarry Smith 106*47c6ae99SBarry Smith } 107*47c6ae99SBarry Smith } 108*47c6ae99SBarry Smith ierr = PetscDrawSynchronizedFlush(draw);CHKERRQ(ierr); 109*47c6ae99SBarry Smith ierr = PetscDrawPause(draw);CHKERRQ(ierr); 110*47c6ae99SBarry Smith 111*47c6ae99SBarry Smith for (k=0-dd->s; k<dd->P+dd->s; k++) { 112*47c6ae99SBarry Smith /* Go through and draw for each plane */ 113*47c6ae99SBarry Smith if ((k >= dd->Zs) && (k < dd->Ze)) { 114*47c6ae99SBarry Smith 115*47c6ae99SBarry Smith /* overlay ghost numbers, useful for error checking */ 116*47c6ae99SBarry Smith base = (dd->Xe-dd->Xs)*(dd->Ye-dd->Ys)*(k-dd->Zs); idx = dd->idx; 117*47c6ae99SBarry Smith plane=k; 118*47c6ae99SBarry Smith /* Keep z wrap around points on the dradrawg */ 119*47c6ae99SBarry Smith if (k<0) { plane=dd->P+k; } 120*47c6ae99SBarry Smith if (k>=dd->P) { plane=k-dd->P; } 121*47c6ae99SBarry Smith ymin = dd->Ys; ymax = dd->Ye; 122*47c6ae99SBarry Smith xmin = (dd->M+1)*plane*dd->w; 123*47c6ae99SBarry Smith xmax = (dd->M+1)*plane*dd->w+dd->M*dd->w; 124*47c6ae99SBarry Smith for (y=ymin; y<ymax; y++) { 125*47c6ae99SBarry Smith for (x=xmin+dd->Xs; x<xmin+dd->Xe; x+=dd->w) { 126*47c6ae99SBarry Smith sprintf(node,"%d",(int)(idx[base]/dd->w)); 127*47c6ae99SBarry Smith ycoord = y; 128*47c6ae99SBarry Smith /*Keep y wrap around points on drawing */ 129*47c6ae99SBarry Smith if (y<0) { ycoord = dd->N+y; } 130*47c6ae99SBarry Smith 131*47c6ae99SBarry Smith if (y>=dd->N) { ycoord = y-dd->N; } 132*47c6ae99SBarry Smith xcoord = x; /* Keep x wrap points on drawing */ 133*47c6ae99SBarry Smith 134*47c6ae99SBarry Smith if (x<xmin) { xcoord = xmax - (xmin-x); } 135*47c6ae99SBarry Smith if (x>=xmax) { xcoord = xmin + (x-xmax); } 136*47c6ae99SBarry Smith ierr = PetscDrawString(draw,xcoord/dd->w,ycoord,PETSC_DRAW_BLUE,node);CHKERRQ(ierr); 137*47c6ae99SBarry Smith base+=dd->w; 138*47c6ae99SBarry Smith } 139*47c6ae99SBarry Smith } 140*47c6ae99SBarry Smith } 141*47c6ae99SBarry Smith } 142*47c6ae99SBarry Smith ierr = PetscDrawSynchronizedFlush(draw);CHKERRQ(ierr); 143*47c6ae99SBarry Smith ierr = PetscDrawPause(draw);CHKERRQ(ierr); 144*47c6ae99SBarry Smith } else { 145*47c6ae99SBarry Smith SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Viewer type %s not supported for DA 3d",((PetscObject)viewer)->type_name); 146*47c6ae99SBarry Smith } 147*47c6ae99SBarry Smith PetscFunctionReturn(0); 148*47c6ae99SBarry Smith } 149*47c6ae99SBarry Smith 150*47c6ae99SBarry Smith EXTERN_C_BEGIN 151*47c6ae99SBarry Smith #undef __FUNCT__ 152*47c6ae99SBarry Smith #define __FUNCT__ "DACreate_3D" 153*47c6ae99SBarry Smith PetscErrorCode PETSCDM_DLLEXPORT DACreate_3D(DA da) 154*47c6ae99SBarry Smith { 155*47c6ae99SBarry Smith DM_DA *dd = (DM_DA*)da->data; 156*47c6ae99SBarry Smith const PetscInt dim = dd->dim; 157*47c6ae99SBarry Smith const PetscInt M = dd->M; 158*47c6ae99SBarry Smith const PetscInt N = dd->N; 159*47c6ae99SBarry Smith const PetscInt P = dd->P; 160*47c6ae99SBarry Smith PetscInt m = dd->m; 161*47c6ae99SBarry Smith PetscInt n = dd->n; 162*47c6ae99SBarry Smith PetscInt p = dd->p; 163*47c6ae99SBarry Smith const PetscInt dof = dd->w; 164*47c6ae99SBarry Smith const PetscInt s = dd->s; 165*47c6ae99SBarry Smith const DAPeriodicType wrap = dd->wrap; 166*47c6ae99SBarry Smith const DAStencilType stencil_type = dd->stencil_type; 167*47c6ae99SBarry Smith PetscInt *lx = dd->lx; 168*47c6ae99SBarry Smith PetscInt *ly = dd->ly; 169*47c6ae99SBarry Smith PetscInt *lz = dd->lz; 170*47c6ae99SBarry Smith MPI_Comm comm; 171*47c6ae99SBarry Smith PetscMPIInt rank,size; 172*47c6ae99SBarry Smith PetscInt xs = 0,xe,ys = 0,ye,zs = 0,ze,x = 0,y = 0,z = 0,Xs,Xe,Ys,Ye,Zs,Ze,start,end,pm; 173*47c6ae99SBarry Smith PetscInt left,up,down,bottom,top,i,j,k,*idx,nn; 174*47c6ae99SBarry Smith PetscInt n0,n1,n2,n3,n4,n5,n6,n7,n8,n9,n10,n11,n12,n14; 175*47c6ae99SBarry Smith PetscInt n15,n16,n17,n18,n19,n20,n21,n22,n23,n24,n25,n26; 176*47c6ae99SBarry Smith PetscInt *bases,*ldims,x_t,y_t,z_t,s_t,base,count,s_x,s_y,s_z; 177*47c6ae99SBarry Smith PetscInt sn0 = 0,sn1 = 0,sn2 = 0,sn3 = 0,sn5 = 0,sn6 = 0,sn7 = 0; 178*47c6ae99SBarry Smith PetscInt sn8 = 0,sn9 = 0,sn11 = 0,sn15 = 0,sn24 = 0,sn25 = 0,sn26 = 0; 179*47c6ae99SBarry Smith PetscInt sn17 = 0,sn18 = 0,sn19 = 0,sn20 = 0,sn21 = 0,sn23 = 0; 180*47c6ae99SBarry Smith Vec local,global; 181*47c6ae99SBarry Smith VecScatter ltog,gtol; 182*47c6ae99SBarry Smith IS to,from; 183*47c6ae99SBarry Smith PetscErrorCode ierr; 184*47c6ae99SBarry Smith 185*47c6ae99SBarry Smith PetscFunctionBegin; 186*47c6ae99SBarry Smith #ifndef PETSC_USE_DYNAMIC_LIBRARIES 187*47c6ae99SBarry Smith ierr = DMInitializePackage(PETSC_NULL);CHKERRQ(ierr); 188*47c6ae99SBarry Smith #endif 189*47c6ae99SBarry Smith 190*47c6ae99SBarry Smith if (dim != PETSC_DECIDE && dim != 3) SETERRQ1(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Dimension should be 3: %D",dim); 191*47c6ae99SBarry Smith if (dof < 1) SETERRQ1(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Must have 1 or more degrees of freedom per node: %D",dof); 192*47c6ae99SBarry Smith if (s < 0) SETERRQ1(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Stencil width cannot be negative: %D",s); 193*47c6ae99SBarry Smith 194*47c6ae99SBarry Smith ierr = PetscObjectGetComm((PetscObject) da, &comm);CHKERRQ(ierr); 195*47c6ae99SBarry Smith ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr); 196*47c6ae99SBarry Smith ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 197*47c6ae99SBarry Smith 198*47c6ae99SBarry Smith dd->dim = 3; 199*47c6ae99SBarry Smith ierr = PetscMalloc(dof*sizeof(char*),&dd->fieldname);CHKERRQ(ierr); 200*47c6ae99SBarry Smith ierr = PetscMemzero(dd->fieldname,dof*sizeof(char*));CHKERRQ(ierr); 201*47c6ae99SBarry Smith 202*47c6ae99SBarry Smith if (m != PETSC_DECIDE) { 203*47c6ae99SBarry Smith if (m < 1) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Non-positive number of processors in X direction: %D",m); 204*47c6ae99SBarry Smith else if (m > size) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many processors in X direction: %D %d",m,size); 205*47c6ae99SBarry Smith } 206*47c6ae99SBarry Smith if (n != PETSC_DECIDE) { 207*47c6ae99SBarry Smith if (n < 1) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Non-positive number of processors in Y direction: %D",n); 208*47c6ae99SBarry Smith else if (n > size) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many processors in Y direction: %D %d",n,size); 209*47c6ae99SBarry Smith } 210*47c6ae99SBarry Smith if (p != PETSC_DECIDE) { 211*47c6ae99SBarry Smith if (p < 1) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Non-positive number of processors in Z direction: %D",p); 212*47c6ae99SBarry Smith else if (p > size) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many processors in Z direction: %D %d",p,size); 213*47c6ae99SBarry Smith } 214*47c6ae99SBarry Smith 215*47c6ae99SBarry Smith /* Partition the array among the processors */ 216*47c6ae99SBarry Smith if (m == PETSC_DECIDE && n != PETSC_DECIDE && p != PETSC_DECIDE) { 217*47c6ae99SBarry Smith m = size/(n*p); 218*47c6ae99SBarry Smith } else if (m != PETSC_DECIDE && n == PETSC_DECIDE && p != PETSC_DECIDE) { 219*47c6ae99SBarry Smith n = size/(m*p); 220*47c6ae99SBarry Smith } else if (m != PETSC_DECIDE && n != PETSC_DECIDE && p == PETSC_DECIDE) { 221*47c6ae99SBarry Smith p = size/(m*n); 222*47c6ae99SBarry Smith } else if (m == PETSC_DECIDE && n == PETSC_DECIDE && p != PETSC_DECIDE) { 223*47c6ae99SBarry Smith /* try for squarish distribution */ 224*47c6ae99SBarry Smith m = (int)(0.5 + sqrt(((PetscReal)M)*((PetscReal)size)/((PetscReal)N*p))); 225*47c6ae99SBarry Smith if (!m) m = 1; 226*47c6ae99SBarry Smith while (m > 0) { 227*47c6ae99SBarry Smith n = size/(m*p); 228*47c6ae99SBarry Smith if (m*n*p == size) break; 229*47c6ae99SBarry Smith m--; 230*47c6ae99SBarry Smith } 231*47c6ae99SBarry Smith if (!m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"bad p value: p = %D",p); 232*47c6ae99SBarry Smith if (M > N && m < n) {PetscInt _m = m; m = n; n = _m;} 233*47c6ae99SBarry Smith } else if (m == PETSC_DECIDE && n != PETSC_DECIDE && p == PETSC_DECIDE) { 234*47c6ae99SBarry Smith /* try for squarish distribution */ 235*47c6ae99SBarry Smith m = (int)(0.5 + sqrt(((PetscReal)M)*((PetscReal)size)/((PetscReal)P*n))); 236*47c6ae99SBarry Smith if (!m) m = 1; 237*47c6ae99SBarry Smith while (m > 0) { 238*47c6ae99SBarry Smith p = size/(m*n); 239*47c6ae99SBarry Smith if (m*n*p == size) break; 240*47c6ae99SBarry Smith m--; 241*47c6ae99SBarry Smith } 242*47c6ae99SBarry Smith if (!m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"bad n value: n = %D",n); 243*47c6ae99SBarry Smith if (M > P && m < p) {PetscInt _m = m; m = p; p = _m;} 244*47c6ae99SBarry Smith } else if (m != PETSC_DECIDE && n == PETSC_DECIDE && p == PETSC_DECIDE) { 245*47c6ae99SBarry Smith /* try for squarish distribution */ 246*47c6ae99SBarry Smith n = (int)(0.5 + sqrt(((PetscReal)N)*((PetscReal)size)/((PetscReal)P*m))); 247*47c6ae99SBarry Smith if (!n) n = 1; 248*47c6ae99SBarry Smith while (n > 0) { 249*47c6ae99SBarry Smith p = size/(m*n); 250*47c6ae99SBarry Smith if (m*n*p == size) break; 251*47c6ae99SBarry Smith n--; 252*47c6ae99SBarry Smith } 253*47c6ae99SBarry Smith if (!n) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"bad m value: m = %D",n); 254*47c6ae99SBarry Smith if (N > P && n < p) {PetscInt _n = n; n = p; p = _n;} 255*47c6ae99SBarry Smith } else if (m == PETSC_DECIDE && n == PETSC_DECIDE && p == PETSC_DECIDE) { 256*47c6ae99SBarry Smith /* try for squarish distribution */ 257*47c6ae99SBarry Smith n = (PetscInt)(0.5 + pow(((PetscReal)N*N)*((PetscReal)size)/((PetscReal)P*M),(PetscReal)(1./3.))); 258*47c6ae99SBarry Smith if (!n) n = 1; 259*47c6ae99SBarry Smith while (n > 0) { 260*47c6ae99SBarry Smith pm = size/n; 261*47c6ae99SBarry Smith if (n*pm == size) break; 262*47c6ae99SBarry Smith n--; 263*47c6ae99SBarry Smith } 264*47c6ae99SBarry Smith if (!n) n = 1; 265*47c6ae99SBarry Smith m = (PetscInt)(0.5 + sqrt(((PetscReal)M)*((PetscReal)size)/((PetscReal)P*n))); 266*47c6ae99SBarry Smith if (!m) m = 1; 267*47c6ae99SBarry Smith while (m > 0) { 268*47c6ae99SBarry Smith p = size/(m*n); 269*47c6ae99SBarry Smith if (m*n*p == size) break; 270*47c6ae99SBarry Smith m--; 271*47c6ae99SBarry Smith } 272*47c6ae99SBarry Smith if (M > P && m < p) {PetscInt _m = m; m = p; p = _m;} 273*47c6ae99SBarry Smith } else if (m*n*p != size) SETERRQ(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Given Bad partition"); 274*47c6ae99SBarry Smith 275*47c6ae99SBarry Smith if (m*n*p != size) SETERRQ(((PetscObject)da)->comm,PETSC_ERR_PLIB,"Could not find good partition"); 276*47c6ae99SBarry Smith if (M < m) SETERRQ2(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Partition in x direction is too fine! %D %D",M,m); 277*47c6ae99SBarry Smith if (N < n) SETERRQ2(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Partition in y direction is too fine! %D %D",N,n); 278*47c6ae99SBarry Smith if (P < p) SETERRQ2(((PetscObject)da)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Partition in z direction is too fine! %D %D",P,p); 279*47c6ae99SBarry Smith 280*47c6ae99SBarry Smith /* 281*47c6ae99SBarry Smith Determine locally owned region 282*47c6ae99SBarry Smith [x, y, or z]s is the first local node number, [x, y, z] is the number of local nodes 283*47c6ae99SBarry Smith */ 284*47c6ae99SBarry Smith 285*47c6ae99SBarry Smith if (!lx) { 286*47c6ae99SBarry Smith ierr = PetscMalloc(m*sizeof(PetscInt), &dd->lx);CHKERRQ(ierr); 287*47c6ae99SBarry Smith lx = dd->lx; 288*47c6ae99SBarry Smith for (i=0; i<m; i++) { 289*47c6ae99SBarry Smith lx[i] = M/m + ((M % m) > (i % m)); 290*47c6ae99SBarry Smith } 291*47c6ae99SBarry Smith } 292*47c6ae99SBarry Smith x = lx[rank % m]; 293*47c6ae99SBarry Smith xs = 0; 294*47c6ae99SBarry Smith for (i=0; i<(rank%m); i++) { xs += lx[i];} 295*47c6ae99SBarry Smith if (m > 1 && x < s) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column width is too thin for stencil! %D %D",x,s); 296*47c6ae99SBarry Smith 297*47c6ae99SBarry Smith if (!ly) { 298*47c6ae99SBarry Smith ierr = PetscMalloc(n*sizeof(PetscInt), &dd->ly);CHKERRQ(ierr); 299*47c6ae99SBarry Smith ly = dd->ly; 300*47c6ae99SBarry Smith for (i=0; i<n; i++) { 301*47c6ae99SBarry Smith ly[i] = N/n + ((N % n) > (i % n)); 302*47c6ae99SBarry Smith } 303*47c6ae99SBarry Smith } 304*47c6ae99SBarry Smith y = ly[(rank % (m*n))/m]; 305*47c6ae99SBarry Smith if (n > 1 && y < s) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Row width is too thin for stencil! %D %D",y,s); 306*47c6ae99SBarry Smith ys = 0; 307*47c6ae99SBarry Smith for (i=0; i<(rank % (m*n))/m; i++) { ys += ly[i];} 308*47c6ae99SBarry Smith 309*47c6ae99SBarry Smith if (!lz) { 310*47c6ae99SBarry Smith ierr = PetscMalloc(p*sizeof(PetscInt), &dd->lz);CHKERRQ(ierr); 311*47c6ae99SBarry Smith lz = dd->lz; 312*47c6ae99SBarry Smith for (i=0; i<p; i++) { 313*47c6ae99SBarry Smith lz[i] = P/p + ((P % p) > (i % p)); 314*47c6ae99SBarry Smith } 315*47c6ae99SBarry Smith } 316*47c6ae99SBarry Smith z = lz[rank/(m*n)]; 317*47c6ae99SBarry Smith if (p > 1 && z < s) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Plane width is too thin for stencil! %D %D",z,s); 318*47c6ae99SBarry Smith zs = 0; 319*47c6ae99SBarry Smith for (i=0; i<(rank/(m*n)); i++) { zs += lz[i];} 320*47c6ae99SBarry Smith ye = ys + y; 321*47c6ae99SBarry Smith xe = xs + x; 322*47c6ae99SBarry Smith ze = zs + z; 323*47c6ae99SBarry Smith 324*47c6ae99SBarry Smith /* determine ghost region */ 325*47c6ae99SBarry Smith /* Assume No Periodicity */ 326*47c6ae99SBarry Smith if (xs-s > 0) Xs = xs - s; else Xs = 0; 327*47c6ae99SBarry Smith if (ys-s > 0) Ys = ys - s; else Ys = 0; 328*47c6ae99SBarry Smith if (zs-s > 0) Zs = zs - s; else Zs = 0; 329*47c6ae99SBarry Smith if (xe+s <= M) Xe = xe + s; else Xe = M; 330*47c6ae99SBarry Smith if (ye+s <= N) Ye = ye + s; else Ye = N; 331*47c6ae99SBarry Smith if (ze+s <= P) Ze = ze + s; else Ze = P; 332*47c6ae99SBarry Smith 333*47c6ae99SBarry Smith /* X Periodic */ 334*47c6ae99SBarry Smith if (DAXPeriodic(wrap)){ 335*47c6ae99SBarry Smith Xs = xs - s; 336*47c6ae99SBarry Smith Xe = xe + s; 337*47c6ae99SBarry Smith } 338*47c6ae99SBarry Smith 339*47c6ae99SBarry Smith /* Y Periodic */ 340*47c6ae99SBarry Smith if (DAYPeriodic(wrap)){ 341*47c6ae99SBarry Smith Ys = ys - s; 342*47c6ae99SBarry Smith Ye = ye + s; 343*47c6ae99SBarry Smith } 344*47c6ae99SBarry Smith 345*47c6ae99SBarry Smith /* Z Periodic */ 346*47c6ae99SBarry Smith if (DAZPeriodic(wrap)){ 347*47c6ae99SBarry Smith Zs = zs - s; 348*47c6ae99SBarry Smith Ze = ze + s; 349*47c6ae99SBarry Smith } 350*47c6ae99SBarry Smith 351*47c6ae99SBarry Smith /* Resize all X parameters to reflect w */ 352*47c6ae99SBarry Smith x *= dof; 353*47c6ae99SBarry Smith xs *= dof; 354*47c6ae99SBarry Smith xe *= dof; 355*47c6ae99SBarry Smith Xs *= dof; 356*47c6ae99SBarry Smith Xe *= dof; 357*47c6ae99SBarry Smith s_x = s*dof; 358*47c6ae99SBarry Smith s_y = s; 359*47c6ae99SBarry Smith s_z = s; 360*47c6ae99SBarry Smith 361*47c6ae99SBarry Smith /* determine starting point of each processor */ 362*47c6ae99SBarry Smith nn = x*y*z; 363*47c6ae99SBarry Smith ierr = PetscMalloc2(size+1,PetscInt,&bases,size,PetscInt,&ldims);CHKERRQ(ierr); 364*47c6ae99SBarry Smith ierr = MPI_Allgather(&nn,1,MPIU_INT,ldims,1,MPIU_INT,comm);CHKERRQ(ierr); 365*47c6ae99SBarry Smith bases[0] = 0; 366*47c6ae99SBarry Smith for (i=1; i<=size; i++) { 367*47c6ae99SBarry Smith bases[i] = ldims[i-1]; 368*47c6ae99SBarry Smith } 369*47c6ae99SBarry Smith for (i=1; i<=size; i++) { 370*47c6ae99SBarry Smith bases[i] += bases[i-1]; 371*47c6ae99SBarry Smith } 372*47c6ae99SBarry Smith 373*47c6ae99SBarry Smith /* allocate the base parallel and sequential vectors */ 374*47c6ae99SBarry Smith dd->Nlocal = x*y*z; 375*47c6ae99SBarry Smith ierr = VecCreateMPIWithArray(comm,dd->Nlocal,PETSC_DECIDE,0,&global);CHKERRQ(ierr); 376*47c6ae99SBarry Smith ierr = VecSetBlockSize(global,dof);CHKERRQ(ierr); 377*47c6ae99SBarry Smith dd->nlocal = (Xe-Xs)*(Ye-Ys)*(Ze-Zs); 378*47c6ae99SBarry Smith ierr = VecCreateSeqWithArray(MPI_COMM_SELF,dd->nlocal,0,&local);CHKERRQ(ierr); 379*47c6ae99SBarry Smith ierr = VecSetBlockSize(local,dof);CHKERRQ(ierr); 380*47c6ae99SBarry Smith 381*47c6ae99SBarry Smith /* generate appropriate vector scatters */ 382*47c6ae99SBarry Smith /* local to global inserts non-ghost point region into global */ 383*47c6ae99SBarry Smith ierr = VecGetOwnershipRange(global,&start,&end);CHKERRQ(ierr); 384*47c6ae99SBarry Smith ierr = ISCreateStride(comm,x*y*z,start,1,&to);CHKERRQ(ierr); 385*47c6ae99SBarry Smith 386*47c6ae99SBarry Smith left = xs - Xs; 387*47c6ae99SBarry Smith bottom = ys - Ys; top = bottom + y; 388*47c6ae99SBarry Smith down = zs - Zs; up = down + z; 389*47c6ae99SBarry Smith count = x*(top-bottom)*(up-down); 390*47c6ae99SBarry Smith ierr = PetscMalloc(count*sizeof(PetscInt)/dof,&idx);CHKERRQ(ierr); 391*47c6ae99SBarry Smith count = 0; 392*47c6ae99SBarry Smith for (i=down; i<up; i++) { 393*47c6ae99SBarry Smith for (j=bottom; j<top; j++) { 394*47c6ae99SBarry Smith for (k=0; k<x; k += dof) { 395*47c6ae99SBarry Smith idx[count++] = ((left+j*(Xe-Xs))+i*(Xe-Xs)*(Ye-Ys) + k)/dof; 396*47c6ae99SBarry Smith } 397*47c6ae99SBarry Smith } 398*47c6ae99SBarry Smith } 399*47c6ae99SBarry Smith 400*47c6ae99SBarry Smith ierr = ISCreateBlock(comm,dof,count,idx,PETSC_OWN_POINTER,&from);CHKERRQ(ierr); 401*47c6ae99SBarry Smith 402*47c6ae99SBarry Smith ierr = VecScatterCreate(local,from,global,to,<og);CHKERRQ(ierr); 403*47c6ae99SBarry Smith ierr = PetscLogObjectParent(da,ltog);CHKERRQ(ierr); 404*47c6ae99SBarry Smith ierr = ISDestroy(from);CHKERRQ(ierr); 405*47c6ae99SBarry Smith ierr = ISDestroy(to);CHKERRQ(ierr); 406*47c6ae99SBarry Smith 407*47c6ae99SBarry Smith /* global to local must include ghost points */ 408*47c6ae99SBarry Smith if (stencil_type == DA_STENCIL_BOX) { 409*47c6ae99SBarry Smith ierr = ISCreateStride(comm,(Xe-Xs)*(Ye-Ys)*(Ze-Zs),0,1,&to);CHKERRQ(ierr); 410*47c6ae99SBarry Smith } else { 411*47c6ae99SBarry Smith /* This is way ugly! We need to list the funny cross type region */ 412*47c6ae99SBarry Smith /* the bottom chunck */ 413*47c6ae99SBarry Smith left = xs - Xs; 414*47c6ae99SBarry Smith bottom = ys - Ys; top = bottom + y; 415*47c6ae99SBarry Smith down = zs - Zs; up = down + z; 416*47c6ae99SBarry Smith count = down*(top-bottom)*x + (up-down)*(bottom*x + (top-bottom)*(Xe-Xs) + (Ye-Ys-top)*x) + (Ze-Zs-up)*(top-bottom)*x; 417*47c6ae99SBarry Smith ierr = PetscMalloc(count*sizeof(PetscInt)/dof,&idx);CHKERRQ(ierr); 418*47c6ae99SBarry Smith count = 0; 419*47c6ae99SBarry Smith for (i=0; i<down; i++) { 420*47c6ae99SBarry Smith for (j=bottom; j<top; j++) { 421*47c6ae99SBarry Smith for (k=0; k<x; k += dof) idx[count++] = left+j*(Xe-Xs)+i*(Xe-Xs)*(Ye-Ys)+k; 422*47c6ae99SBarry Smith } 423*47c6ae99SBarry Smith } 424*47c6ae99SBarry Smith /* the middle piece */ 425*47c6ae99SBarry Smith for (i=down; i<up; i++) { 426*47c6ae99SBarry Smith /* front */ 427*47c6ae99SBarry Smith for (j=0; j<bottom; j++) { 428*47c6ae99SBarry Smith for (k=0; k<x; k += dof) idx[count++] = left+j*(Xe-Xs)+i*(Xe-Xs)*(Ye-Ys)+k; 429*47c6ae99SBarry Smith } 430*47c6ae99SBarry Smith /* middle */ 431*47c6ae99SBarry Smith for (j=bottom; j<top; j++) { 432*47c6ae99SBarry Smith for (k=0; k<Xe-Xs; k += dof) idx[count++] = j*(Xe-Xs)+i*(Xe-Xs)*(Ye-Ys)+k; 433*47c6ae99SBarry Smith } 434*47c6ae99SBarry Smith /* back */ 435*47c6ae99SBarry Smith for (j=top; j<Ye-Ys; j++) { 436*47c6ae99SBarry Smith for (k=0; k<x; k += dof) idx[count++] = left+j*(Xe-Xs)+i*(Xe-Xs)*(Ye-Ys)+k; 437*47c6ae99SBarry Smith } 438*47c6ae99SBarry Smith } 439*47c6ae99SBarry Smith /* the top piece */ 440*47c6ae99SBarry Smith for (i=up; i<Ze-Zs; i++) { 441*47c6ae99SBarry Smith for (j=bottom; j<top; j++) { 442*47c6ae99SBarry Smith for (k=0; k<x; k += dof) idx[count++] = left+j*(Xe-Xs)+i*(Xe-Xs)*(Ye-Ys)+k; 443*47c6ae99SBarry Smith } 444*47c6ae99SBarry Smith } 445*47c6ae99SBarry Smith for (i=0; i<count; i++) idx[i] = idx[i]/dof; 446*47c6ae99SBarry Smith ierr = ISCreateBlock(comm,dof,count,idx,PETSC_OWN_POINTER,&to);CHKERRQ(ierr); 447*47c6ae99SBarry Smith } 448*47c6ae99SBarry Smith 449*47c6ae99SBarry Smith /* determine who lies on each side of use stored in n24 n25 n26 450*47c6ae99SBarry Smith n21 n22 n23 451*47c6ae99SBarry Smith n18 n19 n20 452*47c6ae99SBarry Smith 453*47c6ae99SBarry Smith n15 n16 n17 454*47c6ae99SBarry Smith n12 n14 455*47c6ae99SBarry Smith n9 n10 n11 456*47c6ae99SBarry Smith 457*47c6ae99SBarry Smith n6 n7 n8 458*47c6ae99SBarry Smith n3 n4 n5 459*47c6ae99SBarry Smith n0 n1 n2 460*47c6ae99SBarry Smith */ 461*47c6ae99SBarry Smith 462*47c6ae99SBarry Smith /* Solve for X,Y, and Z Periodic Case First, Then Modify Solution */ 463*47c6ae99SBarry Smith 464*47c6ae99SBarry Smith /* Assume Nodes are Internal to the Cube */ 465*47c6ae99SBarry Smith 466*47c6ae99SBarry Smith n0 = rank - m*n - m - 1; 467*47c6ae99SBarry Smith n1 = rank - m*n - m; 468*47c6ae99SBarry Smith n2 = rank - m*n - m + 1; 469*47c6ae99SBarry Smith n3 = rank - m*n -1; 470*47c6ae99SBarry Smith n4 = rank - m*n; 471*47c6ae99SBarry Smith n5 = rank - m*n + 1; 472*47c6ae99SBarry Smith n6 = rank - m*n + m - 1; 473*47c6ae99SBarry Smith n7 = rank - m*n + m; 474*47c6ae99SBarry Smith n8 = rank - m*n + m + 1; 475*47c6ae99SBarry Smith 476*47c6ae99SBarry Smith n9 = rank - m - 1; 477*47c6ae99SBarry Smith n10 = rank - m; 478*47c6ae99SBarry Smith n11 = rank - m + 1; 479*47c6ae99SBarry Smith n12 = rank - 1; 480*47c6ae99SBarry Smith n14 = rank + 1; 481*47c6ae99SBarry Smith n15 = rank + m - 1; 482*47c6ae99SBarry Smith n16 = rank + m; 483*47c6ae99SBarry Smith n17 = rank + m + 1; 484*47c6ae99SBarry Smith 485*47c6ae99SBarry Smith n18 = rank + m*n - m - 1; 486*47c6ae99SBarry Smith n19 = rank + m*n - m; 487*47c6ae99SBarry Smith n20 = rank + m*n - m + 1; 488*47c6ae99SBarry Smith n21 = rank + m*n - 1; 489*47c6ae99SBarry Smith n22 = rank + m*n; 490*47c6ae99SBarry Smith n23 = rank + m*n + 1; 491*47c6ae99SBarry Smith n24 = rank + m*n + m - 1; 492*47c6ae99SBarry Smith n25 = rank + m*n + m; 493*47c6ae99SBarry Smith n26 = rank + m*n + m + 1; 494*47c6ae99SBarry Smith 495*47c6ae99SBarry Smith /* Assume Pieces are on Faces of Cube */ 496*47c6ae99SBarry Smith 497*47c6ae99SBarry Smith if (xs == 0) { /* First assume not corner or edge */ 498*47c6ae99SBarry Smith n0 = rank -1 - (m*n); 499*47c6ae99SBarry Smith n3 = rank + m -1 - (m*n); 500*47c6ae99SBarry Smith n6 = rank + 2*m -1 - (m*n); 501*47c6ae99SBarry Smith n9 = rank -1; 502*47c6ae99SBarry Smith n12 = rank + m -1; 503*47c6ae99SBarry Smith n15 = rank + 2*m -1; 504*47c6ae99SBarry Smith n18 = rank -1 + (m*n); 505*47c6ae99SBarry Smith n21 = rank + m -1 + (m*n); 506*47c6ae99SBarry Smith n24 = rank + 2*m -1 + (m*n); 507*47c6ae99SBarry Smith } 508*47c6ae99SBarry Smith 509*47c6ae99SBarry Smith if (xe == M*dof) { /* First assume not corner or edge */ 510*47c6ae99SBarry Smith n2 = rank -2*m +1 - (m*n); 511*47c6ae99SBarry Smith n5 = rank - m +1 - (m*n); 512*47c6ae99SBarry Smith n8 = rank +1 - (m*n); 513*47c6ae99SBarry Smith n11 = rank -2*m +1; 514*47c6ae99SBarry Smith n14 = rank - m +1; 515*47c6ae99SBarry Smith n17 = rank +1; 516*47c6ae99SBarry Smith n20 = rank -2*m +1 + (m*n); 517*47c6ae99SBarry Smith n23 = rank - m +1 + (m*n); 518*47c6ae99SBarry Smith n26 = rank +1 + (m*n); 519*47c6ae99SBarry Smith } 520*47c6ae99SBarry Smith 521*47c6ae99SBarry Smith if (ys==0) { /* First assume not corner or edge */ 522*47c6ae99SBarry Smith n0 = rank + m * (n-1) -1 - (m*n); 523*47c6ae99SBarry Smith n1 = rank + m * (n-1) - (m*n); 524*47c6ae99SBarry Smith n2 = rank + m * (n-1) +1 - (m*n); 525*47c6ae99SBarry Smith n9 = rank + m * (n-1) -1; 526*47c6ae99SBarry Smith n10 = rank + m * (n-1); 527*47c6ae99SBarry Smith n11 = rank + m * (n-1) +1; 528*47c6ae99SBarry Smith n18 = rank + m * (n-1) -1 + (m*n); 529*47c6ae99SBarry Smith n19 = rank + m * (n-1) + (m*n); 530*47c6ae99SBarry Smith n20 = rank + m * (n-1) +1 + (m*n); 531*47c6ae99SBarry Smith } 532*47c6ae99SBarry Smith 533*47c6ae99SBarry Smith if (ye == N) { /* First assume not corner or edge */ 534*47c6ae99SBarry Smith n6 = rank - m * (n-1) -1 - (m*n); 535*47c6ae99SBarry Smith n7 = rank - m * (n-1) - (m*n); 536*47c6ae99SBarry Smith n8 = rank - m * (n-1) +1 - (m*n); 537*47c6ae99SBarry Smith n15 = rank - m * (n-1) -1; 538*47c6ae99SBarry Smith n16 = rank - m * (n-1); 539*47c6ae99SBarry Smith n17 = rank - m * (n-1) +1; 540*47c6ae99SBarry Smith n24 = rank - m * (n-1) -1 + (m*n); 541*47c6ae99SBarry Smith n25 = rank - m * (n-1) + (m*n); 542*47c6ae99SBarry Smith n26 = rank - m * (n-1) +1 + (m*n); 543*47c6ae99SBarry Smith } 544*47c6ae99SBarry Smith 545*47c6ae99SBarry Smith if (zs == 0) { /* First assume not corner or edge */ 546*47c6ae99SBarry Smith n0 = size - (m*n) + rank - m - 1; 547*47c6ae99SBarry Smith n1 = size - (m*n) + rank - m; 548*47c6ae99SBarry Smith n2 = size - (m*n) + rank - m + 1; 549*47c6ae99SBarry Smith n3 = size - (m*n) + rank - 1; 550*47c6ae99SBarry Smith n4 = size - (m*n) + rank; 551*47c6ae99SBarry Smith n5 = size - (m*n) + rank + 1; 552*47c6ae99SBarry Smith n6 = size - (m*n) + rank + m - 1; 553*47c6ae99SBarry Smith n7 = size - (m*n) + rank + m ; 554*47c6ae99SBarry Smith n8 = size - (m*n) + rank + m + 1; 555*47c6ae99SBarry Smith } 556*47c6ae99SBarry Smith 557*47c6ae99SBarry Smith if (ze == P) { /* First assume not corner or edge */ 558*47c6ae99SBarry Smith n18 = (m*n) - (size-rank) - m - 1; 559*47c6ae99SBarry Smith n19 = (m*n) - (size-rank) - m; 560*47c6ae99SBarry Smith n20 = (m*n) - (size-rank) - m + 1; 561*47c6ae99SBarry Smith n21 = (m*n) - (size-rank) - 1; 562*47c6ae99SBarry Smith n22 = (m*n) - (size-rank); 563*47c6ae99SBarry Smith n23 = (m*n) - (size-rank) + 1; 564*47c6ae99SBarry Smith n24 = (m*n) - (size-rank) + m - 1; 565*47c6ae99SBarry Smith n25 = (m*n) - (size-rank) + m; 566*47c6ae99SBarry Smith n26 = (m*n) - (size-rank) + m + 1; 567*47c6ae99SBarry Smith } 568*47c6ae99SBarry Smith 569*47c6ae99SBarry Smith if ((xs==0) && (zs==0)) { /* Assume an edge, not corner */ 570*47c6ae99SBarry Smith n0 = size - m*n + rank + m-1 - m; 571*47c6ae99SBarry Smith n3 = size - m*n + rank + m-1; 572*47c6ae99SBarry Smith n6 = size - m*n + rank + m-1 + m; 573*47c6ae99SBarry Smith } 574*47c6ae99SBarry Smith 575*47c6ae99SBarry Smith if ((xs==0) && (ze==P)) { /* Assume an edge, not corner */ 576*47c6ae99SBarry Smith n18 = m*n - (size - rank) + m-1 - m; 577*47c6ae99SBarry Smith n21 = m*n - (size - rank) + m-1; 578*47c6ae99SBarry Smith n24 = m*n - (size - rank) + m-1 + m; 579*47c6ae99SBarry Smith } 580*47c6ae99SBarry Smith 581*47c6ae99SBarry Smith if ((xs==0) && (ys==0)) { /* Assume an edge, not corner */ 582*47c6ae99SBarry Smith n0 = rank + m*n -1 - m*n; 583*47c6ae99SBarry Smith n9 = rank + m*n -1; 584*47c6ae99SBarry Smith n18 = rank + m*n -1 + m*n; 585*47c6ae99SBarry Smith } 586*47c6ae99SBarry Smith 587*47c6ae99SBarry Smith if ((xs==0) && (ye==N)) { /* Assume an edge, not corner */ 588*47c6ae99SBarry Smith n6 = rank - m*(n-1) + m-1 - m*n; 589*47c6ae99SBarry Smith n15 = rank - m*(n-1) + m-1; 590*47c6ae99SBarry Smith n24 = rank - m*(n-1) + m-1 + m*n; 591*47c6ae99SBarry Smith } 592*47c6ae99SBarry Smith 593*47c6ae99SBarry Smith if ((xe==M*dof) && (zs==0)) { /* Assume an edge, not corner */ 594*47c6ae99SBarry Smith n2 = size - (m*n-rank) - (m-1) - m; 595*47c6ae99SBarry Smith n5 = size - (m*n-rank) - (m-1); 596*47c6ae99SBarry Smith n8 = size - (m*n-rank) - (m-1) + m; 597*47c6ae99SBarry Smith } 598*47c6ae99SBarry Smith 599*47c6ae99SBarry Smith if ((xe==M*dof) && (ze==P)) { /* Assume an edge, not corner */ 600*47c6ae99SBarry Smith n20 = m*n - (size - rank) - (m-1) - m; 601*47c6ae99SBarry Smith n23 = m*n - (size - rank) - (m-1); 602*47c6ae99SBarry Smith n26 = m*n - (size - rank) - (m-1) + m; 603*47c6ae99SBarry Smith } 604*47c6ae99SBarry Smith 605*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0)) { /* Assume an edge, not corner */ 606*47c6ae99SBarry Smith n2 = rank + m*(n-1) - (m-1) - m*n; 607*47c6ae99SBarry Smith n11 = rank + m*(n-1) - (m-1); 608*47c6ae99SBarry Smith n20 = rank + m*(n-1) - (m-1) + m*n; 609*47c6ae99SBarry Smith } 610*47c6ae99SBarry Smith 611*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N)) { /* Assume an edge, not corner */ 612*47c6ae99SBarry Smith n8 = rank - m*n +1 - m*n; 613*47c6ae99SBarry Smith n17 = rank - m*n +1; 614*47c6ae99SBarry Smith n26 = rank - m*n +1 + m*n; 615*47c6ae99SBarry Smith } 616*47c6ae99SBarry Smith 617*47c6ae99SBarry Smith if ((ys==0) && (zs==0)) { /* Assume an edge, not corner */ 618*47c6ae99SBarry Smith n0 = size - m + rank -1; 619*47c6ae99SBarry Smith n1 = size - m + rank; 620*47c6ae99SBarry Smith n2 = size - m + rank +1; 621*47c6ae99SBarry Smith } 622*47c6ae99SBarry Smith 623*47c6ae99SBarry Smith if ((ys==0) && (ze==P)) { /* Assume an edge, not corner */ 624*47c6ae99SBarry Smith n18 = m*n - (size - rank) + m*(n-1) -1; 625*47c6ae99SBarry Smith n19 = m*n - (size - rank) + m*(n-1); 626*47c6ae99SBarry Smith n20 = m*n - (size - rank) + m*(n-1) +1; 627*47c6ae99SBarry Smith } 628*47c6ae99SBarry Smith 629*47c6ae99SBarry Smith if ((ye==N) && (zs==0)) { /* Assume an edge, not corner */ 630*47c6ae99SBarry Smith n6 = size - (m*n-rank) - m * (n-1) -1; 631*47c6ae99SBarry Smith n7 = size - (m*n-rank) - m * (n-1); 632*47c6ae99SBarry Smith n8 = size - (m*n-rank) - m * (n-1) +1; 633*47c6ae99SBarry Smith } 634*47c6ae99SBarry Smith 635*47c6ae99SBarry Smith if ((ye==N) && (ze==P)) { /* Assume an edge, not corner */ 636*47c6ae99SBarry Smith n24 = rank - (size-m) -1; 637*47c6ae99SBarry Smith n25 = rank - (size-m); 638*47c6ae99SBarry Smith n26 = rank - (size-m) +1; 639*47c6ae99SBarry Smith } 640*47c6ae99SBarry Smith 641*47c6ae99SBarry Smith /* Check for Corners */ 642*47c6ae99SBarry Smith if ((xs==0) && (ys==0) && (zs==0)) { n0 = size -1;} 643*47c6ae99SBarry Smith if ((xs==0) && (ys==0) && (ze==P)) { n18 = m*n-1;} 644*47c6ae99SBarry Smith if ((xs==0) && (ye==N) && (zs==0)) { n6 = (size-1)-m*(n-1);} 645*47c6ae99SBarry Smith if ((xs==0) && (ye==N) && (ze==P)) { n24 = m-1;} 646*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0) && (zs==0)) { n2 = size-m;} 647*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0) && (ze==P)) { n20 = m*n-m;} 648*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N) && (zs==0)) { n8 = size-m*n;} 649*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N) && (ze==P)) { n26 = 0;} 650*47c6ae99SBarry Smith 651*47c6ae99SBarry Smith /* Check for when not X,Y, and Z Periodic */ 652*47c6ae99SBarry Smith 653*47c6ae99SBarry Smith /* If not X periodic */ 654*47c6ae99SBarry Smith if ((wrap != DA_XPERIODIC) && (wrap != DA_XYPERIODIC) && 655*47c6ae99SBarry Smith (wrap != DA_XZPERIODIC) && (wrap != DA_XYZPERIODIC)) { 656*47c6ae99SBarry Smith if (xs==0) {n0 = n3 = n6 = n9 = n12 = n15 = n18 = n21 = n24 = -2;} 657*47c6ae99SBarry Smith if (xe==M*dof) {n2 = n5 = n8 = n11 = n14 = n17 = n20 = n23 = n26 = -2;} 658*47c6ae99SBarry Smith } 659*47c6ae99SBarry Smith 660*47c6ae99SBarry Smith /* If not Y periodic */ 661*47c6ae99SBarry Smith if ((wrap != DA_YPERIODIC) && (wrap != DA_XYPERIODIC) && 662*47c6ae99SBarry Smith (wrap != DA_YZPERIODIC) && (wrap != DA_XYZPERIODIC)) { 663*47c6ae99SBarry Smith if (ys==0) {n0 = n1 = n2 = n9 = n10 = n11 = n18 = n19 = n20 = -2;} 664*47c6ae99SBarry Smith if (ye==N) {n6 = n7 = n8 = n15 = n16 = n17 = n24 = n25 = n26 = -2;} 665*47c6ae99SBarry Smith } 666*47c6ae99SBarry Smith 667*47c6ae99SBarry Smith /* If not Z periodic */ 668*47c6ae99SBarry Smith if ((wrap != DA_ZPERIODIC) && (wrap != DA_XZPERIODIC) && 669*47c6ae99SBarry Smith (wrap != DA_YZPERIODIC) && (wrap != DA_XYZPERIODIC)) { 670*47c6ae99SBarry Smith if (zs==0) {n0 = n1 = n2 = n3 = n4 = n5 = n6 = n7 = n8 = -2;} 671*47c6ae99SBarry Smith if (ze==P) {n18 = n19 = n20 = n21 = n22 = n23 = n24 = n25 = n26 = -2;} 672*47c6ae99SBarry Smith } 673*47c6ae99SBarry Smith 674*47c6ae99SBarry Smith ierr = PetscMalloc(27*sizeof(PetscInt),&dd->neighbors);CHKERRQ(ierr); 675*47c6ae99SBarry Smith dd->neighbors[0] = n0; 676*47c6ae99SBarry Smith dd->neighbors[1] = n1; 677*47c6ae99SBarry Smith dd->neighbors[2] = n2; 678*47c6ae99SBarry Smith dd->neighbors[3] = n3; 679*47c6ae99SBarry Smith dd->neighbors[4] = n4; 680*47c6ae99SBarry Smith dd->neighbors[5] = n5; 681*47c6ae99SBarry Smith dd->neighbors[6] = n6; 682*47c6ae99SBarry Smith dd->neighbors[7] = n7; 683*47c6ae99SBarry Smith dd->neighbors[8] = n8; 684*47c6ae99SBarry Smith dd->neighbors[9] = n9; 685*47c6ae99SBarry Smith dd->neighbors[10] = n10; 686*47c6ae99SBarry Smith dd->neighbors[11] = n11; 687*47c6ae99SBarry Smith dd->neighbors[12] = n12; 688*47c6ae99SBarry Smith dd->neighbors[13] = rank; 689*47c6ae99SBarry Smith dd->neighbors[14] = n14; 690*47c6ae99SBarry Smith dd->neighbors[15] = n15; 691*47c6ae99SBarry Smith dd->neighbors[16] = n16; 692*47c6ae99SBarry Smith dd->neighbors[17] = n17; 693*47c6ae99SBarry Smith dd->neighbors[18] = n18; 694*47c6ae99SBarry Smith dd->neighbors[19] = n19; 695*47c6ae99SBarry Smith dd->neighbors[20] = n20; 696*47c6ae99SBarry Smith dd->neighbors[21] = n21; 697*47c6ae99SBarry Smith dd->neighbors[22] = n22; 698*47c6ae99SBarry Smith dd->neighbors[23] = n23; 699*47c6ae99SBarry Smith dd->neighbors[24] = n24; 700*47c6ae99SBarry Smith dd->neighbors[25] = n25; 701*47c6ae99SBarry Smith dd->neighbors[26] = n26; 702*47c6ae99SBarry Smith 703*47c6ae99SBarry Smith /* If star stencil then delete the corner neighbors */ 704*47c6ae99SBarry Smith if (stencil_type == DA_STENCIL_STAR) { 705*47c6ae99SBarry Smith /* save information about corner neighbors */ 706*47c6ae99SBarry Smith sn0 = n0; sn1 = n1; sn2 = n2; sn3 = n3; sn5 = n5; sn6 = n6; sn7 = n7; 707*47c6ae99SBarry Smith sn8 = n8; sn9 = n9; sn11 = n11; sn15 = n15; sn17 = n17; sn18 = n18; 708*47c6ae99SBarry Smith sn19 = n19; sn20 = n20; sn21 = n21; sn23 = n23; sn24 = n24; sn25 = n25; 709*47c6ae99SBarry Smith sn26 = n26; 710*47c6ae99SBarry Smith n0 = n1 = n2 = n3 = n5 = n6 = n7 = n8 = n9 = n11 = 711*47c6ae99SBarry Smith n15 = n17 = n18 = n19 = n20 = n21 = n23 = n24 = n25 = n26 = -1; 712*47c6ae99SBarry Smith } 713*47c6ae99SBarry Smith 714*47c6ae99SBarry Smith 715*47c6ae99SBarry Smith ierr = PetscMalloc((Xe-Xs)*(Ye-Ys)*(Ze-Zs)*sizeof(PetscInt),&idx);CHKERRQ(ierr); 716*47c6ae99SBarry Smith ierr = PetscLogObjectMemory(da,(Xe-Xs)*(Ye-Ys)*(Ze-Zs)*sizeof(PetscInt));CHKERRQ(ierr); 717*47c6ae99SBarry Smith 718*47c6ae99SBarry Smith nn = 0; 719*47c6ae99SBarry Smith 720*47c6ae99SBarry Smith /* Bottom Level */ 721*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 722*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 723*47c6ae99SBarry Smith if (n0 >= 0) { /* left below */ 724*47c6ae99SBarry Smith x_t = lx[n0 % m]*dof; 725*47c6ae99SBarry Smith y_t = ly[(n0 % (m*n))/m]; 726*47c6ae99SBarry Smith z_t = lz[n0 / (m*n)]; 727*47c6ae99SBarry Smith s_t = bases[n0] + x_t*y_t*z_t - (s_y-i)*x_t - s_x - (s_z-k-1)*x_t*y_t; 728*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 729*47c6ae99SBarry Smith } 730*47c6ae99SBarry Smith if (n1 >= 0) { /* directly below */ 731*47c6ae99SBarry Smith x_t = x; 732*47c6ae99SBarry Smith y_t = ly[(n1 % (m*n))/m]; 733*47c6ae99SBarry Smith z_t = lz[n1 / (m*n)]; 734*47c6ae99SBarry Smith s_t = bases[n1] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 735*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 736*47c6ae99SBarry Smith } 737*47c6ae99SBarry Smith if (n2 >= 0) { /* right below */ 738*47c6ae99SBarry Smith x_t = lx[n2 % m]*dof; 739*47c6ae99SBarry Smith y_t = ly[(n2 % (m*n))/m]; 740*47c6ae99SBarry Smith z_t = lz[n2 / (m*n)]; 741*47c6ae99SBarry Smith s_t = bases[n2] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 742*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 743*47c6ae99SBarry Smith } 744*47c6ae99SBarry Smith } 745*47c6ae99SBarry Smith 746*47c6ae99SBarry Smith for (i=0; i<y; i++) { 747*47c6ae99SBarry Smith if (n3 >= 0) { /* directly left */ 748*47c6ae99SBarry Smith x_t = lx[n3 % m]*dof; 749*47c6ae99SBarry Smith y_t = y; 750*47c6ae99SBarry Smith z_t = lz[n3 / (m*n)]; 751*47c6ae99SBarry Smith s_t = bases[n3] + (i+1)*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 752*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 753*47c6ae99SBarry Smith } 754*47c6ae99SBarry Smith 755*47c6ae99SBarry Smith if (n4 >= 0) { /* middle */ 756*47c6ae99SBarry Smith x_t = x; 757*47c6ae99SBarry Smith y_t = y; 758*47c6ae99SBarry Smith z_t = lz[n4 / (m*n)]; 759*47c6ae99SBarry Smith s_t = bases[n4] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 760*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 761*47c6ae99SBarry Smith } 762*47c6ae99SBarry Smith 763*47c6ae99SBarry Smith if (n5 >= 0) { /* directly right */ 764*47c6ae99SBarry Smith x_t = lx[n5 % m]*dof; 765*47c6ae99SBarry Smith y_t = y; 766*47c6ae99SBarry Smith z_t = lz[n5 / (m*n)]; 767*47c6ae99SBarry Smith s_t = bases[n5] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 768*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 769*47c6ae99SBarry Smith } 770*47c6ae99SBarry Smith } 771*47c6ae99SBarry Smith 772*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 773*47c6ae99SBarry Smith if (n6 >= 0) { /* left above */ 774*47c6ae99SBarry Smith x_t = lx[n6 % m]*dof; 775*47c6ae99SBarry Smith y_t = ly[(n6 % (m*n))/m]; 776*47c6ae99SBarry Smith z_t = lz[n6 / (m*n)]; 777*47c6ae99SBarry Smith s_t = bases[n6] + i*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 778*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 779*47c6ae99SBarry Smith } 780*47c6ae99SBarry Smith if (n7 >= 0) { /* directly above */ 781*47c6ae99SBarry Smith x_t = x; 782*47c6ae99SBarry Smith y_t = ly[(n7 % (m*n))/m]; 783*47c6ae99SBarry Smith z_t = lz[n7 / (m*n)]; 784*47c6ae99SBarry Smith s_t = bases[n7] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 785*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 786*47c6ae99SBarry Smith } 787*47c6ae99SBarry Smith if (n8 >= 0) { /* right above */ 788*47c6ae99SBarry Smith x_t = lx[n8 % m]*dof; 789*47c6ae99SBarry Smith y_t = ly[(n8 % (m*n))/m]; 790*47c6ae99SBarry Smith z_t = lz[n8 / (m*n)]; 791*47c6ae99SBarry Smith s_t = bases[n8] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 792*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 793*47c6ae99SBarry Smith } 794*47c6ae99SBarry Smith } 795*47c6ae99SBarry Smith } 796*47c6ae99SBarry Smith 797*47c6ae99SBarry Smith /* Middle Level */ 798*47c6ae99SBarry Smith for (k=0; k<z; k++) { 799*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 800*47c6ae99SBarry Smith if (n9 >= 0) { /* left below */ 801*47c6ae99SBarry Smith x_t = lx[n9 % m]*dof; 802*47c6ae99SBarry Smith y_t = ly[(n9 % (m*n))/m]; 803*47c6ae99SBarry Smith /* z_t = z; */ 804*47c6ae99SBarry Smith s_t = bases[n9] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 805*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 806*47c6ae99SBarry Smith } 807*47c6ae99SBarry Smith if (n10 >= 0) { /* directly below */ 808*47c6ae99SBarry Smith x_t = x; 809*47c6ae99SBarry Smith y_t = ly[(n10 % (m*n))/m]; 810*47c6ae99SBarry Smith /* z_t = z; */ 811*47c6ae99SBarry Smith s_t = bases[n10] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 812*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 813*47c6ae99SBarry Smith } 814*47c6ae99SBarry Smith if (n11 >= 0) { /* right below */ 815*47c6ae99SBarry Smith x_t = lx[n11 % m]*dof; 816*47c6ae99SBarry Smith y_t = ly[(n11 % (m*n))/m]; 817*47c6ae99SBarry Smith /* z_t = z; */ 818*47c6ae99SBarry Smith s_t = bases[n11] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 819*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 820*47c6ae99SBarry Smith } 821*47c6ae99SBarry Smith } 822*47c6ae99SBarry Smith 823*47c6ae99SBarry Smith for (i=0; i<y; i++) { 824*47c6ae99SBarry Smith if (n12 >= 0) { /* directly left */ 825*47c6ae99SBarry Smith x_t = lx[n12 % m]*dof; 826*47c6ae99SBarry Smith y_t = y; 827*47c6ae99SBarry Smith /* z_t = z; */ 828*47c6ae99SBarry Smith s_t = bases[n12] + (i+1)*x_t - s_x + k*x_t*y_t; 829*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 830*47c6ae99SBarry Smith } 831*47c6ae99SBarry Smith 832*47c6ae99SBarry Smith /* Interior */ 833*47c6ae99SBarry Smith s_t = bases[rank] + i*x + k*x*y; 834*47c6ae99SBarry Smith for (j=0; j<x; j++) { idx[nn++] = s_t++;} 835*47c6ae99SBarry Smith 836*47c6ae99SBarry Smith if (n14 >= 0) { /* directly right */ 837*47c6ae99SBarry Smith x_t = lx[n14 % m]*dof; 838*47c6ae99SBarry Smith y_t = y; 839*47c6ae99SBarry Smith /* z_t = z; */ 840*47c6ae99SBarry Smith s_t = bases[n14] + i*x_t + k*x_t*y_t; 841*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 842*47c6ae99SBarry Smith } 843*47c6ae99SBarry Smith } 844*47c6ae99SBarry Smith 845*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 846*47c6ae99SBarry Smith if (n15 >= 0) { /* left above */ 847*47c6ae99SBarry Smith x_t = lx[n15 % m]*dof; 848*47c6ae99SBarry Smith y_t = ly[(n15 % (m*n))/m]; 849*47c6ae99SBarry Smith /* z_t = z; */ 850*47c6ae99SBarry Smith s_t = bases[n15] + i*x_t - s_x + k*x_t*y_t; 851*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 852*47c6ae99SBarry Smith } 853*47c6ae99SBarry Smith if (n16 >= 0) { /* directly above */ 854*47c6ae99SBarry Smith x_t = x; 855*47c6ae99SBarry Smith y_t = ly[(n16 % (m*n))/m]; 856*47c6ae99SBarry Smith /* z_t = z; */ 857*47c6ae99SBarry Smith s_t = bases[n16] + (i-1)*x_t + k*x_t*y_t; 858*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 859*47c6ae99SBarry Smith } 860*47c6ae99SBarry Smith if (n17 >= 0) { /* right above */ 861*47c6ae99SBarry Smith x_t = lx[n17 % m]*dof; 862*47c6ae99SBarry Smith y_t = ly[(n17 % (m*n))/m]; 863*47c6ae99SBarry Smith /* z_t = z; */ 864*47c6ae99SBarry Smith s_t = bases[n17] + (i-1)*x_t + k*x_t*y_t; 865*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 866*47c6ae99SBarry Smith } 867*47c6ae99SBarry Smith } 868*47c6ae99SBarry Smith } 869*47c6ae99SBarry Smith 870*47c6ae99SBarry Smith /* Upper Level */ 871*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 872*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 873*47c6ae99SBarry Smith if (n18 >= 0) { /* left below */ 874*47c6ae99SBarry Smith x_t = lx[n18 % m]*dof; 875*47c6ae99SBarry Smith y_t = ly[(n18 % (m*n))/m]; 876*47c6ae99SBarry Smith /* z_t = lz[n18 / (m*n)]; */ 877*47c6ae99SBarry Smith s_t = bases[n18] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 878*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 879*47c6ae99SBarry Smith } 880*47c6ae99SBarry Smith if (n19 >= 0) { /* directly below */ 881*47c6ae99SBarry Smith x_t = x; 882*47c6ae99SBarry Smith y_t = ly[(n19 % (m*n))/m]; 883*47c6ae99SBarry Smith /* z_t = lz[n19 / (m*n)]; */ 884*47c6ae99SBarry Smith s_t = bases[n19] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 885*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 886*47c6ae99SBarry Smith } 887*47c6ae99SBarry Smith if (n20 >= 0) { /* right below */ 888*47c6ae99SBarry Smith x_t = lx[n20 % m]*dof; 889*47c6ae99SBarry Smith y_t = ly[(n20 % (m*n))/m]; 890*47c6ae99SBarry Smith /* z_t = lz[n20 / (m*n)]; */ 891*47c6ae99SBarry Smith s_t = bases[n20] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 892*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 893*47c6ae99SBarry Smith } 894*47c6ae99SBarry Smith } 895*47c6ae99SBarry Smith 896*47c6ae99SBarry Smith for (i=0; i<y; i++) { 897*47c6ae99SBarry Smith if (n21 >= 0) { /* directly left */ 898*47c6ae99SBarry Smith x_t = lx[n21 % m]*dof; 899*47c6ae99SBarry Smith y_t = y; 900*47c6ae99SBarry Smith /* z_t = lz[n21 / (m*n)]; */ 901*47c6ae99SBarry Smith s_t = bases[n21] + (i+1)*x_t - s_x + k*x_t*y_t; 902*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 903*47c6ae99SBarry Smith } 904*47c6ae99SBarry Smith 905*47c6ae99SBarry Smith if (n22 >= 0) { /* middle */ 906*47c6ae99SBarry Smith x_t = x; 907*47c6ae99SBarry Smith y_t = y; 908*47c6ae99SBarry Smith /* z_t = lz[n22 / (m*n)]; */ 909*47c6ae99SBarry Smith s_t = bases[n22] + i*x_t + k*x_t*y_t; 910*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 911*47c6ae99SBarry Smith } 912*47c6ae99SBarry Smith 913*47c6ae99SBarry Smith if (n23 >= 0) { /* directly right */ 914*47c6ae99SBarry Smith x_t = lx[n23 % m]*dof; 915*47c6ae99SBarry Smith y_t = y; 916*47c6ae99SBarry Smith /* z_t = lz[n23 / (m*n)]; */ 917*47c6ae99SBarry Smith s_t = bases[n23] + i*x_t + k*x_t*y_t; 918*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 919*47c6ae99SBarry Smith } 920*47c6ae99SBarry Smith } 921*47c6ae99SBarry Smith 922*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 923*47c6ae99SBarry Smith if (n24 >= 0) { /* left above */ 924*47c6ae99SBarry Smith x_t = lx[n24 % m]*dof; 925*47c6ae99SBarry Smith y_t = ly[(n24 % (m*n))/m]; 926*47c6ae99SBarry Smith /* z_t = lz[n24 / (m*n)]; */ 927*47c6ae99SBarry Smith s_t = bases[n24] + i*x_t - s_x + k*x_t*y_t; 928*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 929*47c6ae99SBarry Smith } 930*47c6ae99SBarry Smith if (n25 >= 0) { /* directly above */ 931*47c6ae99SBarry Smith x_t = x; 932*47c6ae99SBarry Smith y_t = ly[(n25 % (m*n))/m]; 933*47c6ae99SBarry Smith /* z_t = lz[n25 / (m*n)]; */ 934*47c6ae99SBarry Smith s_t = bases[n25] + (i-1)*x_t + k*x_t*y_t; 935*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 936*47c6ae99SBarry Smith } 937*47c6ae99SBarry Smith if (n26 >= 0) { /* right above */ 938*47c6ae99SBarry Smith x_t = lx[n26 % m]*dof; 939*47c6ae99SBarry Smith y_t = ly[(n26 % (m*n))/m]; 940*47c6ae99SBarry Smith /* z_t = lz[n26 / (m*n)]; */ 941*47c6ae99SBarry Smith s_t = bases[n26] + (i-1)*x_t + k*x_t*y_t; 942*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 943*47c6ae99SBarry Smith } 944*47c6ae99SBarry Smith } 945*47c6ae99SBarry Smith } 946*47c6ae99SBarry Smith base = bases[rank]; 947*47c6ae99SBarry Smith { 948*47c6ae99SBarry Smith PetscInt nnn = nn/dof,*iidx; 949*47c6ae99SBarry Smith ierr = PetscMalloc(nnn*sizeof(PetscInt),&iidx);CHKERRQ(ierr); 950*47c6ae99SBarry Smith for (i=0; i<nnn; i++) { 951*47c6ae99SBarry Smith iidx[i] = idx[dof*i]/dof; 952*47c6ae99SBarry Smith } 953*47c6ae99SBarry Smith ierr = ISCreateBlock(comm,dof,nnn,iidx,PETSC_OWN_POINTER,&from);CHKERRQ(ierr); 954*47c6ae99SBarry Smith } 955*47c6ae99SBarry Smith ierr = VecScatterCreate(global,from,local,to,>ol);CHKERRQ(ierr); 956*47c6ae99SBarry Smith ierr = PetscLogObjectParent(da,gtol);CHKERRQ(ierr); 957*47c6ae99SBarry Smith ierr = ISDestroy(from);CHKERRQ(ierr); 958*47c6ae99SBarry Smith ierr = ISDestroy(to);CHKERRQ(ierr); 959*47c6ae99SBarry Smith 960*47c6ae99SBarry Smith dd->m = m; dd->n = n; dd->p = p; 961*47c6ae99SBarry Smith dd->xs = xs; dd->xe = xe; dd->ys = ys; dd->ye = ye; dd->zs = zs; dd->ze = ze; 962*47c6ae99SBarry Smith dd->Xs = Xs; dd->Xe = Xe; dd->Ys = Ys; dd->Ye = Ye; dd->Zs = Zs; dd->Ze = Ze; 963*47c6ae99SBarry Smith 964*47c6ae99SBarry Smith ierr = VecDestroy(local);CHKERRQ(ierr); 965*47c6ae99SBarry Smith ierr = VecDestroy(global);CHKERRQ(ierr); 966*47c6ae99SBarry Smith 967*47c6ae99SBarry Smith if (stencil_type == DA_STENCIL_STAR) { 968*47c6ae99SBarry Smith /* 969*47c6ae99SBarry Smith Recompute the local to global mappings, this time keeping the 970*47c6ae99SBarry Smith information about the cross corner processor numbers. 971*47c6ae99SBarry Smith */ 972*47c6ae99SBarry Smith n0 = sn0; n1 = sn1; n2 = sn2; n3 = sn3; n5 = sn5; n6 = sn6; n7 = sn7; 973*47c6ae99SBarry Smith n8 = sn8; n9 = sn9; n11 = sn11; n15 = sn15; n17 = sn17; n18 = sn18; 974*47c6ae99SBarry Smith n19 = sn19; n20 = sn20; n21 = sn21; n23 = sn23; n24 = sn24; n25 = sn25; 975*47c6ae99SBarry Smith n26 = sn26; 976*47c6ae99SBarry Smith 977*47c6ae99SBarry Smith nn = 0; 978*47c6ae99SBarry Smith 979*47c6ae99SBarry Smith /* Bottom Level */ 980*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 981*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 982*47c6ae99SBarry Smith if (n0 >= 0) { /* left below */ 983*47c6ae99SBarry Smith x_t = lx[n0 % m]*dof; 984*47c6ae99SBarry Smith y_t = ly[(n0 % (m*n))/m]; 985*47c6ae99SBarry Smith z_t = lz[n0 / (m*n)]; 986*47c6ae99SBarry Smith s_t = bases[n0] + x_t*y_t*z_t - (s_y-i)*x_t - s_x - (s_z-k-1)*x_t*y_t; 987*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 988*47c6ae99SBarry Smith } 989*47c6ae99SBarry Smith if (n1 >= 0) { /* directly below */ 990*47c6ae99SBarry Smith x_t = x; 991*47c6ae99SBarry Smith y_t = ly[(n1 % (m*n))/m]; 992*47c6ae99SBarry Smith z_t = lz[n1 / (m*n)]; 993*47c6ae99SBarry Smith s_t = bases[n1] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 994*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 995*47c6ae99SBarry Smith } 996*47c6ae99SBarry Smith if (n2 >= 0) { /* right below */ 997*47c6ae99SBarry Smith x_t = lx[n2 % m]*dof; 998*47c6ae99SBarry Smith y_t = ly[(n2 % (m*n))/m]; 999*47c6ae99SBarry Smith z_t = lz[n2 / (m*n)]; 1000*47c6ae99SBarry Smith s_t = bases[n2] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 1001*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1002*47c6ae99SBarry Smith } 1003*47c6ae99SBarry Smith } 1004*47c6ae99SBarry Smith 1005*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1006*47c6ae99SBarry Smith if (n3 >= 0) { /* directly left */ 1007*47c6ae99SBarry Smith x_t = lx[n3 % m]*dof; 1008*47c6ae99SBarry Smith y_t = y; 1009*47c6ae99SBarry Smith z_t = lz[n3 / (m*n)]; 1010*47c6ae99SBarry Smith s_t = bases[n3] + (i+1)*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1011*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1012*47c6ae99SBarry Smith } 1013*47c6ae99SBarry Smith 1014*47c6ae99SBarry Smith if (n4 >= 0) { /* middle */ 1015*47c6ae99SBarry Smith x_t = x; 1016*47c6ae99SBarry Smith y_t = y; 1017*47c6ae99SBarry Smith z_t = lz[n4 / (m*n)]; 1018*47c6ae99SBarry Smith s_t = bases[n4] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1019*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1020*47c6ae99SBarry Smith } 1021*47c6ae99SBarry Smith 1022*47c6ae99SBarry Smith if (n5 >= 0) { /* directly right */ 1023*47c6ae99SBarry Smith x_t = lx[n5 % m]*dof; 1024*47c6ae99SBarry Smith y_t = y; 1025*47c6ae99SBarry Smith z_t = lz[n5 / (m*n)]; 1026*47c6ae99SBarry Smith s_t = bases[n5] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1027*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1028*47c6ae99SBarry Smith } 1029*47c6ae99SBarry Smith } 1030*47c6ae99SBarry Smith 1031*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1032*47c6ae99SBarry Smith if (n6 >= 0) { /* left above */ 1033*47c6ae99SBarry Smith x_t = lx[n6 % m]*dof; 1034*47c6ae99SBarry Smith y_t = ly[(n6 % (m*n))/m]; 1035*47c6ae99SBarry Smith z_t = lz[n6 / (m*n)]; 1036*47c6ae99SBarry Smith s_t = bases[n6] + i*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1037*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1038*47c6ae99SBarry Smith } 1039*47c6ae99SBarry Smith if (n7 >= 0) { /* directly above */ 1040*47c6ae99SBarry Smith x_t = x; 1041*47c6ae99SBarry Smith y_t = ly[(n7 % (m*n))/m]; 1042*47c6ae99SBarry Smith z_t = lz[n7 / (m*n)]; 1043*47c6ae99SBarry Smith s_t = bases[n7] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1044*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1045*47c6ae99SBarry Smith } 1046*47c6ae99SBarry Smith if (n8 >= 0) { /* right above */ 1047*47c6ae99SBarry Smith x_t = lx[n8 % m]*dof; 1048*47c6ae99SBarry Smith y_t = ly[(n8 % (m*n))/m]; 1049*47c6ae99SBarry Smith z_t = lz[n8 / (m*n)]; 1050*47c6ae99SBarry Smith s_t = bases[n8] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1051*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1052*47c6ae99SBarry Smith } 1053*47c6ae99SBarry Smith } 1054*47c6ae99SBarry Smith } 1055*47c6ae99SBarry Smith 1056*47c6ae99SBarry Smith /* Middle Level */ 1057*47c6ae99SBarry Smith for (k=0; k<z; k++) { 1058*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1059*47c6ae99SBarry Smith if (n9 >= 0) { /* left below */ 1060*47c6ae99SBarry Smith x_t = lx[n9 % m]*dof; 1061*47c6ae99SBarry Smith y_t = ly[(n9 % (m*n))/m]; 1062*47c6ae99SBarry Smith /* z_t = z; */ 1063*47c6ae99SBarry Smith s_t = bases[n9] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 1064*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1065*47c6ae99SBarry Smith } 1066*47c6ae99SBarry Smith if (n10 >= 0) { /* directly below */ 1067*47c6ae99SBarry Smith x_t = x; 1068*47c6ae99SBarry Smith y_t = ly[(n10 % (m*n))/m]; 1069*47c6ae99SBarry Smith /* z_t = z; */ 1070*47c6ae99SBarry Smith s_t = bases[n10] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1071*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1072*47c6ae99SBarry Smith } 1073*47c6ae99SBarry Smith if (n11 >= 0) { /* right below */ 1074*47c6ae99SBarry Smith x_t = lx[n11 % m]*dof; 1075*47c6ae99SBarry Smith y_t = ly[(n11 % (m*n))/m]; 1076*47c6ae99SBarry Smith /* z_t = z; */ 1077*47c6ae99SBarry Smith s_t = bases[n11] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1078*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1079*47c6ae99SBarry Smith } 1080*47c6ae99SBarry Smith } 1081*47c6ae99SBarry Smith 1082*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1083*47c6ae99SBarry Smith if (n12 >= 0) { /* directly left */ 1084*47c6ae99SBarry Smith x_t = lx[n12 % m]*dof; 1085*47c6ae99SBarry Smith y_t = y; 1086*47c6ae99SBarry Smith /* z_t = z; */ 1087*47c6ae99SBarry Smith s_t = bases[n12] + (i+1)*x_t - s_x + k*x_t*y_t; 1088*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1089*47c6ae99SBarry Smith } 1090*47c6ae99SBarry Smith 1091*47c6ae99SBarry Smith /* Interior */ 1092*47c6ae99SBarry Smith s_t = bases[rank] + i*x + k*x*y; 1093*47c6ae99SBarry Smith for (j=0; j<x; j++) { idx[nn++] = s_t++;} 1094*47c6ae99SBarry Smith 1095*47c6ae99SBarry Smith if (n14 >= 0) { /* directly right */ 1096*47c6ae99SBarry Smith x_t = lx[n14 % m]*dof; 1097*47c6ae99SBarry Smith y_t = y; 1098*47c6ae99SBarry Smith /* z_t = z; */ 1099*47c6ae99SBarry Smith s_t = bases[n14] + i*x_t + k*x_t*y_t; 1100*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1101*47c6ae99SBarry Smith } 1102*47c6ae99SBarry Smith } 1103*47c6ae99SBarry Smith 1104*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1105*47c6ae99SBarry Smith if (n15 >= 0) { /* left above */ 1106*47c6ae99SBarry Smith x_t = lx[n15 % m]*dof; 1107*47c6ae99SBarry Smith y_t = ly[(n15 % (m*n))/m]; 1108*47c6ae99SBarry Smith /* z_t = z; */ 1109*47c6ae99SBarry Smith s_t = bases[n15] + i*x_t - s_x + k*x_t*y_t; 1110*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1111*47c6ae99SBarry Smith } 1112*47c6ae99SBarry Smith if (n16 >= 0) { /* directly above */ 1113*47c6ae99SBarry Smith x_t = x; 1114*47c6ae99SBarry Smith y_t = ly[(n16 % (m*n))/m]; 1115*47c6ae99SBarry Smith /* z_t = z; */ 1116*47c6ae99SBarry Smith s_t = bases[n16] + (i-1)*x_t + k*x_t*y_t; 1117*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1118*47c6ae99SBarry Smith } 1119*47c6ae99SBarry Smith if (n17 >= 0) { /* right above */ 1120*47c6ae99SBarry Smith x_t = lx[n17 % m]*dof; 1121*47c6ae99SBarry Smith y_t = ly[(n17 % (m*n))/m]; 1122*47c6ae99SBarry Smith /* z_t = z; */ 1123*47c6ae99SBarry Smith s_t = bases[n17] + (i-1)*x_t + k*x_t*y_t; 1124*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1125*47c6ae99SBarry Smith } 1126*47c6ae99SBarry Smith } 1127*47c6ae99SBarry Smith } 1128*47c6ae99SBarry Smith 1129*47c6ae99SBarry Smith /* Upper Level */ 1130*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 1131*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1132*47c6ae99SBarry Smith if (n18 >= 0) { /* left below */ 1133*47c6ae99SBarry Smith x_t = lx[n18 % m]*dof; 1134*47c6ae99SBarry Smith y_t = ly[(n18 % (m*n))/m]; 1135*47c6ae99SBarry Smith /* z_t = lz[n18 / (m*n)]; */ 1136*47c6ae99SBarry Smith s_t = bases[n18] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 1137*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1138*47c6ae99SBarry Smith } 1139*47c6ae99SBarry Smith if (n19 >= 0) { /* directly below */ 1140*47c6ae99SBarry Smith x_t = x; 1141*47c6ae99SBarry Smith y_t = ly[(n19 % (m*n))/m]; 1142*47c6ae99SBarry Smith /* z_t = lz[n19 / (m*n)]; */ 1143*47c6ae99SBarry Smith s_t = bases[n19] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1144*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1145*47c6ae99SBarry Smith } 1146*47c6ae99SBarry Smith if (n20 >= 0) { /* right below */ 1147*47c6ae99SBarry Smith x_t = lx[n20 % m]*dof; 1148*47c6ae99SBarry Smith y_t = ly[(n20 % (m*n))/m]; 1149*47c6ae99SBarry Smith /* z_t = lz[n20 / (m*n)]; */ 1150*47c6ae99SBarry Smith s_t = bases[n20] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1151*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1152*47c6ae99SBarry Smith } 1153*47c6ae99SBarry Smith } 1154*47c6ae99SBarry Smith 1155*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1156*47c6ae99SBarry Smith if (n21 >= 0) { /* directly left */ 1157*47c6ae99SBarry Smith x_t = lx[n21 % m]*dof; 1158*47c6ae99SBarry Smith y_t = y; 1159*47c6ae99SBarry Smith /* z_t = lz[n21 / (m*n)]; */ 1160*47c6ae99SBarry Smith s_t = bases[n21] + (i+1)*x_t - s_x + k*x_t*y_t; 1161*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1162*47c6ae99SBarry Smith } 1163*47c6ae99SBarry Smith 1164*47c6ae99SBarry Smith if (n22 >= 0) { /* middle */ 1165*47c6ae99SBarry Smith x_t = x; 1166*47c6ae99SBarry Smith y_t = y; 1167*47c6ae99SBarry Smith /* z_t = lz[n22 / (m*n)]; */ 1168*47c6ae99SBarry Smith s_t = bases[n22] + i*x_t + k*x_t*y_t; 1169*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1170*47c6ae99SBarry Smith } 1171*47c6ae99SBarry Smith 1172*47c6ae99SBarry Smith if (n23 >= 0) { /* directly right */ 1173*47c6ae99SBarry Smith x_t = lx[n23 % m]*dof; 1174*47c6ae99SBarry Smith y_t = y; 1175*47c6ae99SBarry Smith /* z_t = lz[n23 / (m*n)]; */ 1176*47c6ae99SBarry Smith s_t = bases[n23] + i*x_t + k*x_t*y_t; 1177*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1178*47c6ae99SBarry Smith } 1179*47c6ae99SBarry Smith } 1180*47c6ae99SBarry Smith 1181*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1182*47c6ae99SBarry Smith if (n24 >= 0) { /* left above */ 1183*47c6ae99SBarry Smith x_t = lx[n24 % m]*dof; 1184*47c6ae99SBarry Smith y_t = ly[(n24 % (m*n))/m]; 1185*47c6ae99SBarry Smith /* z_t = lz[n24 / (m*n)]; */ 1186*47c6ae99SBarry Smith s_t = bases[n24] + i*x_t - s_x + k*x_t*y_t; 1187*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1188*47c6ae99SBarry Smith } 1189*47c6ae99SBarry Smith if (n25 >= 0) { /* directly above */ 1190*47c6ae99SBarry Smith x_t = x; 1191*47c6ae99SBarry Smith y_t = ly[(n25 % (m*n))/m]; 1192*47c6ae99SBarry Smith /* z_t = lz[n25 / (m*n)]; */ 1193*47c6ae99SBarry Smith s_t = bases[n25] + (i-1)*x_t + k*x_t*y_t; 1194*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1195*47c6ae99SBarry Smith } 1196*47c6ae99SBarry Smith if (n26 >= 0) { /* right above */ 1197*47c6ae99SBarry Smith x_t = lx[n26 % m]*dof; 1198*47c6ae99SBarry Smith y_t = ly[(n26 % (m*n))/m]; 1199*47c6ae99SBarry Smith /* z_t = lz[n26 / (m*n)]; */ 1200*47c6ae99SBarry Smith s_t = bases[n26] + (i-1)*x_t + k*x_t*y_t; 1201*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1202*47c6ae99SBarry Smith } 1203*47c6ae99SBarry Smith } 1204*47c6ae99SBarry Smith } 1205*47c6ae99SBarry Smith } 1206*47c6ae99SBarry Smith /* redo idx to include "missing" ghost points */ 1207*47c6ae99SBarry Smith /* Solve for X,Y, and Z Periodic Case First, Then Modify Solution */ 1208*47c6ae99SBarry Smith 1209*47c6ae99SBarry Smith /* Assume Nodes are Internal to the Cube */ 1210*47c6ae99SBarry Smith 1211*47c6ae99SBarry Smith n0 = rank - m*n - m - 1; 1212*47c6ae99SBarry Smith n1 = rank - m*n - m; 1213*47c6ae99SBarry Smith n2 = rank - m*n - m + 1; 1214*47c6ae99SBarry Smith n3 = rank - m*n -1; 1215*47c6ae99SBarry Smith n4 = rank - m*n; 1216*47c6ae99SBarry Smith n5 = rank - m*n + 1; 1217*47c6ae99SBarry Smith n6 = rank - m*n + m - 1; 1218*47c6ae99SBarry Smith n7 = rank - m*n + m; 1219*47c6ae99SBarry Smith n8 = rank - m*n + m + 1; 1220*47c6ae99SBarry Smith 1221*47c6ae99SBarry Smith n9 = rank - m - 1; 1222*47c6ae99SBarry Smith n10 = rank - m; 1223*47c6ae99SBarry Smith n11 = rank - m + 1; 1224*47c6ae99SBarry Smith n12 = rank - 1; 1225*47c6ae99SBarry Smith n14 = rank + 1; 1226*47c6ae99SBarry Smith n15 = rank + m - 1; 1227*47c6ae99SBarry Smith n16 = rank + m; 1228*47c6ae99SBarry Smith n17 = rank + m + 1; 1229*47c6ae99SBarry Smith 1230*47c6ae99SBarry Smith n18 = rank + m*n - m - 1; 1231*47c6ae99SBarry Smith n19 = rank + m*n - m; 1232*47c6ae99SBarry Smith n20 = rank + m*n - m + 1; 1233*47c6ae99SBarry Smith n21 = rank + m*n - 1; 1234*47c6ae99SBarry Smith n22 = rank + m*n; 1235*47c6ae99SBarry Smith n23 = rank + m*n + 1; 1236*47c6ae99SBarry Smith n24 = rank + m*n + m - 1; 1237*47c6ae99SBarry Smith n25 = rank + m*n + m; 1238*47c6ae99SBarry Smith n26 = rank + m*n + m + 1; 1239*47c6ae99SBarry Smith 1240*47c6ae99SBarry Smith /* Assume Pieces are on Faces of Cube */ 1241*47c6ae99SBarry Smith 1242*47c6ae99SBarry Smith if (xs == 0) { /* First assume not corner or edge */ 1243*47c6ae99SBarry Smith n0 = rank -1 - (m*n); 1244*47c6ae99SBarry Smith n3 = rank + m -1 - (m*n); 1245*47c6ae99SBarry Smith n6 = rank + 2*m -1 - (m*n); 1246*47c6ae99SBarry Smith n9 = rank -1; 1247*47c6ae99SBarry Smith n12 = rank + m -1; 1248*47c6ae99SBarry Smith n15 = rank + 2*m -1; 1249*47c6ae99SBarry Smith n18 = rank -1 + (m*n); 1250*47c6ae99SBarry Smith n21 = rank + m -1 + (m*n); 1251*47c6ae99SBarry Smith n24 = rank + 2*m -1 + (m*n); 1252*47c6ae99SBarry Smith } 1253*47c6ae99SBarry Smith 1254*47c6ae99SBarry Smith if (xe == M*dof) { /* First assume not corner or edge */ 1255*47c6ae99SBarry Smith n2 = rank -2*m +1 - (m*n); 1256*47c6ae99SBarry Smith n5 = rank - m +1 - (m*n); 1257*47c6ae99SBarry Smith n8 = rank +1 - (m*n); 1258*47c6ae99SBarry Smith n11 = rank -2*m +1; 1259*47c6ae99SBarry Smith n14 = rank - m +1; 1260*47c6ae99SBarry Smith n17 = rank +1; 1261*47c6ae99SBarry Smith n20 = rank -2*m +1 + (m*n); 1262*47c6ae99SBarry Smith n23 = rank - m +1 + (m*n); 1263*47c6ae99SBarry Smith n26 = rank +1 + (m*n); 1264*47c6ae99SBarry Smith } 1265*47c6ae99SBarry Smith 1266*47c6ae99SBarry Smith if (ys==0) { /* First assume not corner or edge */ 1267*47c6ae99SBarry Smith n0 = rank + m * (n-1) -1 - (m*n); 1268*47c6ae99SBarry Smith n1 = rank + m * (n-1) - (m*n); 1269*47c6ae99SBarry Smith n2 = rank + m * (n-1) +1 - (m*n); 1270*47c6ae99SBarry Smith n9 = rank + m * (n-1) -1; 1271*47c6ae99SBarry Smith n10 = rank + m * (n-1); 1272*47c6ae99SBarry Smith n11 = rank + m * (n-1) +1; 1273*47c6ae99SBarry Smith n18 = rank + m * (n-1) -1 + (m*n); 1274*47c6ae99SBarry Smith n19 = rank + m * (n-1) + (m*n); 1275*47c6ae99SBarry Smith n20 = rank + m * (n-1) +1 + (m*n); 1276*47c6ae99SBarry Smith } 1277*47c6ae99SBarry Smith 1278*47c6ae99SBarry Smith if (ye == N) { /* First assume not corner or edge */ 1279*47c6ae99SBarry Smith n6 = rank - m * (n-1) -1 - (m*n); 1280*47c6ae99SBarry Smith n7 = rank - m * (n-1) - (m*n); 1281*47c6ae99SBarry Smith n8 = rank - m * (n-1) +1 - (m*n); 1282*47c6ae99SBarry Smith n15 = rank - m * (n-1) -1; 1283*47c6ae99SBarry Smith n16 = rank - m * (n-1); 1284*47c6ae99SBarry Smith n17 = rank - m * (n-1) +1; 1285*47c6ae99SBarry Smith n24 = rank - m * (n-1) -1 + (m*n); 1286*47c6ae99SBarry Smith n25 = rank - m * (n-1) + (m*n); 1287*47c6ae99SBarry Smith n26 = rank - m * (n-1) +1 + (m*n); 1288*47c6ae99SBarry Smith } 1289*47c6ae99SBarry Smith 1290*47c6ae99SBarry Smith if (zs == 0) { /* First assume not corner or edge */ 1291*47c6ae99SBarry Smith n0 = size - (m*n) + rank - m - 1; 1292*47c6ae99SBarry Smith n1 = size - (m*n) + rank - m; 1293*47c6ae99SBarry Smith n2 = size - (m*n) + rank - m + 1; 1294*47c6ae99SBarry Smith n3 = size - (m*n) + rank - 1; 1295*47c6ae99SBarry Smith n4 = size - (m*n) + rank; 1296*47c6ae99SBarry Smith n5 = size - (m*n) + rank + 1; 1297*47c6ae99SBarry Smith n6 = size - (m*n) + rank + m - 1; 1298*47c6ae99SBarry Smith n7 = size - (m*n) + rank + m ; 1299*47c6ae99SBarry Smith n8 = size - (m*n) + rank + m + 1; 1300*47c6ae99SBarry Smith } 1301*47c6ae99SBarry Smith 1302*47c6ae99SBarry Smith if (ze == P) { /* First assume not corner or edge */ 1303*47c6ae99SBarry Smith n18 = (m*n) - (size-rank) - m - 1; 1304*47c6ae99SBarry Smith n19 = (m*n) - (size-rank) - m; 1305*47c6ae99SBarry Smith n20 = (m*n) - (size-rank) - m + 1; 1306*47c6ae99SBarry Smith n21 = (m*n) - (size-rank) - 1; 1307*47c6ae99SBarry Smith n22 = (m*n) - (size-rank); 1308*47c6ae99SBarry Smith n23 = (m*n) - (size-rank) + 1; 1309*47c6ae99SBarry Smith n24 = (m*n) - (size-rank) + m - 1; 1310*47c6ae99SBarry Smith n25 = (m*n) - (size-rank) + m; 1311*47c6ae99SBarry Smith n26 = (m*n) - (size-rank) + m + 1; 1312*47c6ae99SBarry Smith } 1313*47c6ae99SBarry Smith 1314*47c6ae99SBarry Smith if ((xs==0) && (zs==0)) { /* Assume an edge, not corner */ 1315*47c6ae99SBarry Smith n0 = size - m*n + rank + m-1 - m; 1316*47c6ae99SBarry Smith n3 = size - m*n + rank + m-1; 1317*47c6ae99SBarry Smith n6 = size - m*n + rank + m-1 + m; 1318*47c6ae99SBarry Smith } 1319*47c6ae99SBarry Smith 1320*47c6ae99SBarry Smith if ((xs==0) && (ze==P)) { /* Assume an edge, not corner */ 1321*47c6ae99SBarry Smith n18 = m*n - (size - rank) + m-1 - m; 1322*47c6ae99SBarry Smith n21 = m*n - (size - rank) + m-1; 1323*47c6ae99SBarry Smith n24 = m*n - (size - rank) + m-1 + m; 1324*47c6ae99SBarry Smith } 1325*47c6ae99SBarry Smith 1326*47c6ae99SBarry Smith if ((xs==0) && (ys==0)) { /* Assume an edge, not corner */ 1327*47c6ae99SBarry Smith n0 = rank + m*n -1 - m*n; 1328*47c6ae99SBarry Smith n9 = rank + m*n -1; 1329*47c6ae99SBarry Smith n18 = rank + m*n -1 + m*n; 1330*47c6ae99SBarry Smith } 1331*47c6ae99SBarry Smith 1332*47c6ae99SBarry Smith if ((xs==0) && (ye==N)) { /* Assume an edge, not corner */ 1333*47c6ae99SBarry Smith n6 = rank - m*(n-1) + m-1 - m*n; 1334*47c6ae99SBarry Smith n15 = rank - m*(n-1) + m-1; 1335*47c6ae99SBarry Smith n24 = rank - m*(n-1) + m-1 + m*n; 1336*47c6ae99SBarry Smith } 1337*47c6ae99SBarry Smith 1338*47c6ae99SBarry Smith if ((xe==M*dof) && (zs==0)) { /* Assume an edge, not corner */ 1339*47c6ae99SBarry Smith n2 = size - (m*n-rank) - (m-1) - m; 1340*47c6ae99SBarry Smith n5 = size - (m*n-rank) - (m-1); 1341*47c6ae99SBarry Smith n8 = size - (m*n-rank) - (m-1) + m; 1342*47c6ae99SBarry Smith } 1343*47c6ae99SBarry Smith 1344*47c6ae99SBarry Smith if ((xe==M*dof) && (ze==P)) { /* Assume an edge, not corner */ 1345*47c6ae99SBarry Smith n20 = m*n - (size - rank) - (m-1) - m; 1346*47c6ae99SBarry Smith n23 = m*n - (size - rank) - (m-1); 1347*47c6ae99SBarry Smith n26 = m*n - (size - rank) - (m-1) + m; 1348*47c6ae99SBarry Smith } 1349*47c6ae99SBarry Smith 1350*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0)) { /* Assume an edge, not corner */ 1351*47c6ae99SBarry Smith n2 = rank + m*(n-1) - (m-1) - m*n; 1352*47c6ae99SBarry Smith n11 = rank + m*(n-1) - (m-1); 1353*47c6ae99SBarry Smith n20 = rank + m*(n-1) - (m-1) + m*n; 1354*47c6ae99SBarry Smith } 1355*47c6ae99SBarry Smith 1356*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N)) { /* Assume an edge, not corner */ 1357*47c6ae99SBarry Smith n8 = rank - m*n +1 - m*n; 1358*47c6ae99SBarry Smith n17 = rank - m*n +1; 1359*47c6ae99SBarry Smith n26 = rank - m*n +1 + m*n; 1360*47c6ae99SBarry Smith } 1361*47c6ae99SBarry Smith 1362*47c6ae99SBarry Smith if ((ys==0) && (zs==0)) { /* Assume an edge, not corner */ 1363*47c6ae99SBarry Smith n0 = size - m + rank -1; 1364*47c6ae99SBarry Smith n1 = size - m + rank; 1365*47c6ae99SBarry Smith n2 = size - m + rank +1; 1366*47c6ae99SBarry Smith } 1367*47c6ae99SBarry Smith 1368*47c6ae99SBarry Smith if ((ys==0) && (ze==P)) { /* Assume an edge, not corner */ 1369*47c6ae99SBarry Smith n18 = m*n - (size - rank) + m*(n-1) -1; 1370*47c6ae99SBarry Smith n19 = m*n - (size - rank) + m*(n-1); 1371*47c6ae99SBarry Smith n20 = m*n - (size - rank) + m*(n-1) +1; 1372*47c6ae99SBarry Smith } 1373*47c6ae99SBarry Smith 1374*47c6ae99SBarry Smith if ((ye==N) && (zs==0)) { /* Assume an edge, not corner */ 1375*47c6ae99SBarry Smith n6 = size - (m*n-rank) - m * (n-1) -1; 1376*47c6ae99SBarry Smith n7 = size - (m*n-rank) - m * (n-1); 1377*47c6ae99SBarry Smith n8 = size - (m*n-rank) - m * (n-1) +1; 1378*47c6ae99SBarry Smith } 1379*47c6ae99SBarry Smith 1380*47c6ae99SBarry Smith if ((ye==N) && (ze==P)) { /* Assume an edge, not corner */ 1381*47c6ae99SBarry Smith n24 = rank - (size-m) -1; 1382*47c6ae99SBarry Smith n25 = rank - (size-m); 1383*47c6ae99SBarry Smith n26 = rank - (size-m) +1; 1384*47c6ae99SBarry Smith } 1385*47c6ae99SBarry Smith 1386*47c6ae99SBarry Smith /* Check for Corners */ 1387*47c6ae99SBarry Smith if ((xs==0) && (ys==0) && (zs==0)) { n0 = size -1;} 1388*47c6ae99SBarry Smith if ((xs==0) && (ys==0) && (ze==P)) { n18 = m*n-1;} 1389*47c6ae99SBarry Smith if ((xs==0) && (ye==N) && (zs==0)) { n6 = (size-1)-m*(n-1);} 1390*47c6ae99SBarry Smith if ((xs==0) && (ye==N) && (ze==P)) { n24 = m-1;} 1391*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0) && (zs==0)) { n2 = size-m;} 1392*47c6ae99SBarry Smith if ((xe==M*dof) && (ys==0) && (ze==P)) { n20 = m*n-m;} 1393*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N) && (zs==0)) { n8 = size-m*n;} 1394*47c6ae99SBarry Smith if ((xe==M*dof) && (ye==N) && (ze==P)) { n26 = 0;} 1395*47c6ae99SBarry Smith 1396*47c6ae99SBarry Smith /* Check for when not X,Y, and Z Periodic */ 1397*47c6ae99SBarry Smith 1398*47c6ae99SBarry Smith /* If not X periodic */ 1399*47c6ae99SBarry Smith if (!DAXPeriodic(wrap)){ 1400*47c6ae99SBarry Smith if (xs==0) {n0 = n3 = n6 = n9 = n12 = n15 = n18 = n21 = n24 = -2;} 1401*47c6ae99SBarry Smith if (xe==M*dof) {n2 = n5 = n8 = n11 = n14 = n17 = n20 = n23 = n26 = -2;} 1402*47c6ae99SBarry Smith } 1403*47c6ae99SBarry Smith 1404*47c6ae99SBarry Smith /* If not Y periodic */ 1405*47c6ae99SBarry Smith if (!DAYPeriodic(wrap)){ 1406*47c6ae99SBarry Smith if (ys==0) {n0 = n1 = n2 = n9 = n10 = n11 = n18 = n19 = n20 = -2;} 1407*47c6ae99SBarry Smith if (ye==N) {n6 = n7 = n8 = n15 = n16 = n17 = n24 = n25 = n26 = -2;} 1408*47c6ae99SBarry Smith } 1409*47c6ae99SBarry Smith 1410*47c6ae99SBarry Smith /* If not Z periodic */ 1411*47c6ae99SBarry Smith if (!DAZPeriodic(wrap)){ 1412*47c6ae99SBarry Smith if (zs==0) {n0 = n1 = n2 = n3 = n4 = n5 = n6 = n7 = n8 = -2;} 1413*47c6ae99SBarry Smith if (ze==P) {n18 = n19 = n20 = n21 = n22 = n23 = n24 = n25 = n26 = -2;} 1414*47c6ae99SBarry Smith } 1415*47c6ae99SBarry Smith 1416*47c6ae99SBarry Smith nn = 0; 1417*47c6ae99SBarry Smith 1418*47c6ae99SBarry Smith /* Bottom Level */ 1419*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 1420*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1421*47c6ae99SBarry Smith if (n0 >= 0) { /* left below */ 1422*47c6ae99SBarry Smith x_t = lx[n0 % m]*dof; 1423*47c6ae99SBarry Smith y_t = ly[(n0 % (m*n))/m]; 1424*47c6ae99SBarry Smith z_t = lz[n0 / (m*n)]; 1425*47c6ae99SBarry Smith s_t = bases[n0] + x_t*y_t*z_t - (s_y-i)*x_t -s_x - (s_z-k-1)*x_t*y_t; 1426*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1427*47c6ae99SBarry Smith } 1428*47c6ae99SBarry Smith if (n1 >= 0) { /* directly below */ 1429*47c6ae99SBarry Smith x_t = x; 1430*47c6ae99SBarry Smith y_t = ly[(n1 % (m*n))/m]; 1431*47c6ae99SBarry Smith z_t = lz[n1 / (m*n)]; 1432*47c6ae99SBarry Smith s_t = bases[n1] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 1433*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1434*47c6ae99SBarry Smith } 1435*47c6ae99SBarry Smith if (n2 >= 0) { /* right below */ 1436*47c6ae99SBarry Smith x_t = lx[n2 % m]*dof; 1437*47c6ae99SBarry Smith y_t = ly[(n2 % (m*n))/m]; 1438*47c6ae99SBarry Smith z_t = lz[n2 / (m*n)]; 1439*47c6ae99SBarry Smith s_t = bases[n2] + x_t*y_t*z_t - (s_y+1-i)*x_t - (s_z-k-1)*x_t*y_t; 1440*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1441*47c6ae99SBarry Smith } 1442*47c6ae99SBarry Smith } 1443*47c6ae99SBarry Smith 1444*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1445*47c6ae99SBarry Smith if (n3 >= 0) { /* directly left */ 1446*47c6ae99SBarry Smith x_t = lx[n3 % m]*dof; 1447*47c6ae99SBarry Smith y_t = y; 1448*47c6ae99SBarry Smith z_t = lz[n3 / (m*n)]; 1449*47c6ae99SBarry Smith s_t = bases[n3] + (i+1)*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1450*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1451*47c6ae99SBarry Smith } 1452*47c6ae99SBarry Smith 1453*47c6ae99SBarry Smith if (n4 >= 0) { /* middle */ 1454*47c6ae99SBarry Smith x_t = x; 1455*47c6ae99SBarry Smith y_t = y; 1456*47c6ae99SBarry Smith z_t = lz[n4 / (m*n)]; 1457*47c6ae99SBarry Smith s_t = bases[n4] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1458*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1459*47c6ae99SBarry Smith } 1460*47c6ae99SBarry Smith 1461*47c6ae99SBarry Smith if (n5 >= 0) { /* directly right */ 1462*47c6ae99SBarry Smith x_t = lx[n5 % m]*dof; 1463*47c6ae99SBarry Smith y_t = y; 1464*47c6ae99SBarry Smith z_t = lz[n5 / (m*n)]; 1465*47c6ae99SBarry Smith s_t = bases[n5] + i*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1466*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1467*47c6ae99SBarry Smith } 1468*47c6ae99SBarry Smith } 1469*47c6ae99SBarry Smith 1470*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1471*47c6ae99SBarry Smith if (n6 >= 0) { /* left above */ 1472*47c6ae99SBarry Smith x_t = lx[n6 % m]*dof; 1473*47c6ae99SBarry Smith y_t = ly[(n6 % (m*n))/m]; 1474*47c6ae99SBarry Smith z_t = lz[n6 / (m*n)]; 1475*47c6ae99SBarry Smith s_t = bases[n6] + i*x_t - s_x + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1476*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1477*47c6ae99SBarry Smith } 1478*47c6ae99SBarry Smith if (n7 >= 0) { /* directly above */ 1479*47c6ae99SBarry Smith x_t = x; 1480*47c6ae99SBarry Smith y_t = ly[(n7 % (m*n))/m]; 1481*47c6ae99SBarry Smith z_t = lz[n7 / (m*n)]; 1482*47c6ae99SBarry Smith s_t = bases[n7] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1483*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1484*47c6ae99SBarry Smith } 1485*47c6ae99SBarry Smith if (n8 >= 0) { /* right above */ 1486*47c6ae99SBarry Smith x_t = lx[n8 % m]*dof; 1487*47c6ae99SBarry Smith y_t = ly[(n8 % (m*n))/m]; 1488*47c6ae99SBarry Smith z_t = lz[n8 / (m*n)]; 1489*47c6ae99SBarry Smith s_t = bases[n8] + (i-1)*x_t + x_t*y_t*z_t - (s_z-k)*x_t*y_t; 1490*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1491*47c6ae99SBarry Smith } 1492*47c6ae99SBarry Smith } 1493*47c6ae99SBarry Smith } 1494*47c6ae99SBarry Smith 1495*47c6ae99SBarry Smith /* Middle Level */ 1496*47c6ae99SBarry Smith for (k=0; k<z; k++) { 1497*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1498*47c6ae99SBarry Smith if (n9 >= 0) { /* left below */ 1499*47c6ae99SBarry Smith x_t = lx[n9 % m]*dof; 1500*47c6ae99SBarry Smith y_t = ly[(n9 % (m*n))/m]; 1501*47c6ae99SBarry Smith /* z_t = z; */ 1502*47c6ae99SBarry Smith s_t = bases[n9] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 1503*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1504*47c6ae99SBarry Smith } 1505*47c6ae99SBarry Smith if (n10 >= 0) { /* directly below */ 1506*47c6ae99SBarry Smith x_t = x; 1507*47c6ae99SBarry Smith y_t = ly[(n10 % (m*n))/m]; 1508*47c6ae99SBarry Smith /* z_t = z; */ 1509*47c6ae99SBarry Smith s_t = bases[n10] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1510*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1511*47c6ae99SBarry Smith } 1512*47c6ae99SBarry Smith if (n11 >= 0) { /* right below */ 1513*47c6ae99SBarry Smith x_t = lx[n11 % m]*dof; 1514*47c6ae99SBarry Smith y_t = ly[(n11 % (m*n))/m]; 1515*47c6ae99SBarry Smith /* z_t = z; */ 1516*47c6ae99SBarry Smith s_t = bases[n11] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1517*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1518*47c6ae99SBarry Smith } 1519*47c6ae99SBarry Smith } 1520*47c6ae99SBarry Smith 1521*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1522*47c6ae99SBarry Smith if (n12 >= 0) { /* directly left */ 1523*47c6ae99SBarry Smith x_t = lx[n12 % m]*dof; 1524*47c6ae99SBarry Smith y_t = y; 1525*47c6ae99SBarry Smith /* z_t = z; */ 1526*47c6ae99SBarry Smith s_t = bases[n12] + (i+1)*x_t - s_x + k*x_t*y_t; 1527*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1528*47c6ae99SBarry Smith } 1529*47c6ae99SBarry Smith 1530*47c6ae99SBarry Smith /* Interior */ 1531*47c6ae99SBarry Smith s_t = bases[rank] + i*x + k*x*y; 1532*47c6ae99SBarry Smith for (j=0; j<x; j++) { idx[nn++] = s_t++;} 1533*47c6ae99SBarry Smith 1534*47c6ae99SBarry Smith if (n14 >= 0) { /* directly right */ 1535*47c6ae99SBarry Smith x_t = lx[n14 % m]*dof; 1536*47c6ae99SBarry Smith y_t = y; 1537*47c6ae99SBarry Smith /* z_t = z; */ 1538*47c6ae99SBarry Smith s_t = bases[n14] + i*x_t + k*x_t*y_t; 1539*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1540*47c6ae99SBarry Smith } 1541*47c6ae99SBarry Smith } 1542*47c6ae99SBarry Smith 1543*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1544*47c6ae99SBarry Smith if (n15 >= 0) { /* left above */ 1545*47c6ae99SBarry Smith x_t = lx[n15 % m]*dof; 1546*47c6ae99SBarry Smith y_t = ly[(n15 % (m*n))/m]; 1547*47c6ae99SBarry Smith /* z_t = z; */ 1548*47c6ae99SBarry Smith s_t = bases[n15] + i*x_t - s_x + k*x_t*y_t; 1549*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1550*47c6ae99SBarry Smith } 1551*47c6ae99SBarry Smith if (n16 >= 0) { /* directly above */ 1552*47c6ae99SBarry Smith x_t = x; 1553*47c6ae99SBarry Smith y_t = ly[(n16 % (m*n))/m]; 1554*47c6ae99SBarry Smith /* z_t = z; */ 1555*47c6ae99SBarry Smith s_t = bases[n16] + (i-1)*x_t + k*x_t*y_t; 1556*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1557*47c6ae99SBarry Smith } 1558*47c6ae99SBarry Smith if (n17 >= 0) { /* right above */ 1559*47c6ae99SBarry Smith x_t = lx[n17 % m]*dof; 1560*47c6ae99SBarry Smith y_t = ly[(n17 % (m*n))/m]; 1561*47c6ae99SBarry Smith /* z_t = z; */ 1562*47c6ae99SBarry Smith s_t = bases[n17] + (i-1)*x_t + k*x_t*y_t; 1563*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1564*47c6ae99SBarry Smith } 1565*47c6ae99SBarry Smith } 1566*47c6ae99SBarry Smith } 1567*47c6ae99SBarry Smith 1568*47c6ae99SBarry Smith /* Upper Level */ 1569*47c6ae99SBarry Smith for (k=0; k<s_z; k++) { 1570*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1571*47c6ae99SBarry Smith if (n18 >= 0) { /* left below */ 1572*47c6ae99SBarry Smith x_t = lx[n18 % m]*dof; 1573*47c6ae99SBarry Smith y_t = ly[(n18 % (m*n))/m]; 1574*47c6ae99SBarry Smith /* z_t = lz[n18 / (m*n)]; */ 1575*47c6ae99SBarry Smith s_t = bases[n18] - (s_y-i)*x_t -s_x + (k+1)*x_t*y_t; 1576*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1577*47c6ae99SBarry Smith } 1578*47c6ae99SBarry Smith if (n19 >= 0) { /* directly below */ 1579*47c6ae99SBarry Smith x_t = x; 1580*47c6ae99SBarry Smith y_t = ly[(n19 % (m*n))/m]; 1581*47c6ae99SBarry Smith /* z_t = lz[n19 / (m*n)]; */ 1582*47c6ae99SBarry Smith s_t = bases[n19] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1583*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1584*47c6ae99SBarry Smith } 1585*47c6ae99SBarry Smith if (n20 >= 0) { /* right belodof */ 1586*47c6ae99SBarry Smith x_t = lx[n20 % m]*dof; 1587*47c6ae99SBarry Smith y_t = ly[(n20 % (m*n))/m]; 1588*47c6ae99SBarry Smith /* z_t = lz[n20 / (m*n)]; */ 1589*47c6ae99SBarry Smith s_t = bases[n20] - (s_y+1-i)*x_t + (k+1)*x_t*y_t; 1590*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1591*47c6ae99SBarry Smith } 1592*47c6ae99SBarry Smith } 1593*47c6ae99SBarry Smith 1594*47c6ae99SBarry Smith for (i=0; i<y; i++) { 1595*47c6ae99SBarry Smith if (n21 >= 0) { /* directly left */ 1596*47c6ae99SBarry Smith x_t = lx[n21 % m]*dof; 1597*47c6ae99SBarry Smith y_t = y; 1598*47c6ae99SBarry Smith /* z_t = lz[n21 / (m*n)]; */ 1599*47c6ae99SBarry Smith s_t = bases[n21] + (i+1)*x_t - s_x + k*x_t*y_t; 1600*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1601*47c6ae99SBarry Smith } 1602*47c6ae99SBarry Smith 1603*47c6ae99SBarry Smith if (n22 >= 0) { /* middle */ 1604*47c6ae99SBarry Smith x_t = x; 1605*47c6ae99SBarry Smith y_t = y; 1606*47c6ae99SBarry Smith /* z_t = lz[n22 / (m*n)]; */ 1607*47c6ae99SBarry Smith s_t = bases[n22] + i*x_t + k*x_t*y_t; 1608*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1609*47c6ae99SBarry Smith } 1610*47c6ae99SBarry Smith 1611*47c6ae99SBarry Smith if (n23 >= 0) { /* directly right */ 1612*47c6ae99SBarry Smith x_t = lx[n23 % m]*dof; 1613*47c6ae99SBarry Smith y_t = y; 1614*47c6ae99SBarry Smith /* z_t = lz[n23 / (m*n)]; */ 1615*47c6ae99SBarry Smith s_t = bases[n23] + i*x_t + k*x_t*y_t; 1616*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1617*47c6ae99SBarry Smith } 1618*47c6ae99SBarry Smith } 1619*47c6ae99SBarry Smith 1620*47c6ae99SBarry Smith for (i=1; i<=s_y; i++) { 1621*47c6ae99SBarry Smith if (n24 >= 0) { /* left above */ 1622*47c6ae99SBarry Smith x_t = lx[n24 % m]*dof; 1623*47c6ae99SBarry Smith y_t = ly[(n24 % (m*n))/m]; 1624*47c6ae99SBarry Smith /* z_t = lz[n24 / (m*n)]; */ 1625*47c6ae99SBarry Smith s_t = bases[n24] + i*x_t - s_x + k*x_t*y_t; 1626*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1627*47c6ae99SBarry Smith } 1628*47c6ae99SBarry Smith if (n25 >= 0) { /* directly above */ 1629*47c6ae99SBarry Smith x_t = x; 1630*47c6ae99SBarry Smith y_t = ly[(n25 % (m*n))/m]; 1631*47c6ae99SBarry Smith /* z_t = lz[n25 / (m*n)]; */ 1632*47c6ae99SBarry Smith s_t = bases[n25] + (i-1)*x_t + k*x_t*y_t; 1633*47c6ae99SBarry Smith for (j=0; j<x_t; j++) { idx[nn++] = s_t++;} 1634*47c6ae99SBarry Smith } 1635*47c6ae99SBarry Smith if (n26 >= 0) { /* right above */ 1636*47c6ae99SBarry Smith x_t = lx[n26 % m]*dof; 1637*47c6ae99SBarry Smith y_t = ly[(n26 % (m*n))/m]; 1638*47c6ae99SBarry Smith /* z_t = lz[n26 / (m*n)]; */ 1639*47c6ae99SBarry Smith s_t = bases[n26] + (i-1)*x_t + k*x_t*y_t; 1640*47c6ae99SBarry Smith for (j=0; j<s_x; j++) { idx[nn++] = s_t++;} 1641*47c6ae99SBarry Smith } 1642*47c6ae99SBarry Smith } 1643*47c6ae99SBarry Smith } 1644*47c6ae99SBarry Smith ierr = PetscFree2(bases,ldims);CHKERRQ(ierr); 1645*47c6ae99SBarry Smith dd->gtol = gtol; 1646*47c6ae99SBarry Smith dd->ltog = ltog; 1647*47c6ae99SBarry Smith dd->idx = idx; 1648*47c6ae99SBarry Smith dd->Nl = nn; 1649*47c6ae99SBarry Smith dd->base = base; 1650*47c6ae99SBarry Smith da->ops->view = DAView_3d; 1651*47c6ae99SBarry Smith 1652*47c6ae99SBarry Smith /* 1653*47c6ae99SBarry Smith Set the local to global ordering in the global vector, this allows use 1654*47c6ae99SBarry Smith of VecSetValuesLocal(). 1655*47c6ae99SBarry Smith */ 1656*47c6ae99SBarry Smith ierr = ISLocalToGlobalMappingCreate(comm,nn,idx,PETSC_OWN_POINTER,&dd->ltogmap);CHKERRQ(ierr); 1657*47c6ae99SBarry Smith ierr = ISLocalToGlobalMappingBlock(dd->ltogmap,dd->w,&dd->ltogmapb);CHKERRQ(ierr); 1658*47c6ae99SBarry Smith ierr = PetscLogObjectParent(da,dd->ltogmap);CHKERRQ(ierr); 1659*47c6ae99SBarry Smith 1660*47c6ae99SBarry Smith dd->ltol = PETSC_NULL; 1661*47c6ae99SBarry Smith dd->ao = PETSC_NULL; 1662*47c6ae99SBarry Smith PetscFunctionReturn(0); 1663*47c6ae99SBarry Smith } 1664*47c6ae99SBarry Smith EXTERN_C_END 1665*47c6ae99SBarry Smith 1666*47c6ae99SBarry Smith #undef __FUNCT__ 1667*47c6ae99SBarry Smith #define __FUNCT__ "DACreate3d" 1668*47c6ae99SBarry Smith /*@C 1669*47c6ae99SBarry Smith DACreate3d - Creates an object that will manage the communication of three-dimensional 1670*47c6ae99SBarry Smith regular array data that is distributed across some processors. 1671*47c6ae99SBarry Smith 1672*47c6ae99SBarry Smith Collective on MPI_Comm 1673*47c6ae99SBarry Smith 1674*47c6ae99SBarry Smith Input Parameters: 1675*47c6ae99SBarry Smith + comm - MPI communicator 1676*47c6ae99SBarry Smith . wrap - type of periodicity the array should have, if any. Use one 1677*47c6ae99SBarry Smith of DA_NONPERIODIC, DA_XPERIODIC, DA_YPERIODIC, DA_ZPERIODIC, DA_XYPERIODIC, DA_XZPERIODIC, DA_YZPERIODIC, DA_XYZPERIODIC, or DA_XYZGHOSTED. 1678*47c6ae99SBarry Smith . stencil_type - Type of stencil (DA_STENCIL_STAR or DA_STENCIL_BOX) 1679*47c6ae99SBarry Smith . M,N,P - global dimension in each direction of the array (use -M, -N, and or -P to indicate that it may be set to a different value 1680*47c6ae99SBarry Smith from the command line with -da_grid_x <M> -da_grid_y <N> -da_grid_z <P>) 1681*47c6ae99SBarry Smith . m,n,p - corresponding number of processors in each dimension 1682*47c6ae99SBarry Smith (or PETSC_DECIDE to have calculated) 1683*47c6ae99SBarry Smith . dof - number of degrees of freedom per node 1684*47c6ae99SBarry Smith . lx, ly, lz - arrays containing the number of nodes in each cell along 1685*47c6ae99SBarry Smith the x, y, and z coordinates, or PETSC_NULL. If non-null, these 1686*47c6ae99SBarry Smith must be of length as m,n,p and the corresponding 1687*47c6ae99SBarry Smith m,n, or p cannot be PETSC_DECIDE. Sum of the lx[] entries must be M, sum of 1688*47c6ae99SBarry Smith the ly[] must N, sum of the lz[] must be P 1689*47c6ae99SBarry Smith - s - stencil width 1690*47c6ae99SBarry Smith 1691*47c6ae99SBarry Smith Output Parameter: 1692*47c6ae99SBarry Smith . da - the resulting distributed array object 1693*47c6ae99SBarry Smith 1694*47c6ae99SBarry Smith Options Database Key: 1695*47c6ae99SBarry Smith + -da_view - Calls DAView() at the conclusion of DACreate3d() 1696*47c6ae99SBarry Smith . -da_grid_x <nx> - number of grid points in x direction, if M < 0 1697*47c6ae99SBarry Smith . -da_grid_y <ny> - number of grid points in y direction, if N < 0 1698*47c6ae99SBarry Smith . -da_grid_z <nz> - number of grid points in z direction, if P < 0 1699*47c6ae99SBarry Smith . -da_processors_x <MX> - number of processors in x direction 1700*47c6ae99SBarry Smith . -da_processors_y <MY> - number of processors in y direction 1701*47c6ae99SBarry Smith . -da_processors_z <MZ> - number of processors in z direction 1702*47c6ae99SBarry Smith . -da_refine_x - refinement ratio in x direction 1703*47c6ae99SBarry Smith . -da_refine_y - refinement ratio in y direction 1704*47c6ae99SBarry Smith - -da_refine_y - refinement ratio in z direction 1705*47c6ae99SBarry Smith 1706*47c6ae99SBarry Smith Level: beginner 1707*47c6ae99SBarry Smith 1708*47c6ae99SBarry Smith Notes: 1709*47c6ae99SBarry Smith The stencil type DA_STENCIL_STAR with width 1 corresponds to the 1710*47c6ae99SBarry Smith standard 7-pt stencil, while DA_STENCIL_BOX with width 1 denotes 1711*47c6ae99SBarry Smith the standard 27-pt stencil. 1712*47c6ae99SBarry Smith 1713*47c6ae99SBarry Smith The array data itself is NOT stored in the DA, it is stored in Vec objects; 1714*47c6ae99SBarry Smith The appropriate vector objects can be obtained with calls to DACreateGlobalVector() 1715*47c6ae99SBarry Smith and DACreateLocalVector() and calls to VecDuplicate() if more are needed. 1716*47c6ae99SBarry Smith 1717*47c6ae99SBarry Smith .keywords: distributed array, create, three-dimensional 1718*47c6ae99SBarry Smith 1719*47c6ae99SBarry Smith .seealso: DADestroy(), DAView(), DACreate1d(), DACreate2d(), DAGlobalToLocalBegin(), DAGetRefinementFactor(), 1720*47c6ae99SBarry Smith DAGlobalToLocalEnd(), DALocalToGlobal(), DALocalToLocalBegin(), DALocalToLocalEnd(), DASetRefinementFactor(), 1721*47c6ae99SBarry Smith DAGetInfo(), DACreateGlobalVector(), DACreateLocalVector(), DACreateNaturalVector(), DALoad(), DAView(), DAGetOwnershipRanges() 1722*47c6ae99SBarry Smith 1723*47c6ae99SBarry Smith @*/ 1724*47c6ae99SBarry Smith PetscErrorCode PETSCDM_DLLEXPORT DACreate3d(MPI_Comm comm,DAPeriodicType wrap,DAStencilType stencil_type,PetscInt M, 1725*47c6ae99SBarry Smith PetscInt N,PetscInt P,PetscInt m,PetscInt n,PetscInt p,PetscInt dof,PetscInt s,const PetscInt lx[],const PetscInt ly[],const PetscInt lz[],DA *da) 1726*47c6ae99SBarry Smith { 1727*47c6ae99SBarry Smith PetscErrorCode ierr; 1728*47c6ae99SBarry Smith 1729*47c6ae99SBarry Smith PetscFunctionBegin; 1730*47c6ae99SBarry Smith ierr = DACreate(comm, da);CHKERRQ(ierr); 1731*47c6ae99SBarry Smith ierr = DASetDim(*da, 3);CHKERRQ(ierr); 1732*47c6ae99SBarry Smith ierr = DASetSizes(*da, M, N, P);CHKERRQ(ierr); 1733*47c6ae99SBarry Smith ierr = DASetNumProcs(*da, m, n, p);CHKERRQ(ierr); 1734*47c6ae99SBarry Smith ierr = DASetPeriodicity(*da, wrap);CHKERRQ(ierr); 1735*47c6ae99SBarry Smith ierr = DASetDof(*da, dof);CHKERRQ(ierr); 1736*47c6ae99SBarry Smith ierr = DASetStencilType(*da, stencil_type);CHKERRQ(ierr); 1737*47c6ae99SBarry Smith ierr = DASetStencilWidth(*da, s);CHKERRQ(ierr); 1738*47c6ae99SBarry Smith ierr = DASetOwnershipRanges(*da, lx, ly, lz);CHKERRQ(ierr); 1739*47c6ae99SBarry Smith /* This violates the behavior for other classes, but right now users expect negative dimensions to be handled this way */ 1740*47c6ae99SBarry Smith ierr = DASetFromOptions(*da);CHKERRQ(ierr); 1741*47c6ae99SBarry Smith ierr = DASetType(*da, DA3D);CHKERRQ(ierr); 1742*47c6ae99SBarry Smith PetscFunctionReturn(0); 1743*47c6ae99SBarry Smith } 1744