1 /* 2 Utilites routines to add simple ASCII IO capability. 3 */ 4 #include <../src/sys/fileio/mprint.h> 5 #include <errno.h> 6 /* 7 If petsc_history is on, then all Petsc*Printf() results are saved 8 if the appropriate (usually .petschistory) file. 9 */ 10 extern FILE *petsc_history; 11 /* 12 Allows one to overwrite where standard out is sent. For example 13 PETSC_STDOUT = fopen("/dev/ttyXX","w") will cause all standard out 14 writes to go to terminal XX; assuming you have write permission there 15 */ 16 FILE *PETSC_STDOUT = 0; 17 /* 18 Allows one to overwrite where standard error is sent. For example 19 PETSC_STDERR = fopen("/dev/ttyXX","w") will cause all standard error 20 writes to go to terminal XX; assuming you have write permission there 21 */ 22 FILE *PETSC_STDERR = 0; 23 24 /* 25 Return the maximum expected new size of the format 26 */ 27 #define PETSC_MAX_LENGTH_FORMAT(l) (l+l/8) 28 29 #undef __FUNCT__ 30 #define __FUNCT__ "PetscFormatConvert" 31 /*@C 32 PetscFormatConvert - Takes a PETSc format string and converts it to a reqular C format string 33 34 Input Parameters: 35 + format - the PETSc format string 36 . newformat - the location to put the standard C format string values 37 - size - the length of newformat 38 39 Note: this exists so we can have the same code when PetscInt is either int or long long and PetscScalar is either __float128, double, or float 40 41 Level: developer 42 43 @*/ 44 PetscErrorCode PetscFormatConvert(const char *format,char *newformat,size_t size) 45 { 46 PetscInt i = 0,j = 0; 47 48 PetscFunctionBegin; 49 while (format[i] && j < (PetscInt)size-1) { 50 if (format[i] == '%' && format[i+1] != '%') { 51 /* Find the letter */ 52 for (; format[i] && format[i] <= '9'; i++) newformat[j++] = format[i]; 53 switch (format[i]) { 54 case 'D': 55 #if !defined(PETSC_USE_64BIT_INDICES) 56 newformat[j++] = 'd'; 57 #else 58 newformat[j++] = 'l'; 59 newformat[j++] = 'l'; 60 newformat[j++] = 'd'; 61 #endif 62 break; 63 case 'G': 64 #if defined(PETSC_USE_REAL_DOUBLE) || defined(PETSC_USE_REAL_SINGLE) 65 newformat[j++] = 'g'; 66 #elif defined(PETSC_USE_REAL___FLOAT128) 67 newformat[j++] = 'Q'; 68 newformat[j++] = 'g'; 69 #endif 70 break; 71 case 'F': 72 #if defined(PETSC_USE_REAL_DOUBLE) || defined(PETSC_USE_REAL_SINGLE) 73 newformat[j++] = 'f'; 74 #elif defined(PETSC_USE_REAL_LONG_DOUBLE) 75 newformat[j++] = 'L'; 76 newformat[j++] = 'f'; 77 #elif defined(PETSC_USE_REAL___FLOAT128) 78 newformat[j++] = 'Q'; 79 newformat[j++] = 'f'; 80 #endif 81 break; 82 default: 83 newformat[j++] = format[i]; 84 break; 85 } 86 i++; 87 } else newformat[j++] = format[i++]; 88 } 89 newformat[j] = 0; 90 PetscFunctionReturn(0); 91 } 92 93 #undef __FUNCT__ 94 #define __FUNCT__ "PetscVSNPrintf" 95 /*@C 96 PetscVSNPrintf - The PETSc version of vsnprintf(). Converts a PETSc format string into a standard C format string and then puts all the 97 function arguments into a string using the format statement. 98 99 Input Parameters: 100 + str - location to put result 101 . len - the amount of space in str 102 + format - the PETSc format string 103 - fullLength - the amount of space in str actually used. 104 105 Developer Notes: this function may be called from an error handler, if an error occurs when it is called by the error handler than likely 106 a recursion will occur and possible crash. 107 108 Level: developer 109 110 @*/ 111 PetscErrorCode PetscVSNPrintf(char *str,size_t len,const char *format,size_t *fullLength,va_list Argp) 112 { 113 char *newformat; 114 char formatbuf[8*1024]; 115 size_t oldLength,length; 116 int fullLengthInt; 117 PetscErrorCode ierr; 118 119 PetscFunctionBegin; 120 ierr = PetscStrlen(format, &oldLength);CHKERRQ(ierr); 121 if (oldLength < 8*1024) { 122 newformat = formatbuf; 123 oldLength = 8*1024-1; 124 } else { 125 oldLength = PETSC_MAX_LENGTH_FORMAT(oldLength); 126 ierr = PetscMalloc(oldLength * sizeof(char), &newformat);CHKERRQ(ierr); 127 } 128 PetscFormatConvert(format,newformat,oldLength); 129 ierr = PetscStrlen(newformat, &length);CHKERRQ(ierr); 130 #if 0 131 if (length > len) newformat[len] = '\0'; 132 #endif 133 #if defined(PETSC_HAVE_VSNPRINTF_CHAR) 134 fullLengthInt = vsnprintf(str,len,newformat,(char*)Argp); 135 #elif defined(PETSC_HAVE_VSNPRINTF) 136 fullLengthInt = vsnprintf(str,len,newformat,Argp); 137 #elif defined(PETSC_HAVE__VSNPRINTF) 138 fullLengthInt = _vsnprintf(str,len,newformat,Argp); 139 #else 140 #error "vsnprintf not found" 141 #endif 142 if (fullLengthInt < 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"vsnprintf() failed"); 143 if (fullLength) *fullLength = (size_t)fullLengthInt; 144 if (oldLength >= 8*1024) { 145 ierr = PetscFree(newformat);CHKERRQ(ierr); 146 } 147 PetscFunctionReturn(0); 148 } 149 150 #undef __FUNCT__ 151 #define __FUNCT__ "PetscVFPrintfDefault" 152 /*@C 153 PetscVFPrintf - All PETSc standard out and error messages are sent through this function; so, in theory, this can 154 can be replaced with something that does not simply write to a file. 155 156 To use, write your own function for example, 157 $PetscErrorCode mypetscvfprintf(FILE *fd,const char format[],va_list Argp) 158 ${ 159 $ PetscErrorCode ierr; 160 $ 161 $ PetscFunctionBegin; 162 $ if (fd != stdout && fd != stderr) { handle regular files 163 $ ierr = PetscVFPrintfDefault(fd,format,Argp);CHKERR(ierr); 164 $ } else { 165 $ char buff[BIG]; 166 $ size_t length; 167 $ ierr = PetscVSNPrintf(buff,BIG,format,&length,Argp);CHKERRQ(ierr); 168 $ now send buff to whatever stream or whatever you want 169 $ } 170 $ PetscFunctionReturn(0); 171 $} 172 then before the call to PetscInitialize() do the assignment 173 $ PetscVFPrintf = mypetscvfprintf; 174 175 Notes: For error messages this may be called by any process, for regular standard out it is 176 called only by process 0 of a given communicator 177 178 Developer Notes: this could be called by an error handler, if that happens then a recursion of the error handler may occur 179 and a crash 180 181 Level: developer 182 183 .seealso: PetscVSNPrintf(), PetscErrorPrintf() 184 185 @*/ 186 PetscErrorCode PetscVFPrintfDefault(FILE *fd,const char *format,va_list Argp) 187 { 188 char *newformat; 189 char formatbuf[8*1024]; 190 size_t oldLength; 191 PetscErrorCode ierr; 192 193 PetscFunctionBegin; 194 ierr = PetscStrlen(format, &oldLength);CHKERRQ(ierr); 195 if (oldLength < 8*1024) { 196 newformat = formatbuf; 197 oldLength = 8*1024-1; 198 } else { 199 oldLength = PETSC_MAX_LENGTH_FORMAT(oldLength); 200 ierr = PetscMalloc(oldLength * sizeof(char), &newformat);CHKERRQ(ierr); 201 } 202 ierr = PetscFormatConvert(format,newformat,oldLength);CHKERRQ(ierr); 203 204 #if defined(PETSC_HAVE_VFPRINTF_CHAR) 205 vfprintf(fd,newformat,(char*)Argp); 206 #else 207 vfprintf(fd,newformat,Argp); 208 #endif 209 fflush(fd); 210 if (oldLength >= 8*1024) { 211 ierr = PetscFree(newformat);CHKERRQ(ierr); 212 } 213 PetscFunctionReturn(0); 214 } 215 216 #undef __FUNCT__ 217 #define __FUNCT__ "PetscSNPrintf" 218 /*@C 219 PetscSNPrintf - Prints to a string of given length 220 221 Not Collective 222 223 Input Parameters: 224 + str - the string to print to 225 . len - the length of str 226 . format - the usual printf() format string 227 - any arguments 228 229 Level: intermediate 230 231 .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), PetscVSNPrintf(), 232 PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf() 233 @*/ 234 PetscErrorCode PetscSNPrintf(char *str,size_t len,const char format[],...) 235 { 236 PetscErrorCode ierr; 237 size_t fullLength; 238 va_list Argp; 239 240 PetscFunctionBegin; 241 va_start(Argp,format); 242 ierr = PetscVSNPrintf(str,len,format,&fullLength,Argp);CHKERRQ(ierr); 243 PetscFunctionReturn(0); 244 } 245 246 #undef __FUNCT__ 247 #define __FUNCT__ "PetscSNPrintfCount" 248 /*@C 249 PetscSNPrintfCount - Prints to a string of given length, returns count 250 251 Not Collective 252 253 Input Parameters: 254 + str - the string to print to 255 . len - the length of str 256 . format - the usual printf() format string 257 . countused - number of characters used 258 - any arguments 259 260 Level: intermediate 261 262 .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), PetscVSNPrintf(), 263 PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf(), PetscSNPrintf() 264 @*/ 265 PetscErrorCode PetscSNPrintfCount(char *str,size_t len,const char format[],size_t *countused,...) 266 { 267 PetscErrorCode ierr; 268 va_list Argp; 269 270 PetscFunctionBegin; 271 va_start(Argp,countused); 272 ierr = PetscVSNPrintf(str,len,format,countused,Argp);CHKERRQ(ierr); 273 PetscFunctionReturn(0); 274 } 275 276 /* ----------------------------------------------------------------------- */ 277 278 PrintfQueue petsc_printfqueue = 0,petsc_printfqueuebase = 0; 279 int petsc_printfqueuelength = 0; 280 281 #undef __FUNCT__ 282 #define __FUNCT__ "PetscSynchronizedPrintf" 283 /*@C 284 PetscSynchronizedPrintf - Prints synchronized output from several processors. 285 Output of the first processor is followed by that of the second, etc. 286 287 Not Collective 288 289 Input Parameters: 290 + comm - the communicator 291 - format - the usual printf() format string 292 293 Level: intermediate 294 295 Notes: 296 REQUIRES a intervening call to PetscSynchronizedFlush() for the information 297 from all the processors to be printed. 298 299 Fortran Note: 300 The call sequence is PetscSynchronizedPrintf(MPI_Comm, character(*), PetscErrorCode ierr) from Fortran. 301 That is, you can only pass a single character string from Fortran. 302 303 .seealso: PetscSynchronizedFlush(), PetscSynchronizedFPrintf(), PetscFPrintf(), 304 PetscPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf() 305 @*/ 306 PetscErrorCode PetscSynchronizedPrintf(MPI_Comm comm,const char format[],...) 307 { 308 PetscErrorCode ierr; 309 PetscMPIInt rank; 310 311 PetscFunctionBegin; 312 if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); 313 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 314 315 /* First processor prints immediately to stdout */ 316 if (!rank) { 317 va_list Argp; 318 va_start(Argp,format); 319 ierr = (*PetscVFPrintf)(PETSC_STDOUT,format,Argp);CHKERRQ(ierr); 320 if (petsc_history) { 321 va_start(Argp,format); 322 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 323 } 324 va_end(Argp); 325 } else { /* other processors add to local queue */ 326 va_list Argp; 327 PrintfQueue next; 328 size_t fullLength = 8191; 329 330 ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); 331 if (petsc_printfqueue) { 332 petsc_printfqueue->next = next; 333 petsc_printfqueue = next; 334 petsc_printfqueue->next = 0; 335 } else petsc_printfqueuebase = petsc_printfqueue = next; 336 petsc_printfqueuelength++; 337 next->size = -1; 338 while ((PetscInt)fullLength >= next->size) { 339 next->size = fullLength+1; 340 341 ierr = PetscMalloc(next->size * sizeof(char), &next->string);CHKERRQ(ierr); 342 va_start(Argp,format); 343 ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); 344 ierr = PetscVSNPrintf(next->string,next->size,format, &fullLength,Argp);CHKERRQ(ierr); 345 va_end(Argp); 346 } 347 } 348 PetscFunctionReturn(0); 349 } 350 351 #undef __FUNCT__ 352 #define __FUNCT__ "PetscSynchronizedFPrintf" 353 /*@C 354 PetscSynchronizedFPrintf - Prints synchronized output to the specified file from 355 several processors. Output of the first processor is followed by that of the 356 second, etc. 357 358 Not Collective 359 360 Input Parameters: 361 + comm - the communicator 362 . fd - the file pointer 363 - format - the usual printf() format string 364 365 Level: intermediate 366 367 Notes: 368 REQUIRES a intervening call to PetscSynchronizedFlush() for the information 369 from all the processors to be printed. 370 371 .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), 372 PetscFOpen(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIPrintf() 373 374 @*/ 375 PetscErrorCode PetscSynchronizedFPrintf(MPI_Comm comm,FILE *fp,const char format[],...) 376 { 377 PetscErrorCode ierr; 378 PetscMPIInt rank; 379 380 PetscFunctionBegin; 381 if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); 382 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 383 384 /* First processor prints immediately to fp */ 385 if (!rank) { 386 va_list Argp; 387 va_start(Argp,format); 388 ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); 389 if (petsc_history && (fp !=petsc_history)) { 390 va_start(Argp,format); 391 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 392 } 393 va_end(Argp); 394 } else { /* other processors add to local queue */ 395 va_list Argp; 396 PrintfQueue next; 397 size_t fullLength = 8191; 398 ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); 399 if (petsc_printfqueue) { 400 petsc_printfqueue->next = next; 401 petsc_printfqueue = next; 402 petsc_printfqueue->next = 0; 403 } else petsc_printfqueuebase = petsc_printfqueue = next; 404 petsc_printfqueuelength++; 405 next->size = -1; 406 while ((PetscInt)fullLength >= next->size) { 407 next->size = fullLength+1; 408 ierr = PetscMalloc(next->size * sizeof(char), &next->string);CHKERRQ(ierr); 409 va_start(Argp,format); 410 ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); 411 ierr = PetscVSNPrintf(next->string,next->size,format,&fullLength,Argp);CHKERRQ(ierr); 412 va_end(Argp); 413 } 414 } 415 PetscFunctionReturn(0); 416 } 417 418 #undef __FUNCT__ 419 #define __FUNCT__ "PetscSynchronizedFlush" 420 /*@C 421 PetscSynchronizedFlush - Flushes to the screen output from all processors 422 involved in previous PetscSynchronizedPrintf() calls. 423 424 Collective on MPI_Comm 425 426 Input Parameters: 427 + comm - the communicator 428 - fd - the file pointer (valid on process 0 of the communicator) 429 430 Level: intermediate 431 432 Notes: 433 Usage of PetscSynchronizedPrintf() and PetscSynchronizedFPrintf() with 434 different MPI communicators REQUIRES an intervening call to PetscSynchronizedFlush(). 435 436 .seealso: PetscSynchronizedPrintf(), PetscFPrintf(), PetscPrintf(), PetscViewerASCIIPrintf(), 437 PetscViewerASCIISynchronizedPrintf() 438 C@*/ 439 PetscErrorCode PetscSynchronizedFlush(MPI_Comm comm,FILE *fd) 440 { 441 PetscErrorCode ierr; 442 PetscMPIInt rank,size,tag,i,j,n = 0,dummy = 0; 443 char *message; 444 MPI_Status status; 445 446 PetscFunctionBegin; 447 ierr = PetscCommDuplicate(comm,&comm,&tag);CHKERRQ(ierr); 448 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 449 ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr); 450 451 /* First processor waits for messages from all other processors */ 452 if (!rank) { 453 if (!fd) fd = PETSC_STDOUT; 454 for (i=1; i<size; i++) { 455 /* to prevent a flood of messages to process zero, request each message separately */ 456 ierr = MPI_Send(&dummy,1,MPI_INT,i,tag,comm);CHKERRQ(ierr); 457 ierr = MPI_Recv(&n,1,MPI_INT,i,tag,comm,&status);CHKERRQ(ierr); 458 for (j=0; j<n; j++) { 459 PetscMPIInt size = 0; 460 461 ierr = MPI_Recv(&size,1,MPI_INT,i,tag,comm,&status);CHKERRQ(ierr); 462 ierr = PetscMalloc(size * sizeof(char), &message);CHKERRQ(ierr); 463 ierr = MPI_Recv(message,size,MPI_CHAR,i,tag,comm,&status);CHKERRQ(ierr); 464 ierr = PetscFPrintf(comm,fd,"%s",message);CHKERRQ(ierr); 465 ierr = PetscFree(message);CHKERRQ(ierr); 466 } 467 } 468 } else { /* other processors send queue to processor 0 */ 469 PrintfQueue next = petsc_printfqueuebase,previous; 470 471 ierr = MPI_Recv(&dummy,1,MPI_INT,0,tag,comm,&status);CHKERRQ(ierr); 472 ierr = MPI_Send(&petsc_printfqueuelength,1,MPI_INT,0,tag,comm);CHKERRQ(ierr); 473 for (i=0; i<petsc_printfqueuelength; i++) { 474 ierr = MPI_Send(&next->size,1,MPI_INT,0,tag,comm);CHKERRQ(ierr); 475 ierr = MPI_Send(next->string,next->size,MPI_CHAR,0,tag,comm);CHKERRQ(ierr); 476 previous = next; 477 next = next->next; 478 ierr = PetscFree(previous->string);CHKERRQ(ierr); 479 ierr = PetscFree(previous);CHKERRQ(ierr); 480 } 481 petsc_printfqueue = 0; 482 petsc_printfqueuelength = 0; 483 } 484 ierr = PetscCommDestroy(&comm);CHKERRQ(ierr); 485 PetscFunctionReturn(0); 486 } 487 488 /* ---------------------------------------------------------------------------------------*/ 489 490 #undef __FUNCT__ 491 #define __FUNCT__ "PetscFPrintf" 492 /*@C 493 PetscFPrintf - Prints to a file, only from the first 494 processor in the communicator. 495 496 Not Collective 497 498 Input Parameters: 499 + comm - the communicator 500 . fd - the file pointer 501 - format - the usual printf() format string 502 503 Level: intermediate 504 505 Fortran Note: 506 This routine is not supported in Fortran. 507 508 Concepts: printing^in parallel 509 Concepts: printf^in parallel 510 511 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 512 PetscViewerASCIISynchronizedPrintf(), PetscSynchronizedFlush() 513 @*/ 514 PetscErrorCode PetscFPrintf(MPI_Comm comm,FILE* fd,const char format[],...) 515 { 516 PetscErrorCode ierr; 517 PetscMPIInt rank; 518 519 PetscFunctionBegin; 520 if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); 521 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 522 if (!rank) { 523 va_list Argp; 524 va_start(Argp,format); 525 ierr = (*PetscVFPrintf)(fd,format,Argp);CHKERRQ(ierr); 526 if (petsc_history && (fd !=petsc_history)) { 527 va_start(Argp,format); 528 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 529 } 530 va_end(Argp); 531 } 532 PetscFunctionReturn(0); 533 } 534 535 #undef __FUNCT__ 536 #define __FUNCT__ "PetscPrintf" 537 /*@C 538 PetscPrintf - Prints to standard out, only from the first 539 processor in the communicator. Calls from other processes are ignored. 540 541 Not Collective 542 543 Input Parameters: 544 + comm - the communicator 545 - format - the usual printf() format string 546 547 Level: intermediate 548 549 Fortran Note: 550 The call sequence is PetscPrintf(MPI_Comm, character(*), PetscErrorCode ierr) from Fortran. 551 That is, you can only pass a single character string from Fortran. 552 553 Concepts: printing^in parallel 554 Concepts: printf^in parallel 555 556 .seealso: PetscFPrintf(), PetscSynchronizedPrintf() 557 @*/ 558 PetscErrorCode PetscPrintf(MPI_Comm comm,const char format[],...) 559 { 560 PetscErrorCode ierr; 561 PetscMPIInt rank; 562 563 PetscFunctionBegin; 564 if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); 565 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 566 if (!rank) { 567 va_list Argp; 568 va_start(Argp,format); 569 ierr = (*PetscVFPrintf)(PETSC_STDOUT,format,Argp);CHKERRQ(ierr); 570 if (petsc_history) { 571 va_start(Argp,format); 572 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 573 } 574 va_end(Argp); 575 } 576 PetscFunctionReturn(0); 577 } 578 579 /* ---------------------------------------------------------------------------------------*/ 580 #undef __FUNCT__ 581 #define __FUNCT__ "PetscHelpPrintfDefault" 582 /*@C 583 PetscHelpPrintf - All PETSc help messages are passing through this function. You can change how help messages are printed by 584 replacinng it with something that does not simply write to a stdout. 585 586 To use, write your own function for example, 587 $PetscErrorCode mypetschelpprintf(MPI_Comm comm,const char format[],....) 588 ${ 589 $ PetscFunctionReturn(0); 590 $} 591 then before the call to PetscInitialize() do the assignment 592 $ PetscHelpPrintf = mypetschelpprintf; 593 594 Note: the default routine used is called PetscHelpPrintfDefault(). 595 596 Level: developer 597 598 .seealso: PetscVSNPrintf(), PetscVFPrintf(), PetscErrorPrintf() 599 @*/ 600 PetscErrorCode PetscHelpPrintfDefault(MPI_Comm comm,const char format[],...) 601 { 602 PetscErrorCode ierr; 603 PetscMPIInt rank; 604 605 PetscFunctionBegin; 606 if (comm == MPI_COMM_NULL) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Called with MPI_COMM_NULL, likely PetscObjectComm() failed"); 607 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 608 if (!rank) { 609 va_list Argp; 610 va_start(Argp,format); 611 ierr = (*PetscVFPrintf)(PETSC_STDOUT,format,Argp);CHKERRQ(ierr); 612 if (petsc_history) { 613 va_start(Argp,format); 614 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 615 } 616 va_end(Argp); 617 } 618 PetscFunctionReturn(0); 619 } 620 621 /* ---------------------------------------------------------------------------------------*/ 622 623 624 #undef __FUNCT__ 625 #define __FUNCT__ "PetscSynchronizedFGets" 626 /*@C 627 PetscSynchronizedFGets - Several processors all get the same line from a file. 628 629 Collective on MPI_Comm 630 631 Input Parameters: 632 + comm - the communicator 633 . fd - the file pointer 634 - len - the length of the output buffer 635 636 Output Parameter: 637 . string - the line read from the file, at end of file string[0] == 0 638 639 Level: intermediate 640 641 .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), 642 PetscFOpen(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIPrintf() 643 644 @*/ 645 PetscErrorCode PetscSynchronizedFGets(MPI_Comm comm,FILE *fp,size_t len,char string[]) 646 { 647 PetscErrorCode ierr; 648 PetscMPIInt rank; 649 650 PetscFunctionBegin; 651 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 652 653 if (!rank) { 654 char *ptr = fgets(string, len, fp); 655 656 if (!ptr) { 657 string[0] = 0; 658 if (!feof(fp)) SETERRQ1(PETSC_COMM_SELF, PETSC_ERR_FILE_READ, "Error reading from file: %d", errno); 659 } 660 } 661 ierr = MPI_Bcast(string,len,MPI_BYTE,0,comm);CHKERRQ(ierr); 662 PetscFunctionReturn(0); 663 } 664 665 #if defined(PETSC_HAVE_MATLAB_ENGINE) 666 #include <mex.h> 667 #undef __FUNCT__ 668 #define __FUNCT__ "PetscVFPrintf_Matlab" 669 PetscErrorCode PetscVFPrintf_Matlab(FILE *fd,const char format[],va_list Argp) 670 { 671 PetscErrorCode ierr; 672 673 PetscFunctionBegin; 674 if (fd != stdout && fd != stderr) { /* handle regular files */ 675 ierr = PetscVFPrintfDefault(fd,format,Argp);CHKERRQ(ierr); 676 } else { 677 size_t len=8*1024,length; 678 char buf[len]; 679 680 ierr = PetscVSNPrintf(buf,len,format,&length,Argp);CHKERRQ(ierr); 681 mexPrintf("%s",buf); 682 } 683 PetscFunctionReturn(0); 684 } 685 #endif 686 687 #undef __FUNCT__ 688 #define __FUNCT__ "PetscFormatStrip" 689 /*@C 690 PetscFormatStrip - Takes a PETSc format string and removes all numerical modifiers to % operations 691 692 Input Parameters: 693 . format - the PETSc format string 694 695 Level: developer 696 697 @*/ 698 PetscErrorCode PetscFormatStrip(char *format) 699 { 700 size_t loc1 = 0, loc2 = 0; 701 702 PetscFunctionBegin; 703 while (format[loc2]) { 704 if (format[loc2] == '%') { 705 format[loc1++] = format[loc2++]; 706 while (format[loc2] && ((format[loc2] >= '0' && format[loc2] <= '9') || format[loc2] == '.')) loc2++; 707 } 708 format[loc1++] = format[loc2++]; 709 } 710 PetscFunctionReturn(0); 711 } 712 713