Actual source code: filev.c

  1: /* $Id: filev.c,v 1.118 2001/04/10 19:34:05 bsmith Exp $ */

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

  7: typedef struct {
  8:   FILE          *fd;
  9:   PetscFileMode mode;           /* The mode in which to open the file */
 10:   int           tab;            /* how many times text is tabbed in from left */
 11:   int           tab_store;      /* store tabs value while tabs are turned off */
 12:   PetscViewer   bviewer;        /* if PetscViewer is a singleton, this points to mother */
 13:   PetscViewer   sviewer;        /* if PetscViewer has a singleton, this points to singleton */
 14:   char          *filename;
 15:   PetscTruth    storecompressed;
 16: } PetscViewer_ASCII;

 18: /* ----------------------------------------------------------------------*/
 19: int PetscViewerDestroy_ASCII(PetscViewer viewer)
 20: {
 21:   int               rank,ierr;
 22:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;

 25:   if (vascii->sviewer) {
 26:     SETERRQ(1,"ASCII PetscViewer destroyed before restoring singleton PetscViewer");
 27:   }
 28:   MPI_Comm_rank(viewer->comm,&rank);
 29:   if (!rank && vascii->fd != stderr && vascii->fd != stdout) {
 30:     fclose(vascii->fd);
 31:     if (vascii->storecompressed) {
 32:       char par[1024],buf[1024];
 33:       FILE *fp;
 34:       PetscStrcpy(par,"gzip ");
 35:       PetscStrcat(par,vascii->filename);
 36:       PetscPOpen(PETSC_COMM_SELF,PETSC_NULL,par,"r",&fp);
 37:       if (fgets(buf,1024,fp)) {
 38:         SETERRQ2(1,"Error from compression command %sn%s",par,buf);
 39:       }
 40:     }
 41:   }
 42:   PetscStrfree(vascii->filename);
 43:   PetscFree(vascii);
 44:   return(0);
 45: }

 47: int PetscViewerDestroy_ASCII_Singleton(PetscViewer viewer)
 48: {
 49:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;
 50:   int               ierr;
 52:   PetscViewerRestoreSingleton(vascii->bviewer,&viewer);
 53:   return(0);
 54: }

 56: int PetscViewerFlush_ASCII_Singleton_0(PetscViewer viewer)
 57: {
 58:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;

 61:   fflush(vascii->fd);
 62:   return(0);
 63: }

 65: int PetscViewerFlush_ASCII(PetscViewer viewer)
 66: {
 67:   int               rank,ierr;
 68:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;

 71:   MPI_Comm_rank(viewer->comm,&rank);
 72:   if (!rank) {
 73:     fflush(vascii->fd);
 74:   }

 76:   /*
 77:      Also flush anything printed with PetscViewerASCIISynchronizedPrintf()
 78:   */
 79:   PetscSynchronizedFlush(viewer->comm);
 80:   return(0);
 81: }

 83: /*@C
 84:     PetscViewerASCIIGetPointer - Extracts the file pointer from an ASCII PetscViewer.

 86:     Not Collective

 88: +   viewer - PetscViewer context, obtained from PetscViewerASCIIOpen()
 89: -   fd - file pointer

 91:     Level: intermediate

 93:     Fortran Note:
 94:     This routine is not supported in Fortran.

 96:   Concepts: PetscViewer^file pointer
 97:   Concepts: file pointer^getting from PetscViewer

 99: .seealso: PetscViewerASCIIOpen(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerCreate(), PetscViewerASCIIPrintf(),
100:           PetscViewerASCIISynchronizedPrintf(), PetscViewerFlush()
101: @*/
102: int PetscViewerASCIIGetPointer(PetscViewer viewer,FILE **fd)
103: {
104:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;

107:   *fd = vascii->fd;
108:   return(0);
109: }

111: /*@C
112:     PetscViewerASCIISetMode - Sets the mode in which to open the file.

114:     Not Collective

116: +   viewer - viewer context, obtained from PetscViewerASCIIOpen()
117: -   mode   - The file mode

119:     Level: intermediate

121:     Fortran Note:
122:     This routine is not supported in Fortran.

124: .keywords: Viewer, file, get, pointer

126: .seealso: PetscViewerASCIIOpen()
127: @*/
128: int PetscViewerASCIISetMode(PetscViewer viewer, PetscFileMode mode)
129: {
130:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;

133:   vascii->mode = mode;
134:   return(0);
135: }

137: /*
138:    If petsc_history is on, then all Petsc*Printf() results are saved
139:    if the appropriate (usually .petschistory) file.
140: */
141: extern FILE *petsc_history;

143: /*@C
144:     PetscViewerASCIISetTab - Causes PetscViewer to tab in a number of times

146:     Not Collective, but only first processor in set has any effect

148:     Input Parameters:
149: +    viewer - optained with PetscViewerASCIIOpen()
150: -    tabs - number of tabs

152:     Level: developer

154:     Fortran Note:
155:     This routine is not supported in Fortran.

157:   Concepts: PetscViewerASCII^formating
158:   Concepts: tab^setting

160: .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(),
161:           PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(),
162:           PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushTab()
163: @*/
164: int PetscViewerASCIISetTab(PetscViewer viewer,int tabs)
165: {
166:   PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data;
167:   PetscTruth        isascii;
168:   int               ierr;

172:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
173:   if (isascii) {
174:     ascii->tab = tabs;
175:   }
176:   return(0);
177: }

179: /*@C
180:     PetscViewerASCIIPushTab - Adds one more tab to the amount that PetscViewerASCIIPrintf()
181:      lines are tabbed.

183:     Not Collective, but only first processor in set has any effect

185:     Input Parameters:
186: .    viewer - optained with PetscViewerASCIIOpen()

188:     Level: developer

190:     Fortran Note:
191:     This routine is not supported in Fortran.

193:   Concepts: PetscViewerASCII^formating
194:   Concepts: tab^setting

196: .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(),
197:           PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(),
198:           PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer()
199: @*/
200: int PetscViewerASCIIPushTab(PetscViewer viewer)
201: {
202:   PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data;
203:   PetscTruth        isascii;
204:   int               ierr;

208:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
209:   if (isascii) {
210:     ascii->tab++;
211:   }
212:   return(0);
213: }

215: /*@C
216:     PetscViewerASCIIPopTab - Removes one tab from the amount that PetscViewerASCIIPrintf()
217:      lines are tabbed.

219:     Not Collective, but only first processor in set has any effect

221:     Input Parameters:
222: .    viewer - optained with PetscViewerASCIIOpen()

224:     Level: developer

226:     Fortran Note:
227:     This routine is not supported in Fortran.

229:   Concepts: PetscViewerASCII^formating
230:   Concepts: tab^setting

232: .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(),
233:           PetscViewerASCIIPushTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(),
234:           PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer()
235: @*/
236: int PetscViewerASCIIPopTab(PetscViewer viewer)
237: {
238:   PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data;
239:   int               ierr;
240:   PetscTruth        isascii;

244:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
245:   if (isascii) {
246:     if (ascii->tab <= 0) SETERRQ(1,"More tabs popped than pushed");
247:     ascii->tab--;
248:   }
249:   return(0);
250: }

252: /*@C
253:     PetscViewerASCIIUseTabs - Turns on or off the use of tabs with the ASCII PetscViewer

255:     Not Collective, but only first processor in set has any effect

257:     Input Parameters:
258: +    viewer - optained with PetscViewerASCIIOpen()
259: -    flg - PETSC_YES or PETSC_NO

261:     Level: developer

263:     Fortran Note:
264:     This routine is not supported in Fortran.

266:   Concepts: PetscViewerASCII^formating
267:   Concepts: tab^setting

269: .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(),
270:           PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIPushTab(), PetscViewerASCIIOpen(),
271:           PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer()
272: @*/
273: int PetscViewerASCIIUseTabs(PetscViewer viewer,PetscTruth flg)
274: {
275:   PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data;
276:   PetscTruth        isascii;
277:   int               ierr;

281:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
282:   if (isascii) {
283:     if (flg) {
284:       ascii->tab       = ascii->tab_store;
285:     } else {
286:       ascii->tab_store = ascii->tab;
287:       ascii->tab       = 0;
288:     }
289:   }
290:   return(0);
291: }

293: /* ----------------------------------------------------------------------- */

295:  #include src/sys/src/fileio/mprint.h

297: /*@C
298:     PetscViewerASCIIPrintf - Prints to a file, only from the first
299:     processor in the PetscViewer

301:     Not Collective, but only first processor in set has any effect

303:     Input Parameters:
304: +    viewer - optained with PetscViewerASCIIOpen()
305: -    format - the usual printf() format string 

307:     Level: developer

309:     Fortran Note:
310:     The call sequence is PetscViewerASCIIPrintf(PetscViewer, character(*), int ierr) from Fortran. 
311:     That is, you can only pass a single character string from Fortran.

313:   Concepts: PetscViewerASCII^printing
314:   Concepts: printing^to file
315:   Concepts: printf

317: .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIOpen(),
318:           PetscViewerASCIIPushTab(), PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(),
319:           PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer()
320: @*/
321: int PetscViewerASCIIPrintf(PetscViewer viewer,const char format[],...)
322: {
323:   PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data;
324:   int               rank,tab,ierr;
325:   FILE              *fd = ascii->fd;
326:   PetscTruth        isascii;

330:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
331:   if (!isascii) SETERRQ(1,"Not ASCII PetscViewer");

333:   MPI_Comm_rank(viewer->comm,&rank);
334:   if (ascii->bviewer) {MPI_Comm_rank(ascii->bviewer->comm,&rank);}
335:   if (!rank) {
336:     va_list Argp;
337:     if (ascii->bviewer) {
338:       queuefile = fd;
339:     }

341:     tab = ascii->tab;
342:     while (tab--) fprintf(fd,"  ");

344:     va_start(Argp,format);
345: #if defined(PETSC_HAVE_VPRINTF_CHAR)
346:     vfprintf(fd,format,(char*)Argp);
347: #else
348:     vfprintf(fd,format,Argp);
349: #endif
350:     fflush(fd);
351:     if (petsc_history) {
352:       tab = ascii->tab;
353:       while (tab--) fprintf(fd,"  ");
354: #if defined(PETSC_HAVE_VPRINTF_CHAR)
355:       vfprintf(petsc_history,format,(char *)Argp);
356: #else
357:       vfprintf(petsc_history,format,Argp);
358: #endif
359:       fflush(petsc_history);
360:     }
361:     va_end(Argp);
362:   } else if (ascii->bviewer) { /* this is a singleton PetscViewer that is not on process 0 */
363:     int         len;
364:     va_list     Argp;

366:     PrintfQueue next;
367:     PetscNew(struct _PrintfQueue,&next);
368:     if (queue) {queue->next = next; queue = next;}
369:     else       {queuebase   = queue = next;}
370:     queuelength++;
371:     va_start(Argp,format);
372: #if defined(PETSC_HAVE_VPRINTF_CHAR)
373:     vsprintf(next->string,format,(char *)Argp);
374: #else
375:     vsprintf(next->string,format,Argp);
376: #endif
377:     va_end(Argp);
378:     PetscStrlen(next->string,&len);
379:     if (len > QUEUESTRINGSIZE) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Formatted string longer then %d bytes",QUEUESTRINGSIZE);
380:   }
381:   return(0);
382: }

384: /*@C
385:      PetscViewerSetFilename - Sets the name of the file the PetscViewer uses.

387:     Collective on PetscViewer

389:   Input Parameters:
390: +  viewer - the PetscViewer; either ASCII or binary
391: -  name - the name of the file it should use

393:     Level: advanced

395: .seealso: PetscViewerCreate(), PetscViewerSetType(), PetscViewerASCIIOpen(), PetscViewerBinaryOpen(), PetscViewerDestroy(),
396:           PetscViewerASCIIGetPointer(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf()

398: @*/
399: int PetscViewerSetFilename(PetscViewer viewer,const char name[])
400: {
401:   int ierr,(*f)(PetscViewer,const char[]);

405:   if (!name) SETERRQ(1,"You must pass in non-null string");
406:   PetscObjectQueryFunction((PetscObject)viewer,"PetscViewerSetFilename_C",(void (**)(void))&f);
407:   if (f) {
408:     (*f)(viewer,name);
409:   }

411:   return(0);
412: }

414: /*@C
415:      PetscViewerGetFilename - Gets the name of the file the PetscViewer uses.

417:     Not Collective

419:   Input Parameter:
420: .  viewer - the PetscViewer; either ASCII or binary

422:   Output Parameter:
423: .  name - the name of the file it is using

425:     Level: advanced

427: .seealso: PetscViewerCreate(), PetscViewerSetType(), PetscViewerASCIIOpen(), PetscViewerBinaryOpen(), PetscViewerSetFilename()

429: @*/
430: int PetscViewerGetFilename(PetscViewer viewer,char **name)
431: {
432:   int ierr,(*f)(PetscViewer,char **);

436:   PetscObjectQueryFunction((PetscObject)viewer,"PetscViewerGetFilename_C",(void (**)(void))&f);
437:   if (f) {
438:     (*f)(viewer,name);
439:   }

441:   return(0);
442: }

444: EXTERN_C_BEGIN
445: int PetscViewerGetFilename_ASCII(PetscViewer viewer,char **name)
446: {
447:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data;

450:   *name = vascii->filename;
451:   return(0);
452: }
453: EXTERN_C_END

455: EXTERN_C_BEGIN
456: int PetscViewerSetFilename_ASCII(PetscViewer viewer,const char name[])
457: {
458:   int               ierr,len;
459:   char              fname[256],*gz;
460:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data;
461:   PetscTruth        isstderr,isstdout;

464:   if (!name) return(0);

466:   PetscStrallocpy(name,&vascii->filename);

468:   /* Is this file to be compressed */
469:   vascii->storecompressed = PETSC_FALSE;
470:   PetscStrstr(vascii->filename,".gz",&gz);
471:   if (gz) {
472:     PetscStrlen(gz,&len);
473:     if (len == 3) {
474:       *gz = 0;
475:       vascii->storecompressed = PETSC_TRUE;
476:     }
477:   }
478:   PetscStrcmp(name,"stderr",&isstderr);
479:   PetscStrcmp(name,"stdout",&isstdout);
480:   if (isstderr)      vascii->fd = stderr;
481:   else if (isstdout) vascii->fd = stdout;
482:   else {
483:     PetscFixFilename(name,fname);
484:     switch(vascii->mode) {
485:     case FILE_MODE_READ:
486:       vascii->fd = fopen(fname,"r");
487:       break;
488:     case FILE_MODE_WRITE:
489:       vascii->fd = fopen(fname,"w");
490:       break;
491:     case FILE_MODE_APPEND:
492:       vascii->fd = fopen(fname,"a");
493:       break;
494:     case FILE_MODE_UPDATE:
495:       vascii->fd = fopen(fname,"r+");
496:       if (vascii->fd == PETSC_NULL) {
497:         vascii->fd = fopen(fname,"w+");
498:       }
499:       break;
500:     case FILE_MODE_APPEND_UPDATE:
501:       /* I really want a file which is opened at the end for updating,
502:          not a+, which opens at the beginning, but makes writes at the end.
503:       */
504:       vascii->fd = fopen(fname,"r+");
505:       if (vascii->fd == PETSC_NULL) {
506:         vascii->fd = fopen(fname,"w+");
507:       } else {
508:         ierr     = fseek(vascii->fd, 0, SEEK_END);
509:       }
510:       break;
511:     default:
512:       SETERRQ1(PETSC_ERR_ARG_WRONG, "Invalid file mode %d", vascii->mode);
513:     }

515:     if (!vascii->fd) SETERRQ1(PETSC_ERR_FILE_OPEN,"Cannot open PetscViewer file: %s",fname);
516:   }
517: #if defined(PETSC_USE_LOG)
518:   PetscLogObjectState((PetscObject)viewer,"File: %s",name);
519: #endif

521:   return(0);
522: }
523: EXTERN_C_END

525: int PetscViewerGetSingleton_ASCII(PetscViewer viewer,PetscViewer *outviewer)
526: {
527:   int               rank,ierr;
528:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data,*ovascii;
529:   char              *name;

532:   if (vascii->sviewer) {
533:     SETERRQ(1,"Singleton already obtained from PetscViewer and not restored");
534:   }
535:   ierr         = PetscViewerCreate(PETSC_COMM_SELF,outviewer);
536:   ierr         = PetscViewerSetType(*outviewer,PETSC_VIEWER_ASCII);
537:   ovascii      = (PetscViewer_ASCII*)(*outviewer)->data;
538:   ovascii->fd  = vascii->fd;
539:   ovascii->tab = vascii->tab;

541:   vascii->sviewer = *outviewer;

543:   (*outviewer)->format     = viewer->format;
544:   (*outviewer)->iformat    = viewer->iformat;

546:   PetscObjectGetName((PetscObject)viewer,&name);
547:   PetscObjectSetName((PetscObject)(*outviewer),name);

549:   MPI_Comm_rank(viewer->comm,&rank);
550:   ((PetscViewer_ASCII*)((*outviewer)->data))->bviewer = viewer;
551:   (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII_Singleton;
552:   if (rank) {
553:     (*outviewer)->ops->flush = 0;
554:   } else {
555:     (*outviewer)->ops->flush = PetscViewerFlush_ASCII_Singleton_0;
556:   }
557:   return(0);
558: }

560: int PetscViewerRestoreSingleton_ASCII(PetscViewer viewer,PetscViewer *outviewer)
561: {
562:   int               ierr;
563:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)(*outviewer)->data;
564:   PetscViewer_ASCII *ascii  = (PetscViewer_ASCII *)viewer->data;

567:   if (!ascii->sviewer) {
568:     SETERRQ(1,"Singleton never obtained from PetscViewer");
569:   }
570:   if (ascii->sviewer != *outviewer) {
571:     SETERRQ(1,"This PetscViewer did not generate singleton");
572:   }

574:   ascii->sviewer             = 0;
575:   vascii->fd                 = stdout;
576:   (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII;
577:   ierr                       = PetscViewerDestroy(*outviewer);
578:   PetscViewerFlush(viewer);
579:   return(0);
580: }

582: EXTERN_C_BEGIN
583: int PetscViewerCreate_ASCII(PetscViewer viewer)
584: {
585:   PetscViewer_ASCII *vascii;
586:   int               ierr;

589:   ierr         = PetscNew(PetscViewer_ASCII,&vascii);
590:   viewer->data = (void*)vascii;

592:   viewer->ops->destroy          = PetscViewerDestroy_ASCII;
593:   viewer->ops->flush            = PetscViewerFlush_ASCII;
594:   viewer->ops->getsingleton     = PetscViewerGetSingleton_ASCII;
595:   viewer->ops->restoresingleton = PetscViewerRestoreSingleton_ASCII;

597:   /* defaults to stdout unless set with PetscViewerSetFilename() */
598:   vascii->fd             = stdout;
599:   vascii->mode           = FILE_MODE_WRITE;
600:   vascii->bviewer        = 0;
601:   vascii->sviewer        = 0;
602:   viewer->format         = PETSC_VIEWER_ASCII_DEFAULT;
603:   viewer->iformat        = 0;
604:   vascii->tab            = 0;
605:   vascii->tab_store      = 0;
606:   vascii->filename       = 0;

608:   PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerSetFilename_C","PetscViewerSetFilename_ASCII",
609:                                      PetscViewerSetFilename_ASCII);
610:   PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerGetFilename_C","PetscViewerGetFilename_ASCII",
611:                                      PetscViewerGetFilename_ASCII);

613:   return(0);
614: }
615: EXTERN_C_END


618: /*@C
619:     PetscViewerASCIISynchronizedFPrintf - Prints synchronized output to the specified file from
620:     several processors.  Output of the first processor is followed by that of the 
621:     second, etc.

623:     Not Collective, must call collective PetscViewerFlush() to get the results out

625:     Input Parameters:
626: +   viewer - the ASCII PetscViewer
627: -   format - the usual printf() format string 

629:     Level: intermediate

631:     Fortran Note:
632:       Can only print a single character* string

634: .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(),
635:           PetscFOpen(), PetscViewerFlush(), PetscViewerASCIIGetPointer(), PetscViewerDestroy(), PetscViewerASCIIOpen(),
636:           PetscViewerASCIIPrintf()

638: @*/
639: int PetscViewerASCIISynchronizedPrintf(PetscViewer viewer,const char format[],...)
640: {
641:   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;
642:   int               ierr,rank,tab = vascii->tab;
643:   MPI_Comm          comm;
644:   FILE              *fp;
645:   PetscTruth        isascii;

649:   PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);
650:   if (!isascii) SETERRQ(1,"Not ASCII PetscViewer");

652:   comm = viewer->comm;
653:   fp   = vascii->fd;
654:   MPI_Comm_rank(comm,&rank);
655:   if (vascii->bviewer) {MPI_Comm_rank(vascii->bviewer->comm,&rank);}
656: 

658:   /* First processor prints immediately to fp */
659:   if (!rank) {
660:     va_list Argp;

662:     while (tab--) fprintf(fp,"  ");

664:     va_start(Argp,format);
665: #if defined(PETSC_HAVE_VPRINTF_CHAR)
666:     vfprintf(fp,format,(char*)Argp);
667: #else
668:     vfprintf(fp,format,Argp);
669: #endif
670:     fflush(fp);
671:     queuefile = fp;
672:     if (petsc_history) {
673: #if defined(PETSC_HAVE_VPRINTF_CHAR)
674:       vfprintf(petsc_history,format,(char *)Argp);
675: #else
676:       vfprintf(petsc_history,format,Argp);
677: #endif
678:       fflush(petsc_history);
679:     }
680:     va_end(Argp);
681:   } else { /* other processors add to local queue */
682:     int         len;
683:     char        *string;
684:     va_list     Argp;
685:     PrintfQueue next;

687:     PetscNew(struct _PrintfQueue,&next);
688:     if (queue) {queue->next = next; queue = next;}
689:     else       {queuebase   = queue = next;}
690:     queuelength++;
691:     string = next->string;
692:     while (tab--) {*string++ = ' ';}
693:     va_start(Argp,format);
694: #if defined(PETSC_HAVE_VPRINTF_CHAR)
695:     vsprintf(string,format,(char *)Argp);
696: #else
697:     vsprintf(string,format,Argp);
698: #endif
699:     va_end(Argp);
700:     PetscStrlen(next->string,&len);
701:     if (len > QUEUESTRINGSIZE) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Formatted string longer then %d bytes",QUEUESTRINGSIZE);
702:   }
703:   return(0);
704: }