Actual source code: petscvu.c

  1: /* $Id: petscvu.c,v 1.0 2001/04/10 19:34:05 knepley Exp $ */

 3:  #include src/sys/src/viewer/viewerimpl.h
  4: #include <stdarg.h>
  5: #include "petscfix.h"

  7: #define QUEUESTRINGSIZE 1024

  9: typedef struct _PrintfQueue *PrintfQueue;
 10: struct _PrintfQueue {
 11:   char        string[QUEUESTRINGSIZE];
 12:   PrintfQueue next;
 13: };

 15: typedef struct {
 16:   FILE         *fd;
 17:   PetscFileMode mode;     /* The mode in which to open the file */
 18:   char         *filename;
 19:   PetscTruth    vecSeen;  /* The flag indicating whether any vector has been viewed so far */
 20:   PrintfQueue   queue, queueBase;
 21:   int           queueLength;
 22: } PetscViewer_VU;

 24: int PetscViewerDestroy_VU(PetscViewer viewer)
 25: {
 26:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;
 27:   int             ierr;

 30:   if (vu->vecSeen == PETSC_TRUE) {
 31:     PetscViewerVUPrintDeferred(viewer, "};nn");
 32:   }
 33:   PetscViewerVUFlushDeferred(viewer);
 34:   PetscFClose(viewer->comm, vu->fd);
 35:   PetscStrfree(vu->filename);
 36:   PetscFree(vu);
 37:   return(0);
 38: }

 40: int PetscViewerFlush_VU(PetscViewer viewer)
 41: {
 42:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;
 43:   int             rank;
 44:   int             ierr;

 47:   MPI_Comm_rank(viewer->comm, &rank);
 48:   if (rank == 0) fflush(vu->fd);
 49:   return(0);
 50: }

 52: EXTERN_C_BEGIN
 53: int PetscViewerGetFilename_VU(PetscViewer viewer, char **name)
 54: {
 55:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;

 58:   *name = vu->filename;
 59:   return(0);
 60: }
 61: EXTERN_C_END

 63: EXTERN_C_BEGIN
 64: int PetscViewerSetFilename_VU(PetscViewer viewer, const char name[])
 65: {
 66:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;
 67:   char            fname[256];
 68:   int             rank;
 69:   int             ierr;

 72:   if (name == PETSC_NULL) return(0);
 73:   MPI_Comm_rank(viewer->comm, &rank);
 74:   if (rank != 0) return(0);
 75:   PetscStrallocpy(name, &vu->filename);
 76:   PetscFixFilename(name, fname);
 77:   switch(vu->mode) {
 78:   case FILE_MODE_READ:
 79:     vu->fd = fopen(fname, "r");
 80:     break;
 81:   case FILE_MODE_WRITE:
 82:     vu->fd = fopen(fname, "w");
 83:     break;
 84:   case FILE_MODE_APPEND:
 85:     vu->fd = fopen(fname, "a");
 86:     break;
 87:   case FILE_MODE_UPDATE:
 88:     vu->fd = fopen(fname, "r+");
 89:     if (vu->fd == PETSC_NULL) {
 90:       vu->fd = fopen(fname, "w+");
 91:     }
 92:     break;
 93:   case FILE_MODE_APPEND_UPDATE:
 94:     /* I really want a file which is opened at the end for updating,
 95:        not a+, which opens at the beginning, but makes writes at the end.
 96:     */
 97:     vu->fd = fopen(fname, "r+");
 98:     if (vu->fd == PETSC_NULL) {
 99:       vu->fd = fopen(fname, "w+");
100:     } else {
101:       fseek(vu->fd, 0, SEEK_END);
102:     }
103:     break;
104:   default:
105:     SETERRQ1(PETSC_ERR_ARG_WRONG, "Invalid file mode %d", vu->mode);
106:   }

108:   if (!vu->fd) SETERRQ1(PETSC_ERR_FILE_OPEN, "Cannot open PetscViewer file: %s", fname);
109: #if defined(PETSC_USE_LOG)
110:   PetscLogObjectState((PetscObject) viewer, "File: %s", name);
111: #endif

113:   return(0);
114: }
115: EXTERN_C_END

117: EXTERN_C_BEGIN
118: int PetscViewerCreate_VU(PetscViewer viewer)
119: {
120:   PetscViewer_VU *vu;
121:   int             ierr;

124:   ierr         = PetscNew(PetscViewer_VU, &vu);
125:   viewer->data = (void*) vu;

127:   viewer->ops->destroy          = PetscViewerDestroy_VU;
128:   viewer->ops->flush            = PetscViewerFlush_VU;
129:   viewer->ops->getsingleton     = PETSC_NULL;
130:   viewer->ops->restoresingleton = PETSC_NULL;
131:   viewer->format                = PETSC_VIEWER_ASCII_DEFAULT;
132:   viewer->iformat               = 0;

134:   vu->fd          = PETSC_NULL;
135:   vu->mode        = FILE_MODE_WRITE;
136:   vu->filename    = PETSC_NULL;
137:   vu->vecSeen     = PETSC_FALSE;
138:   vu->queue       = PETSC_NULL;
139:   vu->queueBase   = PETSC_NULL;
140:   vu->queueLength = 0;

142:   PetscObjectComposeFunctionDynamic((PetscObject) viewer,"PetscViewerSetFilename_C", "PetscViewerSetFilename_VU",
143:                                            PetscViewerSetFilename_VU);
144:   PetscObjectComposeFunctionDynamic((PetscObject) viewer,"PetscViewerGetFilename_C", "PetscViewerGetFilename_VU",
145:                                            PetscViewerGetFilename_VU);

147:   return(0);
148: }
149: EXTERN_C_END

151: /*@C
152:   PetscViewerVUGetPointer - Extracts the file pointer from a VU PetscViewer.

154:   Not Collective

156:   Input Parameter:
157: . viewer - The PetscViewer

159:   Output Parameter:
160: . fd     - The file pointer

162:   Level: intermediate

164:   Concepts: PetscViewer^file pointer
165:   Concepts: file pointer^getting from PetscViewer

167: .seealso: PetscViewerASCIIGetPointer()
168: @*/
169: int PetscViewerVUGetPointer(PetscViewer viewer, FILE **fd)
170: {
171:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;

175:   *fd = vu->fd;
176:   return(0);
177: }

179: /*@C
180:   PetscViewerVUSetMode - Sets the mode in which to open the file.

182:   Not Collective

184:   Input Parameters:
185: + viewer - The PetscViewer
186: - mode   - The file mode

188:   Level: intermediate

190: .keywords: Viewer, file, get, pointer
191: .seealso: PetscViewerASCIISetMode()
192: @*/
193: int PetscViewerVUSetMode(PetscViewer viewer, PetscFileMode mode)
194: {
195:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;

198:   vu->mode = mode;
199:   return(0);
200: }

202: /*@C
203:   PetscViewerVUSetVecSeen - Sets the flag which indicates whether we have viewed
204:   a vector. This is usually called internally rather than by a user.

206:   Not Collective

208:   Input Parameters:
209: + viewer  - The PetscViewer
210: - vecSeen - The flag which indicates whether we have viewed a vector

212:   Level: advanced

214: .keywords: Viewer, Vec
215: .seealso: PetscViewerVUGetVecSeen()
216: @*/
217: int PetscViewerVUSetVecSeen(PetscViewer viewer, PetscTruth vecSeen)
218: {
219:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;

222:   vu->vecSeen = vecSeen;
223:   return(0);
224: }

226: /*@C
227:   PetscViewerVUGetVecSeen - Gets the flag which indicates whether we have viewed
228:   a vector. This is usually called internally rather than by a user.

230:   Not Collective

232:   Input Parameter:
233: . viewer  - The PetscViewer

235:   Output Parameter:
236: . vecSeen - The flag which indicates whether we have viewed a vector

238:   Level: advanced

240: .keywords: Viewer, Vec
241: .seealso: PetscViewerVUGetVecSeen()
242: @*/
243: int PetscViewerVUGetVecSeen(PetscViewer viewer, PetscTruth *vecSeen)
244: {
245:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;

249:   *vecSeen = vu->vecSeen;
250:   return(0);
251: }

253: /*@C
254:   PetscViewerVUPrintDeferred - Prints to the deferred write cache instead of the file.

256:   Not Collective

258:   Input Parameters:
259: + viewer - The PetscViewer
260: - format - The format string

262:   Level: intermediate

264: .keywords: Viewer, print, deferred
265: .seealso: PetscViewerVUFlushDeferred()
266: @*/
267: int PetscViewerVUPrintDeferred(PetscViewer viewer, const char format[], ...)
268: {
269:   PetscViewer_VU *vu = (PetscViewer_VU *) viewer->data;
270:   va_list         Argp;
271:   PrintfQueue     next;
272:   int             len;
273:   int             ierr;

276:   PetscNew(struct _PrintfQueue, &next);
277:   if (vu->queue != PETSC_NULL) {
278:     vu->queue->next = next;
279:     vu->queue       = next;
280:     vu->queue->next = PETSC_NULL;
281:   } else {
282:     vu->queueBase   = vu->queue = next;
283:   }
284:   vu->queueLength++;

286:   va_start(Argp, format);
287: #if defined(PETSC_HAVE_VPRINTF_CHAR)
288:   vsprintf(next->string, format, (char *) Argp);
289: #else
290:   vsprintf(next->string, format, Argp);
291: #endif
292:   va_end(Argp);
293:   PetscStrlen(next->string, &len);
294:   if (len > QUEUESTRINGSIZE) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE, "Formatted string longer than %d bytes", QUEUESTRINGSIZE);
295:   return(0);
296: }

298: /*@C
299:   PetscViewerVUFlushDeferred - Flushes the deferred write cache to the file.

301:   Not Collective

303:   Input Parameter:
304: + viewer - The PetscViewer

306:   Level: intermediate

308: .keywords: Viewer, flush, deferred
309: .seealso: PetscViewerVUPrintDeferred()
310: @*/
311: int PetscViewerVUFlushDeferred(PetscViewer viewer)
312: {
313:   PetscViewer_VU *vu   = (PetscViewer_VU *) viewer->data;
314:   PrintfQueue     next = vu->queueBase;
315:   PrintfQueue     previous;
316:   int             i;
317:   int             ierr;

320:   for(i = 0; i < vu->queueLength; i++) {
321:     PetscFPrintf(viewer->comm, vu->fd, "%s", next->string);
322:     previous = next;
323:     next     = next->next;
324:     ierr     = PetscFree(previous);
325:   }
326:   vu->queue       = PETSC_NULL;
327:   vu->queueLength = 0;
328:   return(0);
329: }