Actual source code: daview.c

  1: #define PETSCDM_DLL

  3: /*
  4:   Code for manipulating distributed regular arrays in parallel.
  5: */

 7:  #include src/dm/da/daimpl.h
  8: #if defined(PETSC_HAVE_PNETCDF)
 10: #include "pnetcdf.h"
 12: #endif


 15: #if defined(PETSC_HAVE_MATLAB)
 16: #include "mat.h"   /* Matlab include file */

 20: PetscErrorCode DAView_Matlab(DA da,PetscViewer viewer)
 21: {
 23:   PetscMPIInt    rank;
 24:   PetscInt       dim,m,n,p,dof,swidth;
 25:   DAStencilType  stencil;
 26:   DAPeriodicType periodic;
 27:   mxArray        *mx;
 28:   const char     *fnames[] = {"dimension","m","n","p","dof","stencil_width","periodicity","stencil_type"};

 31:   MPI_Comm_rank(da->comm,&rank);
 32:   if (!rank) {
 33:     DAGetInfo(da,&dim,&m,&n,&p,0,0,0,&dof,&swidth,&periodic,&stencil);
 34:     mx = mxCreateStructMatrix(1,1,8,(const char **)fnames);
 35:     if (!mx) SETERRQ(PETSC_ERR_LIB,"Unable to generate Matlab struct array to hold DA informations");
 36:     mxSetFieldByNumber(mx,0,0,mxCreateDoubleScalar((double)dim));
 37:     mxSetFieldByNumber(mx,0,1,mxCreateDoubleScalar((double)m));
 38:     mxSetFieldByNumber(mx,0,2,mxCreateDoubleScalar((double)n));
 39:     mxSetFieldByNumber(mx,0,3,mxCreateDoubleScalar((double)p));
 40:     mxSetFieldByNumber(mx,0,4,mxCreateDoubleScalar((double)dof));
 41:     mxSetFieldByNumber(mx,0,5,mxCreateDoubleScalar((double)swidth));
 42:     mxSetFieldByNumber(mx,0,6,mxCreateDoubleScalar((double)periodic));
 43:     mxSetFieldByNumber(mx,0,7,mxCreateDoubleScalar((double)stencil));
 44:     PetscObjectName((PetscObject)da);
 45:     PetscViewerMatlabPutVariable(viewer,da->name,mx);
 46:   }
 47:   return(0);
 48: }
 49: #endif

 53: PetscErrorCode DAView_Binary(DA da,PetscViewer viewer)
 54: {
 56:   PetscMPIInt    rank;
 57:   PetscInt       i,dim,m,n,p,dof,swidth,M,N,P;
 58:   size_t         j,len;
 59:   DAStencilType  stencil;
 60:   DAPeriodicType periodic;
 61:   MPI_Comm       comm;

 64:   PetscObjectGetComm((PetscObject)da,&comm);

 66:   DAGetInfo(da,&dim,&m,&n,&p,&M,&N,&P,&dof,&swidth,&periodic,&stencil);
 67:   MPI_Comm_rank(comm,&rank);
 68:   if (!rank) {
 69:     FILE *file;

 71:     PetscViewerBinaryGetInfoPointer(viewer,&file);
 72:     if (file) {
 73:       char fieldname[PETSC_MAX_PATH_LEN];

 75:       PetscFPrintf(PETSC_COMM_SELF,file,"-daload_info %D,%D,%D,%D,%D,%D,%D,%D\n",dim,m,n,p,dof,swidth,stencil,periodic);
 76:       for (i=0; i<dof; i++) {
 77:         if (da->fieldname[i]) {
 78:           PetscStrncpy(fieldname,da->fieldname[i],PETSC_MAX_PATH_LEN);
 79:           PetscStrlen(fieldname,&len);
 80:           len  = PetscMin(PETSC_MAX_PATH_LEN,len);
 81:           for (j=0; j<len; j++) {
 82:             if (fieldname[j] == ' ') fieldname[j] = '_';
 83:           }
 84:           PetscFPrintf(PETSC_COMM_SELF,file,"-daload_fieldname_%D %s\n",i,fieldname);
 85:         }
 86:       }
 87:       if (da->coordinates) { /* save the DA's coordinates */
 88:         PetscFPrintf(PETSC_COMM_SELF,file,"-daload_coordinates\n");
 89:       }
 90:     }
 91:   }

 93:   /* save the coordinates if they exist to disk (in the natural ordering) */
 94:   if (da->coordinates) {
 95:     DA       dac;
 96:     PetscInt *lx,*ly,*lz;
 97:     Vec      natural;

 99:     /* create the appropriate DA to map to natural ordering */
100:     DAGetOwnershipRange(da,&lx,&ly,&lz);
101:     if (dim == 1) {
102:       DACreate1d(comm,DA_NONPERIODIC,m,dim,0,lx,&dac);
103:     } else if (dim == 2) {
104:       DACreate2d(comm,DA_NONPERIODIC,DA_STENCIL_BOX,m,n,M,N,dim,0,lx,ly,&dac);
105:     } else if (dim == 3) {
106:       DACreate3d(comm,DA_NONPERIODIC,DA_STENCIL_BOX,m,n,p,M,N,P,dim,0,lx,ly,lz,&dac);
107:     } else {
108:       SETERRQ1(PETSC_ERR_ARG_CORRUPT,"Dimension is not 1 2 or 3: %D\n",dim);
109:     }
110:     DACreateNaturalVector(dac,&natural);
111:     PetscObjectSetOptionsPrefix((PetscObject)natural,"coor_");
112:     DAGlobalToNaturalBegin(dac,da->coordinates,INSERT_VALUES,natural);
113:     DAGlobalToNaturalEnd(dac,da->coordinates,INSERT_VALUES,natural);
114:     VecView(natural,viewer);
115:     VecDestroy(natural);
116:     DADestroy(dac);
117:   }

119:   return(0);
120: }

124: /*@C
125:    DAView - Visualizes a distributed array object.

127:    Collective on DA

129:    Input Parameters:
130: +  da - the distributed array
131: -  ptr - an optional visualization context

133:    Notes:
134:    The available visualization contexts include
135: +     PETSC_VIEWER_STDOUT_SELF - standard output (default)
136: .     PETSC_VIEWER_STDOUT_WORLD - synchronized standard
137:          output where only the first processor opens
138:          the file.  All other processors send their 
139:          data to the first processor to print. 
140: -     PETSC_VIEWER_DRAW_WORLD - to default window

142:    The user can open alternative visualization contexts with
143: +    PetscViewerASCIIOpen() - Outputs vector to a specified file
144: -    PetscViewerDrawOpen() - Outputs vector to an X window display

146:    Default Output Format:
147:   (for 3d arrays)
148: .vb
149:    Processor [proc] M  N  P  m  n  p  w  s
150:    X range: xs xe, Y range: ys, ye, Z range: zs, ze

152:    where
153:       M,N,P - global dimension in each direction of the array
154:       m,n,p - corresponding number of procs in each dimension 
155:       w - number of degrees of freedom per node
156:       s - stencil width
157:       xs, xe - internal local starting/ending grid points
158:                in x-direction, (augmented to handle multiple 
159:                degrees of freedom per node)
160:       ys, ye - local starting/ending grid points in y-direction
161:       zs, ze - local starting/ending grid points in z-direction
162: .ve

164:    Options Database Key:
165: .  -da_view - Calls DAView() at the conclusion of DACreate1d(),
166:               DACreate2d(), and DACreate3d()

168:    Level: beginner

170:    Notes:
171:    Use DAGetCorners() and DAGetGhostCorners() to get the starting
172:    and ending grid points (ghost points) in each direction.

174:    When drawing the DA grid it only draws the logical grid and does not
175:    respect the grid coordinates set with DASetCoordinates()

177: .keywords: distributed array, view, visualize

179: .seealso: PetscViewerASCIIOpen(), PetscViewerDrawOpen(), DAGetInfo(), DAGetCorners(),
180:           DAGetGhostCorners()
181: @*/
182: PetscErrorCode  DAView(DA da,PetscViewer viewer)
183: {
185:   PetscInt i,dof = da->w;
186:   PetscTruth iascii,fieldsnamed = PETSC_FALSE,isbinary;
187: #if defined(PETSC_HAVE_MATLAB)
188:   PetscTruth ismatlab;
189: #endif

193:   if (!viewer) viewer = PETSC_VIEWER_STDOUT_(da->comm);

196:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);
197:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_BINARY,&isbinary);
198: #if defined(PETSC_HAVE_MATLAB)
199:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_MATLAB,&ismatlab);
200: #endif
201:   if (iascii) {
202:     for (i=0; i<dof; i++) {
203:       if (da->fieldname[i]) {
204:         fieldsnamed = PETSC_TRUE;
205:         break;
206:       }
207:     }
208:     if (fieldsnamed) {
209:       PetscViewerASCIIPrintf(viewer,"FieldNames: ");
210:       for (i=0; i<dof; i++) {
211:         if (da->fieldname[i]) {
212:           PetscViewerASCIIPrintf(viewer,"%s ",da->fieldname[i]);
213:         } else {
214:           PetscViewerASCIIPrintf(viewer,"(not named) ");
215:         }
216:       }
217:       PetscViewerASCIIPrintf(viewer,"\n");
218:     }
219:   }
220:   if (isbinary){
221:     DAView_Binary(da,viewer);
222: #if defined(PETSC_HAVE_MATLAB)
223:   } else if (ismatlab) {
224:     DAView_Matlab(da,viewer);
225: #endif
226:   } else {
227:     (*da->ops->view)(da,viewer);
228:   }
229:   return(0);
230: }

234: /*@C
235:    DAGetInfo - Gets information about a given distributed array.

237:    Not Collective

239:    Input Parameter:
240: .  da - the distributed array

242:    Output Parameters:
243: +  dim     - dimension of the distributed array (1, 2, or 3)
244: .  M, N, P - global dimension in each direction of the array
245: .  m, n, p - corresponding number of procs in each dimension
246: .  dof     - number of degrees of freedom per node
247: .  s       - stencil width
248: .  wrap    - type of periodicity, one of DA_NONPERIODIC, DA_XPERIODIC, DA_YPERIODIC, 
249:              DA_XYPERIODIC, DA_XYZPERIODIC, DA_XZPERIODIC, DA_YZPERIODIC,DA_ZPERIODIC
250: -  st      - stencil type, either DA_STENCIL_STAR or DA_STENCIL_BOX

252:    Level: beginner
253:   
254:    Note:
255:    Use PETSC_NULL (PETSC_NULL_INTEGER in Fortran) in place of any output parameter that is not of interest.

257: .keywords: distributed array, get, information

259: .seealso: DAView(), DAGetCorners(), DAGetLocalInfo()
260: @*/
261: PetscErrorCode  DAGetInfo(DA da,PetscInt *dim,PetscInt *M,PetscInt *N,PetscInt *P,PetscInt *m,PetscInt *n,PetscInt *p,PetscInt *dof,PetscInt *s,DAPeriodicType *wrap,DAStencilType *st)
262: {
265:   if (dim)  *dim  = da->dim;
266:   if (M)    *M    = da->M;
267:   if (N)    *N    = da->N;
268:   if (P)    *P    = da->P;
269:   if (m)    *m    = da->m;
270:   if (n)    *n    = da->n;
271:   if (p)    *p    = da->p;
272:   if (dof)  *dof  = da->w;
273:   if (s)    *s    = da->s;
274:   if (wrap) *wrap = da->wrap;
275:   if (st)   *st   = da->stencil_type;
276:   return(0);
277: }

281: /*@C
282:    DAGetLocalInfo - Gets information about a given distributed array and this processors location in it

284:    Not Collective

286:    Input Parameter:
287: .  da - the distributed array

289:    Output Parameters:
290: .  dainfo - structure containing the information

292:    Level: beginner
293:   
294: .keywords: distributed array, get, information

296: .seealso: DAGetInfo(), DAGetCorners()
297: @*/
298: PetscErrorCode  DAGetLocalInfo(DA da,DALocalInfo *info)
299: {
300:   PetscInt w;

305:   info->da   = da;
306:   info->dim  = da->dim;
307:   info->mx   = da->M;
308:   info->my   = da->N;
309:   info->mz   = da->P;
310:   info->dof  = da->w;
311:   info->sw   = da->s;
312:   info->pt   = da->wrap;
313:   info->st   = da->stencil_type;

315:   /* since the xs, xe ... have all been multiplied by the number of degrees 
316:      of freedom per cell, w = da->w, we divide that out before returning.*/
317:   w = da->w;
318:   info->xs = da->xs/w;
319:   info->xm = (da->xe - da->xs)/w;
320:   /* the y and z have NOT been multiplied by w */
321:   info->ys = da->ys;
322:   info->ym = (da->ye - da->ys);
323:   info->zs = da->zs;
324:   info->zm = (da->ze - da->zs);

326:   info->gxs = da->Xs/w;
327:   info->gxm = (da->Xe - da->Xs)/w;
328:   /* the y and z have NOT been multiplied by w */
329:   info->gys = da->Ys;
330:   info->gym = (da->Ye - da->Ys);
331:   info->gzs = da->Zs;
332:   info->gzm = (da->Ze - da->Zs);
333:   return(0);
334: }