/*@C PetscViewerVUPrintDeferred - Prints to the deferred write cache instead of the file. Not Collective Input Parameters: + viewer - The PetscViewer - format - The format string Level: intermediate .keywords: Viewer, print, deferred .seealso: PetscViewerVUFlushDeferred() @*/ PetscErrorCode PetscViewerVUPrintDeferred(PetscViewer viewer, const char format[], ...) { PetscViewer_VU *vu = (PetscViewer_VU*) viewer->data; va_list Argp; size_t fullLength; PrintfQueue next; PetscErrorCode ierr; PetscFunctionBegin; ierr = PetscNew(struct _PrintfQueue, &next);CHKERRQ(ierr); if (vu->queue) { vu->queue->next = next; vu->queue = next; vu->queue->next = NULL; } else { vu->queueBase = vu->queue = next; } vu->queueLength++; va_start(Argp, format); ierr = PetscMemzero(next->string,QUEUESTRINGSIZE);CHKERRQ(ierr); ierr = PetscVSNPrintf(next->string, QUEUESTRINGSIZE,format,&fullLength, Argp);CHKERRQ(ierr); va_end(Argp); PetscFunctionReturn(0); }
/*@C PetscViewerStringSPrintf - Prints information to a PetscViewer string. Logically Collective on PetscViewer (Hmmm, each processor maintains a separate string) Input Parameters: + v - a string PetscViewer, formed by PetscViewerStringOpen() - format - the format of the input Level: developer Fortran Note: This routine is not supported in Fortran. Concepts: printing^to string .seealso: PetscViewerStringOpen(), PetscViewerStringGetStringRead(), PetscViewerStringSetString(), PETSCVIEWERSTRING @*/ PetscErrorCode PetscViewerStringSPrintf(PetscViewer viewer,const char format[],...) { va_list Argp; size_t fullLength; size_t shift,cshift; PetscErrorCode ierr; PetscBool isstring; char tmp[4096]; PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring);CHKERRQ(ierr); if (!isstring) PetscFunctionReturn(0); if (!vstr->string) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Must call PetscViewerStringSetString() before using"); va_start(Argp,format); ierr = PetscVSNPrintf(tmp,4096,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); ierr = PetscStrlen(tmp,&shift);CHKERRQ(ierr); cshift = shift+1; if (cshift >= vstr->maxlen - vstr->curlen - 1) cshift = vstr->maxlen - vstr->curlen - 1; ierr = PetscStrncpy(vstr->head,tmp,cshift);CHKERRQ(ierr); vstr->head += shift; vstr->curlen += shift; PetscFunctionReturn(0); }
/*@C PetscSNPrintfCount - Prints to a string of given length, returns count Not Collective Input Parameters: + str - the string to print to . len - the length of str . format - the usual printf() format string . countused - number of characters used - any arguments Level: intermediate .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), PetscVSNPrintf(), PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf(), PetscSNPrintf() @*/ PetscErrorCode PetscSNPrintfCount(char *str,size_t len,const char format[],size_t *countused,...) { PetscErrorCode ierr; va_list Argp; PetscFunctionBegin; va_start(Argp,countused); ierr = PetscVSNPrintf(str,len,format,countused,Argp);CHKERRQ(ierr); PetscFunctionReturn(0); }
/*@C PetscSNPrintf - Prints to a string of given length Not Collective Input Parameters: + str - the string to print to . len - the length of str . format - the usual printf() format string - any arguments Level: intermediate .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), PetscVSNPrintf(), PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf() @*/ PetscErrorCode PetscSNPrintf(char *str,size_t len,const char format[],...) { PetscErrorCode ierr; size_t fullLength; va_list Argp; PetscFunctionBegin; va_start(Argp,format); ierr = PetscVSNPrintf(str,len,format,&fullLength,Argp);CHKERRQ(ierr); PetscFunctionReturn(0); }
/*@C PetscVFPrintf - All PETSc standard out and error messages are sent through this function; so, in theory, this can can be replaced with something that does not simply write to a file. To use, write your own function for example, $PetscErrorCode mypetscvfprintf(FILE *fd,const char format[],va_list Argp) ${ $ PetscErrorCode ierr; $ $ PetscFunctionBegin; $ if (fd != stdout && fd != stderr) { handle regular files $ ierr = PetscVFPrintfDefault(fd,format,Argp);CHKERR(ierr); $ } else { $ char buff[BIG]; $ size_t length; $ ierr = PetscVSNPrintf(buff,BIG,format,&length,Argp);CHKERRQ(ierr); $ now send buff to whatever stream or whatever you want $ } $ PetscFunctionReturn(0); $} then before the call to PetscInitialize() do the assignment $ PetscVFPrintf = mypetscvfprintf; Notes: For error messages this may be called by any process, for regular standard out it is called only by process 0 of a given communicator Developer Notes: this could be called by an error handler, if that happens then a recursion of the error handler may occur and a crash Level: developer .seealso: PetscVSNPrintf(), PetscErrorPrintf() @*/ PetscErrorCode PetscVFPrintfDefault(FILE *fd,const char *format,va_list Argp) { char str[8*1024]; PetscErrorCode ierr; PetscFunctionBegin; ierr = PetscVSNPrintf(str,sizeof(str),format,NULL,Argp);CHKERRQ(ierr); fprintf(fd,"%s",str);CHKERRQ(ierr); fflush(fd); PetscFunctionReturn(0); }
PetscErrorCode PetscVFPrintf_Matlab(FILE *fd,const char format[],va_list Argp) { PetscErrorCode ierr; PetscFunctionBegin; if (fd != stdout && fd != stderr) { /* handle regular files */ ierr = PetscVFPrintfDefault(fd,format,Argp);CHKERRQ(ierr); } else { size_t len=8*1024,length; char buf[len]; ierr = PetscVSNPrintf(buf,len,format,&length,Argp);CHKERRQ(ierr); mexPrintf("%s",buf); } PetscFunctionReturn(0); }
/*@C PetscSynchronizedFPrintf - Prints synchronized output to the specified file from several processors. Output of the first processor is followed by that of the second, etc. Not Collective Input Parameters: + comm - the communicator . fd - the file pointer - format - the usual printf() format string Level: intermediate Notes: REQUIRES a intervening call to PetscSynchronizedFlush() for the information from all the processors to be printed. .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), PetscFOpen(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIPrintf() @*/ PetscErrorCode PetscSynchronizedFPrintf(MPI_Comm comm,FILE *fp,const char format[],...) { PetscErrorCode ierr; PetscMPIInt rank; PetscFunctionBegin; if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); /* First processor prints immediately to fp */ if (!rank) { va_list Argp; va_start(Argp,format); ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); petsc_printfqueuefile = fp; if (petsc_history && (fp !=petsc_history)) { va_start(Argp,format); ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); } va_end(Argp); } else { /* other processors add to local queue */ va_list Argp; PrintfQueue next; size_t fullLength = 8191; ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); if (petsc_printfqueue) { petsc_printfqueue->next = next; petsc_printfqueue = next; petsc_printfqueue->next = 0; } else petsc_printfqueuebase = petsc_printfqueue = next; petsc_printfqueuelength++; next->size = -1; while ((PetscInt)fullLength >= next->size) { next->size = fullLength+1; ierr = PetscMalloc(next->size * sizeof(char), &next->string);CHKERRQ(ierr); va_start(Argp,format); ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); ierr = PetscVSNPrintf(next->string,next->size,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); } } PetscFunctionReturn(0); }
/*@C PetscError - Routine that is called when an error has been detected, usually called through the macro SETERRQ(PETSC_COMM_SELF,). Not Collective Input Parameters: + comm - communicator over which error occurred. ALL ranks of this communicator MUST call this routine . line - the line number of the error (indicated by __LINE__) . func - the function where the error occured (indicated by __FUNCT__) . dir - the directory of file (indicated by __SDIR__) . file - the file in which the error was detected (indicated by __FILE__) . mess - an error text string, usually just printed to the screen . n - the generic error number . p - PETSC_ERROR_INITIAL indicates the error was initially detected, PETSC_ERROR_REPEAT indicates this is a traceback from a previously detected error - mess - formatted message string - aka printf Level: intermediate Notes: Most users need not directly use this routine and the error handlers, but can instead use the simplified interface SETERRQ, which has the calling sequence $ SETERRQ(comm,n,mess) Experienced users can set the error handler with PetscPushErrorHandler(). Developer Note: Since this is called after an error condition it should not be calling any error handlers (currently it ignores any error codes) BUT this routine does call regular PETSc functions that may call error handlers, this is problematic and could be fixed by never calling other PETSc routines but this annoying. Concepts: error^setting condition .seealso: PetscTraceBackErrorHandler(), PetscPushErrorHandler(), SETERRQ(), CHKERRQ(), CHKMEMQ, SETERRQ1(), SETERRQ2() @*/ PetscErrorCode PetscError(MPI_Comm comm,int line,const char *func,const char *file,const char *dir,PetscErrorCode n,PetscErrorType p,const char *mess,...) { va_list Argp; size_t fullLength; char buf[2048],*lbuf = 0; PetscBool ismain,isunknown; PetscErrorCode ierr; PetscFunctionBegin; if (!func) func = "User provided function"; if (!file) file = "User file"; if (!dir) dir = " "; if (comm == MPI_COMM_NULL) comm = PETSC_COMM_SELF; /* Compose the message evaluating the print format */ if (mess) { va_start(Argp,mess); PetscVSNPrintf(buf,2048,mess,&fullLength,Argp); va_end(Argp); lbuf = buf; if (p == 1) PetscStrncpy(PetscErrorBaseMessage,lbuf,1023); } if (!eh) ierr = PetscTraceBackErrorHandler(comm,line,func,file,dir,n,p,lbuf,0); else ierr = (*eh->handler)(comm,line,func,file,dir,n,p,lbuf,eh->ctx); /* If this is called from the main() routine we call MPI_Abort() instead of return to allow the parallel program to be properly shutdown. Since this is in the error handler we don't check the errors below. Of course, PetscStrncmp() does its own error checking which is problamatic */ PetscStrncmp(func,"main",4,&ismain); PetscStrncmp(func,"unknown",7,&isunknown); if (ismain || isunknown) MPI_Abort(PETSC_COMM_WORLD,(int)ierr); #if defined(PETSC_CLANGUAGE_CXX) if (p == PETSC_ERROR_IN_CXX) { PetscCxxErrorThrow(); } #endif PetscFunctionReturn(ierr); }
/*MC PetscInfo - Logs informative data, which is printed to standard output or a file when the option -info <file> is specified. Synopsis: #include <petscsys.h> PetscErrorCode PetscInfo(void *vobj, const char message[]) PetscErrorCode PetscInfo1(void *vobj, const char formatmessage[],arg1) PetscErrorCode PetscInfo2(void *vobj, const char formatmessage[],arg1,arg2) etc Collective over PetscObject argument Input Parameter: + vobj - object most closely associated with the logging statement or NULL . message - logging message - formatmessage - logging message using standard "printf" format Options Database Key: $ -info : activates printing of PetscInfo() messages Level: intermediate Fortran Note: This function does not take the vobj argument, there is only the PetscInfo() version, not PetscInfo1() etc. Example of Usage: $ $ Mat A $ double alpha $ PetscInfo1(A,"Matrix uses parameter alpha=%g\n",alpha); $ Concepts: runtime information .seealso: PetscInfoAllow() M*/ PetscErrorCode PetscInfo_Private(const char func[],void *vobj, const char message[], ...) { va_list Argp; PetscMPIInt rank,urank; size_t len; PetscObject obj = (PetscObject)vobj; char string[8*1024]; PetscErrorCode ierr; size_t fullLength; int err; PetscFunctionBegin; if (obj) PetscValidHeader(obj,1); PetscValidCharPointer(message,2); if (!PetscLogPrintInfo) PetscFunctionReturn(0); if ((!PetscLogPrintInfoNull) && !vobj) PetscFunctionReturn(0); if (obj && !PetscInfoFlags[obj->classid - PETSC_SMALLEST_CLASSID - 1]) PetscFunctionReturn(0); if (!obj) rank = 0; else { ierr = MPI_Comm_rank(obj->comm, &rank); CHKERRQ(ierr); } if (rank) PetscFunctionReturn(0); ierr = MPI_Comm_rank(MPI_COMM_WORLD, &urank); CHKERRQ(ierr); va_start(Argp, message); sprintf(string, "[%d] %s(): ", urank,func); ierr = PetscStrlen(string, &len); CHKERRQ(ierr); ierr = PetscVSNPrintf(string+len, 8*1024-len,message,&fullLength, Argp); CHKERRQ(ierr); ierr = PetscFPrintf(PETSC_COMM_SELF,PetscInfoFile, "%s", string); CHKERRQ(ierr); err = fflush(PetscInfoFile); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); if (petsc_history) { va_start(Argp, message); ierr = (*PetscVFPrintf)(petsc_history, message, Argp); CHKERRQ(ierr); } va_end(Argp); PetscFunctionReturn(0); }
/*@C PetscSynchronizedPrintf - Prints synchronized output from several processors. Output of the first processor is followed by that of the second, etc. Not Collective Input Parameters: + comm - the communicator - format - the usual printf() format string Level: intermediate Notes: REQUIRES a intervening call to PetscSynchronizedFlush() for the information from all the processors to be printed. Fortran Note: The call sequence is PetscSynchronizedPrintf(MPI_Comm, character(*), PetscErrorCode ierr) from Fortran. That is, you can only pass a single character string from Fortran. .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf() @*/ PetscErrorCode PetscSynchronizedPrintf(MPI_Comm comm,const char format[],...) { PetscErrorCode ierr; PetscMPIInt rank; PetscFunctionBegin; ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); /* First processor prints immediately to stdout */ if (!rank) { va_list Argp; va_start(Argp,format); ierr = (*PetscVFPrintf)(PETSC_STDOUT,format,Argp);CHKERRQ(ierr); if (petsc_history) { va_start(Argp,format); ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); } va_end(Argp); } else { /* other processors add to local queue */ va_list Argp; PrintfQueue next; size_t fullLength = 8191; ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); if (petsc_printfqueue) {petsc_printfqueue->next = next; petsc_printfqueue = next; petsc_printfqueue->next = 0;} else {petsc_printfqueuebase = petsc_printfqueue = next;} petsc_printfqueuelength++; next->size = -1; while((PetscInt)fullLength >= next->size) { next->size = fullLength+1; ierr = PetscMalloc(next->size * sizeof(char), &next->string);CHKERRQ(ierr); va_start(Argp,format); ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); ierr = PetscVSNPrintf(next->string,next->size,format, &fullLength,Argp);CHKERRQ(ierr); va_end(Argp); } } PetscFunctionReturn(0); }
/*@C PetscMatlabEngineEvaluate - Evaluates a string in MATLAB Not Collective Input Parameters: + mengine - the MATLAB engine - string - format as in a printf() Level: advanced .seealso: PetscMatlabEngineDestroy(), PetscMatlabEnginePut(), PetscMatlabEngineGet(), PetscMatlabEngineCreate(), PetscMatlabEngineGetOutput(), PetscMatlabEnginePrintOutput(), PETSC_MATLAB_ENGINE_(), PetscMatlabEnginePutArray(), PetscMatlabEngineGetArray(), PetscMatlabEngine @*/ PetscErrorCode PetscMatlabEngineEvaluate(PetscMatlabEngine mengine,const char string[],...) { va_list Argp; char buffer[1024]; PetscErrorCode ierr; size_t fullLength; PetscFunctionBegin; va_start(Argp,string); ierr = PetscVSNPrintf(buffer,1024-9-5,string,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); ierr = PetscInfo1(0,"Evaluating MATLAB string: %s\n",buffer);CHKERRQ(ierr); engEvalString(mengine->ep, buffer); /* Check for error in MATLAB: indicated by ? as first character in engine->buffer */ if (mengine->buffer[4] == '?') SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_LIB,"Error in evaluating MATLAB command:%s\n%s",string,mengine->buffer); ierr = PetscInfo1(0,"Done evaluating Matlab string: %s\n",buffer);CHKERRQ(ierr); PetscFunctionReturn(0); }
EXTERN_C_END #undef __FUNCT__ #define __FUNCT__ "PetscViewerASCIISynchronizedPrintf" /*@C PetscViewerASCIISynchronizedPrintf - Prints synchronized output to the specified file from several processors. Output of the first processor is followed by that of the second, etc. Not Collective, must call collective PetscViewerFlush() to get the results out Input Parameters: + viewer - the ASCII PetscViewer - format - the usual printf() format string Level: intermediate Notes: You must have previously called PetscViewerASCIISynchronizeAllow() to allow this routine to be called. Fortran Note: Can only print a single character* string .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), PetscFOpen(), PetscViewerFlush(), PetscViewerASCIIGetPointer(), PetscViewerDestroy(), PetscViewerASCIIOpen(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedAllow() @*/ PetscErrorCode PetscViewerASCIISynchronizedPrintf(PetscViewer viewer,const char format[],...) { PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; PetscErrorCode ierr; PetscMPIInt rank,size; PetscInt tab = vascii->tab; MPI_Comm comm; FILE *fp; PetscBool iascii; int err; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); ierr = MPI_Comm_size(((PetscObject)viewer)->comm,&size);CHKERRQ(ierr); if (size > 1 && !vascii->allowsynchronized) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"First call PetscViewerASCIISynchronizedAllow() to allow this call"); if (!viewer->ops->flush) PetscFunctionReturn(0); /* This viewer obtained via PetscViewerGetSubcomm_ASCII(), should not participate. */ comm = ((PetscObject)viewer)->comm; fp = vascii->fd; ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); /* First processor prints immediately to fp */ if (!rank) { va_list Argp; while (tab--) {ierr = PetscFPrintf(PETSC_COMM_SELF,fp," ");CHKERRQ(ierr);} va_start(Argp,format); ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); err = fflush(fp); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); petsc_printfqueuefile = fp; if (petsc_history) { va_start(Argp,format); ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); err = fflush(petsc_history); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); } va_end(Argp); } else { /* other processors add to local queue */ char *string; va_list Argp; size_t fullLength; PrintfQueue next; ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); if (petsc_printfqueue) {petsc_printfqueue->next = next; petsc_printfqueue = next;} else {petsc_printfqueuebase = petsc_printfqueue = next;} petsc_printfqueuelength++; next->size = QUEUESTRINGSIZE; ierr = PetscMalloc(next->size*sizeof(char), &next->string);CHKERRQ(ierr); ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); string = next->string; tab *= 2; while (tab--) {*string++ = ' ';} va_start(Argp,format); ierr = PetscVSNPrintf(string,next->size-2*vascii->tab,format,&fullLength,Argp); va_end(Argp); } PetscFunctionReturn(0); }
/*@C PetscViewerASCIISynchronizedPrintf - Prints synchronized output to the specified file from several processors. Output of the first processor is followed by that of the second, etc. Not Collective, must call collective PetscViewerFlush() to get the results out Input Parameters: + viewer - the ASCII PetscViewer - format - the usual printf() format string Level: intermediate Notes: You must have previously called PetscViewerASCIISynchronizeAllow() to allow this routine to be called. Fortran Note: Can only print a single character* string .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), PetscFOpen(), PetscViewerFlush(), PetscViewerASCIIGetPointer(), PetscViewerDestroy(), PetscViewerASCIIOpen(), PetscViewerASCIIPrintf(), PetscViewerASCIIPushSynchronized() @*/ PetscErrorCode PetscViewerASCIISynchronizedPrintf(PetscViewer viewer,const char format[],...) { PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data; PetscErrorCode ierr; PetscMPIInt rank; PetscInt tab = vascii->tab; MPI_Comm comm; FILE *fp; PetscBool iascii,hasbviewer = PETSC_FALSE; int err; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); if (!vascii->allowsynchronized) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"First call PetscViewerASCIIPushSynchronized() to allow this call"); ierr = PetscObjectGetComm((PetscObject)viewer,&comm);CHKERRQ(ierr); ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); if (vascii->bviewer) { hasbviewer = PETSC_TRUE; if (!rank) { vascii = (PetscViewer_ASCII*)vascii->bviewer->data; ierr = PetscObjectGetComm((PetscObject)viewer,&comm);CHKERRQ(ierr); ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); } } fp = vascii->fd; if (!rank && !hasbviewer) { /* First processor prints immediately to fp */ va_list Argp; /* flush my own messages that I may have queued up */ PrintfQueue next = vascii->petsc_printfqueuebase,previous; PetscInt i; for (i=0; i<vascii->petsc_printfqueuelength; i++) { ierr = PetscFPrintf(comm,fp,"%s",next->string);CHKERRQ(ierr); previous = next; next = next->next; ierr = PetscFree(previous->string);CHKERRQ(ierr); ierr = PetscFree(previous);CHKERRQ(ierr); } vascii->petsc_printfqueue = 0; vascii->petsc_printfqueuelength = 0; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,fp," ");CHKERRQ(ierr); } va_start(Argp,format); ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); err = fflush(fp); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); if (petsc_history) { va_start(Argp,format); ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); err = fflush(petsc_history); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); } va_end(Argp); } else { /* other processors add to queue */ char *string; va_list Argp; size_t fullLength; PrintfQueue next; ierr = PetscNew(&next);CHKERRQ(ierr); if (vascii->petsc_printfqueue) { vascii->petsc_printfqueue->next = next; vascii->petsc_printfqueue = next; } else { vascii->petsc_printfqueuebase = vascii->petsc_printfqueue = next; } vascii->petsc_printfqueuelength++; next->size = QUEUESTRINGSIZE; ierr = PetscMalloc1(next->size, &next->string);CHKERRQ(ierr); ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); string = next->string; tab *= 2; while (tab--) { *string++ = ' '; } va_start(Argp,format); ierr = PetscVSNPrintf(string,next->size-2*vascii->tab,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); } PetscFunctionReturn(0); }
/*@C PetscViewerASCIIPrintf - Prints to a file, only from the first processor in the PetscViewer Not Collective, but only first processor in set has any effect Input Parameters: + viewer - obtained with PetscViewerASCIIOpen() - format - the usual printf() format string Level: developer Fortran Note: The call sequence is PetscViewerASCIIPrintf(PetscViewer, character(*), int ierr) from Fortran. That is, you can only pass a single character string from Fortran. Concepts: PetscViewerASCII^printing Concepts: printing^to file Concepts: printf .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIOpen(), PetscViewerASCIIPushTab(), PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushSynchronized() @*/ PetscErrorCode PetscViewerASCIIPrintf(PetscViewer viewer,const char format[],...) { PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; PetscMPIInt rank; PetscInt tab,intab = ascii->tab; PetscErrorCode ierr; FILE *fd = ascii->fd; PetscBool iascii; int err; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)viewer),&rank);CHKERRQ(ierr); if (rank) PetscFunctionReturn(0); if (ascii->bviewer) { /* pass string up to parent viewer */ char *string; va_list Argp; size_t fullLength; ierr = PetscCalloc1(QUEUESTRINGSIZE, &string);CHKERRQ(ierr); va_start(Argp,format); ierr = PetscVSNPrintf(string,QUEUESTRINGSIZE,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); ierr = PetscViewerASCIISynchronizedPrintf(viewer,"%s",string);CHKERRQ(ierr); ierr = PetscFree(string);CHKERRQ(ierr); } else { /* write directly to file */ va_list Argp; /* flush my own messages that I may have queued up */ PrintfQueue next = ascii->petsc_printfqueuebase,previous; PetscInt i; for (i=0; i<ascii->petsc_printfqueuelength; i++) { ierr = PetscFPrintf(PETSC_COMM_SELF,fd,"%s",next->string);CHKERRQ(ierr); previous = next; next = next->next; ierr = PetscFree(previous->string);CHKERRQ(ierr); ierr = PetscFree(previous);CHKERRQ(ierr); } ascii->petsc_printfqueue = 0; ascii->petsc_printfqueuelength = 0; tab = intab; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,fd," ");CHKERRQ(ierr); } va_start(Argp,format); ierr = (*PetscVFPrintf)(fd,format,Argp);CHKERRQ(ierr); err = fflush(fd); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); if (petsc_history) { va_start(Argp,format); tab = intab; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,petsc_history," ");CHKERRQ(ierr); } ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); err = fflush(petsc_history); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); } va_end(Argp); } PetscFunctionReturn(0); }
/*@C PetscViewerASCIISynchronizedPrintf - Prints synchronized output to the specified file from several processors. Output of the first processor is followed by that of the second, etc. Not Collective, must call collective PetscViewerFlush() to get the results out Input Parameters: + viewer - the ASCII PetscViewer - format - the usual printf() format string Level: intermediate Notes: You must have previously called PetscViewerASCIISynchronizeAllow() to allow this routine to be called. Fortran Note: Can only print a single character* string .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), PetscFOpen(), PetscViewerFlush(), PetscViewerASCIIGetPointer(), PetscViewerDestroy(), PetscViewerASCIIOpen(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedAllow() @*/ PetscErrorCode PetscViewerASCIISynchronizedPrintf(PetscViewer viewer,const char format[],...) { PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data; PetscErrorCode ierr; PetscMPIInt rank,size; PetscInt tab = vascii->tab; MPI_Comm comm; FILE *fp; PetscBool iascii; int err; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); ierr = MPI_Comm_size(PetscObjectComm((PetscObject)viewer),&size);CHKERRQ(ierr); if (size > 1 && !vascii->allowsynchronized) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"First call PetscViewerASCIISynchronizedAllow() to allow this call"); if (!viewer->ops->flush) PetscFunctionReturn(0); /* This viewer obtained via PetscViewerGetSubcomm_ASCII(), should not participate. */ ierr = PetscObjectGetComm((PetscObject)viewer,&comm);CHKERRQ(ierr); fp = vascii->fd; ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); /* First processor prints immediately to fp */ if (!rank) { va_list Argp; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,fp," ");CHKERRQ(ierr); } va_start(Argp,format); ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); err = fflush(fp); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); if (petsc_history) { va_start(Argp,format); ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); err = fflush(petsc_history); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); } va_end(Argp); } else { /* other processors add to local queue */ char *string; va_list Argp; size_t fullLength; PrintfQueue next; ierr = PetscNew(&next);CHKERRQ(ierr); if (petsc_printfqueue) { petsc_printfqueue->next = next; petsc_printfqueue = next; } else { petsc_printfqueuebase = petsc_printfqueue = next; } petsc_printfqueuelength++; next->size = QUEUESTRINGSIZE; ierr = PetscMalloc1(next->size, &next->string);CHKERRQ(ierr); ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); string = next->string; tab *= 2; while (tab--) { *string++ = ' '; } va_start(Argp,format); ierr = PetscVSNPrintf(string,next->size-2*vascii->tab,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); } PetscFunctionReturn(0); }
/*@C PetscViewerASCIIPrintf - Prints to a file, only from the first processor in the PetscViewer Not Collective, but only first processor in set has any effect Input Parameters: + viewer - optained with PetscViewerASCIIOpen() - format - the usual printf() format string Level: developer Fortran Note: The call sequence is PetscViewerASCIIPrintf(PetscViewer, character(*), int ierr) from Fortran. That is, you can only pass a single character string from Fortran. Concepts: PetscViewerASCII^printing Concepts: printing^to file Concepts: printf .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIOpen(), PetscViewerASCIIPushTab(), PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIISynchronizedAllow() @*/ PetscErrorCode PetscViewerASCIIPrintf(PetscViewer viewer,const char format[],...) { PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; PetscMPIInt rank; PetscInt tab,intab = ascii->tab; PetscErrorCode ierr; FILE *fd = ascii->fd; PetscBool iascii,issingleton = PETSC_FALSE; int err; PetscFunctionBegin; PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); PetscValidCharPointer(format,2); ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); if (ascii->bviewer) { viewer = ascii->bviewer; ascii = (PetscViewer_ASCII*)viewer->data; fd = ascii->fd; issingleton = PETSC_TRUE; } ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)viewer),&rank);CHKERRQ(ierr); if (!rank) { va_list Argp; tab = intab; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,fd," ");CHKERRQ(ierr); } va_start(Argp,format); ierr = (*PetscVFPrintf)(fd,format,Argp);CHKERRQ(ierr); err = fflush(fd); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); if (petsc_history) { va_start(Argp,format); tab = intab; while (tab--) { ierr = PetscFPrintf(PETSC_COMM_SELF,petsc_history," ");CHKERRQ(ierr); } ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); err = fflush(petsc_history); if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); } va_end(Argp); } else if (issingleton) { char *string; va_list Argp; size_t fullLength; PrintfQueue next; ierr = PetscNew(&next);CHKERRQ(ierr); if (petsc_printfqueue) { petsc_printfqueue->next = next; petsc_printfqueue = next; } else { petsc_printfqueuebase = petsc_printfqueue = next; } petsc_printfqueuelength++; next->size = QUEUESTRINGSIZE; ierr = PetscCalloc1(next->size, &next->string);CHKERRQ(ierr); string = next->string; tab = intab; tab *= 2; while (tab--) { *string++ = ' '; } va_start(Argp,format); ierr = PetscVSNPrintf(string,next->size-2*ascii->tab,format,&fullLength,Argp);CHKERRQ(ierr); va_end(Argp); } PetscFunctionReturn(0); }