1 2 #include <../src/sys/classes/viewer/impls/ascii/asciiimpl.h> /*I "petscsys.h" I*/ 3 #include <stdarg.h> 4 5 #define QUEUESTRINGSIZE 8192 6 7 #undef __FUNCT__ 8 #define __FUNCT__ "PetscViewerFileClose_ASCII" 9 static PetscErrorCode PetscViewerFileClose_ASCII(PetscViewer viewer) 10 { 11 PetscErrorCode ierr; 12 PetscMPIInt rank; 13 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 14 int err; 15 16 PetscFunctionBegin; 17 ierr = MPI_Comm_rank(((PetscObject)viewer)->comm,&rank);CHKERRQ(ierr); 18 if (!rank && vascii->fd != stderr && vascii->fd != PETSC_STDOUT) { 19 if (vascii->fd && vascii->closefile) { 20 err = fclose(vascii->fd); 21 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fclose() failed on file"); 22 } 23 if (vascii->storecompressed) { 24 char par[PETSC_MAX_PATH_LEN],buf[PETSC_MAX_PATH_LEN]; 25 FILE *fp; 26 ierr = PetscStrcpy(par,"gzip ");CHKERRQ(ierr); 27 ierr = PetscStrcat(par,vascii->filename);CHKERRQ(ierr); 28 #if defined(PETSC_HAVE_POPEN) 29 ierr = PetscPOpen(PETSC_COMM_SELF,PETSC_NULL,par,"r",&fp);CHKERRQ(ierr); 30 if (fgets(buf,1024,fp)) { 31 SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_LIB,"Error from compression command %s\n%s",par,buf); 32 } 33 ierr = PetscPClose(PETSC_COMM_SELF,fp,PETSC_NULL);CHKERRQ(ierr); 34 #else 35 SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP_SYS,"Cannot run external programs on this machine"); 36 #endif 37 } 38 } 39 ierr = PetscFree(vascii->filename);CHKERRQ(ierr); 40 PetscFunctionReturn(0); 41 } 42 43 /* ----------------------------------------------------------------------*/ 44 #undef __FUNCT__ 45 #define __FUNCT__ "PetscViewerDestroy_ASCII" 46 PetscErrorCode PetscViewerDestroy_ASCII(PetscViewer viewer) 47 { 48 PetscErrorCode ierr; 49 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 50 PetscViewerLink *vlink; 51 PetscBool flg; 52 53 PetscFunctionBegin; 54 if (vascii->sviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"ASCII PetscViewer destroyed before restoring singleton or subcomm PetscViewer"); 55 ierr = PetscViewerFileClose_ASCII(viewer);CHKERRQ(ierr); 56 ierr = PetscFree(vascii);CHKERRQ(ierr); 57 58 /* remove the viewer from the list in the MPI Communicator */ 59 if (Petsc_Viewer_keyval == MPI_KEYVAL_INVALID) { 60 ierr = MPI_Keyval_create(MPI_NULL_COPY_FN,Petsc_DelViewer,&Petsc_Viewer_keyval,(void*)0);CHKERRQ(ierr); 61 } 62 63 ierr = MPI_Attr_get(((PetscObject)viewer)->comm,Petsc_Viewer_keyval,(void**)&vlink,(PetscMPIInt*)&flg);CHKERRQ(ierr); 64 if (flg) { 65 if (vlink && vlink->viewer == viewer) { 66 ierr = MPI_Attr_put(((PetscObject)viewer)->comm,Petsc_Viewer_keyval,vlink->next);CHKERRQ(ierr); 67 ierr = PetscFree(vlink);CHKERRQ(ierr); 68 } else { 69 while (vlink && vlink->next) { 70 if (vlink->next->viewer == viewer) { 71 PetscViewerLink *nv = vlink->next; 72 vlink->next = vlink->next->next; 73 ierr = PetscFree(nv);CHKERRQ(ierr); 74 } 75 vlink = vlink->next; 76 } 77 } 78 } 79 PetscFunctionReturn(0); 80 } 81 82 #undef __FUNCT__ 83 #define __FUNCT__ "PetscViewerDestroy_ASCII_Singleton" 84 PetscErrorCode PetscViewerDestroy_ASCII_Singleton(PetscViewer viewer) 85 { 86 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 87 PetscErrorCode ierr; 88 PetscFunctionBegin; 89 ierr = PetscViewerRestoreSingleton(vascii->bviewer,&viewer);CHKERRQ(ierr); 90 PetscFunctionReturn(0); 91 } 92 93 #undef __FUNCT__ 94 #define __FUNCT__ "PetscViewerDestroy_ASCII_Subcomm" 95 PetscErrorCode PetscViewerDestroy_ASCII_Subcomm(PetscViewer viewer) 96 { 97 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 98 PetscErrorCode ierr; 99 PetscFunctionBegin; 100 ierr = PetscViewerRestoreSubcomm(vascii->bviewer,((PetscObject)viewer)->comm,&viewer);CHKERRQ(ierr); 101 PetscFunctionReturn(0); 102 } 103 104 #undef __FUNCT__ 105 #define __FUNCT__ "PetscViewerFlush_ASCII_Singleton_0" 106 PetscErrorCode PetscViewerFlush_ASCII_Singleton_0(PetscViewer viewer) 107 { 108 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 109 int err; 110 111 PetscFunctionBegin; 112 err = fflush(vascii->fd); 113 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 114 PetscFunctionReturn(0); 115 } 116 117 #undef __FUNCT__ 118 #define __FUNCT__ "PetscViewerFlush_ASCII" 119 PetscErrorCode PetscViewerFlush_ASCII(PetscViewer viewer) 120 { 121 PetscMPIInt rank; 122 PetscErrorCode ierr; 123 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 124 int err; 125 126 PetscFunctionBegin; 127 ierr = MPI_Comm_rank(((PetscObject)viewer)->comm,&rank);CHKERRQ(ierr); 128 /* fflush() fails on OSX for read-only descriptors */ 129 if (!rank && (vascii->mode != FILE_MODE_READ)) { 130 err = fflush(vascii->fd); 131 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() call failed"); 132 } 133 134 if (vascii->allowsynchronized) { 135 /* Also flush anything printed with PetscViewerASCIISynchronizedPrintf() */ 136 ierr = PetscSynchronizedFlush(((PetscObject)viewer)->comm);CHKERRQ(ierr); 137 } 138 PetscFunctionReturn(0); 139 } 140 141 #undef __FUNCT__ 142 #define __FUNCT__ "PetscViewerASCIIGetPointer" 143 /*@C 144 PetscViewerASCIIGetPointer - Extracts the file pointer from an ASCII PetscViewer. 145 146 Not Collective 147 148 + viewer - PetscViewer context, obtained from PetscViewerASCIIOpen() 149 - fd - file pointer 150 151 Level: intermediate 152 153 Fortran Note: 154 This routine is not supported in Fortran. 155 156 Concepts: PetscViewer^file pointer 157 Concepts: file pointer^getting from PetscViewer 158 159 .seealso: PetscViewerASCIIOpen(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerCreate(), PetscViewerASCIIPrintf(), 160 PetscViewerASCIISynchronizedPrintf(), PetscViewerFlush() 161 @*/ 162 PetscErrorCode PetscViewerASCIIGetPointer(PetscViewer viewer,FILE **fd) 163 { 164 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 165 166 PetscFunctionBegin; 167 *fd = vascii->fd; 168 PetscFunctionReturn(0); 169 } 170 171 EXTERN_C_BEGIN 172 #undef __FUNCT__ 173 #define __FUNCT__ "PetscViewerFileGetMode_ASCII" 174 PetscErrorCode PetscViewerFileGetMode_ASCII(PetscViewer viewer, PetscFileMode *mode) 175 { 176 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 177 178 PetscFunctionBegin; 179 *mode = vascii->mode; 180 PetscFunctionReturn(0); 181 } 182 EXTERN_C_END 183 184 /*@C 185 PetscViewerFileSetMode - Sets the mode in which to open the file. 186 187 Not Collective 188 189 + viewer - viewer context, obtained from PetscViewerCreate() 190 - mode - The file mode 191 192 Level: intermediate 193 194 Fortran Note: 195 This routine is not supported in Fortran. 196 197 .keywords: Viewer, file, get, pointer 198 199 .seealso: PetscViewerASCIIOpen(), PetscViewerBinaryOpen() 200 @*/ 201 202 EXTERN_C_BEGIN 203 #undef __FUNCT__ 204 #define __FUNCT__ "PetscViewerFileSetMode_ASCII" 205 PetscErrorCode PetscViewerFileSetMode_ASCII(PetscViewer viewer, PetscFileMode mode) 206 { 207 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 208 209 PetscFunctionBegin; 210 vascii->mode = mode; 211 PetscFunctionReturn(0); 212 } 213 EXTERN_C_END 214 215 /* 216 If petsc_history is on, then all Petsc*Printf() results are saved 217 if the appropriate (usually .petschistory) file. 218 */ 219 extern FILE *petsc_history; 220 221 #undef __FUNCT__ 222 #define __FUNCT__ "PetscViewerASCIISetTab" 223 /*@ 224 PetscViewerASCIISetTab - Causes PetscViewer to tab in a number of times 225 226 Not Collective, but only first processor in set has any effect 227 228 Input Parameters: 229 + viewer - optained with PetscViewerASCIIOpen() 230 - tabs - number of tabs 231 232 Level: developer 233 234 Fortran Note: 235 This routine is not supported in Fortran. 236 237 Concepts: PetscViewerASCII^formating 238 Concepts: tab^setting 239 240 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIIGetTab(), 241 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 242 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushTab() 243 @*/ 244 PetscErrorCode PetscViewerASCIISetTab(PetscViewer viewer,PetscInt tabs) 245 { 246 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 247 PetscBool iascii; 248 PetscErrorCode ierr; 249 250 PetscFunctionBegin; 251 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 252 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 253 if (iascii) { 254 ascii->tab = tabs; 255 } 256 PetscFunctionReturn(0); 257 } 258 259 #undef __FUNCT__ 260 #define __FUNCT__ "PetscViewerASCIIGetTab" 261 /*@ 262 PetscViewerASCIIGetTab - Return the number of tabs used by PetscViewer. 263 264 Not Collective, meaningful on first processor only. 265 266 Input Parameters: 267 . viewer - optained with PetscViewerASCIIOpen() 268 Output Parameters: 269 . tabs - number of tabs 270 271 Level: developer 272 273 Fortran Note: 274 This routine is not supported in Fortran. 275 276 Concepts: PetscViewerASCII^formating 277 Concepts: tab^retrieval 278 279 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), PetscViewerASCIISetTab(), 280 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 281 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushTab() 282 @*/ 283 PetscErrorCode PetscViewerASCIIGetTab(PetscViewer viewer,PetscInt *tabs) 284 { 285 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 286 PetscBool iascii; 287 PetscErrorCode ierr; 288 289 PetscFunctionBegin; 290 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 291 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 292 if (iascii && tabs) { 293 *tabs = ascii->tab; 294 } 295 PetscFunctionReturn(0); 296 } 297 298 #undef __FUNCT__ 299 #define __FUNCT__ "PetscViewerASCIIAddTab" 300 /*@ 301 PetscViewerASCIIAddTab - Add to the number of times an ASCII viewer tabs before printing 302 303 Not Collective, but only first processor in set has any effect 304 305 Input Parameters: 306 + viewer - optained with PetscViewerASCIIOpen() 307 - tabs - number of tabs 308 309 Level: developer 310 311 Fortran Note: 312 This routine is not supported in Fortran. 313 314 Concepts: PetscViewerASCII^formating 315 Concepts: tab^setting 316 317 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 318 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 319 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushTab() 320 @*/ 321 PetscErrorCode PetscViewerASCIIAddTab(PetscViewer viewer,PetscInt tabs) 322 { 323 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 324 PetscBool iascii; 325 PetscErrorCode ierr; 326 327 PetscFunctionBegin; 328 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 329 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 330 if (iascii) { 331 ascii->tab += tabs; 332 } 333 PetscFunctionReturn(0); 334 } 335 336 #undef __FUNCT__ 337 #define __FUNCT__ "PetscViewerASCIISubtractTab" 338 /*@ 339 PetscViewerASCIISubtractTab - Subtracts from the number of times an ASCII viewer tabs before printing 340 341 Not Collective, but only first processor in set has any effect 342 343 Input Parameters: 344 + viewer - optained with PetscViewerASCIIOpen() 345 - tabs - number of tabs 346 347 Level: developer 348 349 Fortran Note: 350 This routine is not supported in Fortran. 351 352 Concepts: PetscViewerASCII^formating 353 Concepts: tab^setting 354 355 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 356 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 357 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIIPushTab() 358 @*/ 359 PetscErrorCode PetscViewerASCIISubtractTab(PetscViewer viewer,PetscInt tabs) 360 { 361 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 362 PetscBool iascii; 363 PetscErrorCode ierr; 364 365 PetscFunctionBegin; 366 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 367 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 368 if (iascii) { 369 ascii->tab -= tabs; 370 } 371 PetscFunctionReturn(0); 372 } 373 374 #undef __FUNCT__ 375 #define __FUNCT__ "PetscViewerASCIISynchronizedAllow" 376 /*@C 377 PetscViewerASCIISynchronizedAllow - Allows calls to PetscViewerASCIISynchronizedPrintf() for this viewer 378 379 Collective on PetscViewer 380 381 Input Parameters: 382 + viewer - optained with PetscViewerASCIIOpen() 383 - allow - PETSC_TRUE to allow the synchronized printing 384 385 Level: intermediate 386 387 Concepts: PetscViewerASCII^formating 388 Concepts: tab^setting 389 390 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 391 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 392 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer() 393 @*/ 394 PetscErrorCode PetscViewerASCIISynchronizedAllow(PetscViewer viewer,PetscBool allow) 395 { 396 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 397 PetscBool iascii; 398 PetscErrorCode ierr; 399 400 PetscFunctionBegin; 401 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 402 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 403 if (iascii) { 404 ascii->allowsynchronized = allow; 405 } 406 PetscFunctionReturn(0); 407 } 408 409 #undef __FUNCT__ 410 #define __FUNCT__ "PetscViewerASCIIPushTab" 411 /*@ 412 PetscViewerASCIIPushTab - Adds one more tab to the amount that PetscViewerASCIIPrintf() 413 lines are tabbed. 414 415 Not Collective, but only first processor in set has any effect 416 417 Input Parameters: 418 . viewer - optained with PetscViewerASCIIOpen() 419 420 Level: developer 421 422 Fortran Note: 423 This routine is not supported in Fortran. 424 425 Concepts: PetscViewerASCII^formating 426 Concepts: tab^setting 427 428 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 429 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 430 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer() 431 @*/ 432 PetscErrorCode PetscViewerASCIIPushTab(PetscViewer viewer) 433 { 434 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 435 PetscBool iascii; 436 PetscErrorCode ierr; 437 438 PetscFunctionBegin; 439 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 440 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 441 if (iascii) { 442 ascii->tab++; 443 } 444 PetscFunctionReturn(0); 445 } 446 447 #undef __FUNCT__ 448 #define __FUNCT__ "PetscViewerASCIIPopTab" 449 /*@ 450 PetscViewerASCIIPopTab - Removes one tab from the amount that PetscViewerASCIIPrintf() 451 lines are tabbed. 452 453 Not Collective, but only first processor in set has any effect 454 455 Input Parameters: 456 . viewer - optained with PetscViewerASCIIOpen() 457 458 Level: developer 459 460 Fortran Note: 461 This routine is not supported in Fortran. 462 463 Concepts: PetscViewerASCII^formating 464 Concepts: tab^setting 465 466 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 467 PetscViewerASCIIPushTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIOpen(), 468 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer() 469 @*/ 470 PetscErrorCode PetscViewerASCIIPopTab(PetscViewer viewer) 471 { 472 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 473 PetscErrorCode ierr; 474 PetscBool iascii; 475 476 PetscFunctionBegin; 477 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 478 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 479 if (iascii) { 480 if (ascii->tab <= 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"More tabs popped than pushed"); 481 ascii->tab--; 482 } 483 PetscFunctionReturn(0); 484 } 485 486 #undef __FUNCT__ 487 #define __FUNCT__ "PetscViewerASCIIUseTabs" 488 /*@ 489 PetscViewerASCIIUseTabs - Turns on or off the use of tabs with the ASCII PetscViewer 490 491 Not Collective, but only first processor in set has any effect 492 493 Input Parameters: 494 + viewer - optained with PetscViewerASCIIOpen() 495 - flg - PETSC_TRUE or PETSC_FALSE 496 497 Level: developer 498 499 Fortran Note: 500 This routine is not supported in Fortran. 501 502 Concepts: PetscViewerASCII^formating 503 Concepts: tab^setting 504 505 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIPrintf(), 506 PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), PetscViewerASCIIPushTab(), PetscViewerASCIIOpen(), 507 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer() 508 @*/ 509 PetscErrorCode PetscViewerASCIIUseTabs(PetscViewer viewer,PetscBool flg) 510 { 511 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 512 PetscBool iascii; 513 PetscErrorCode ierr; 514 515 PetscFunctionBegin; 516 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 517 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 518 if (iascii) { 519 if (flg) { 520 ascii->tab = ascii->tab_store; 521 } else { 522 ascii->tab_store = ascii->tab; 523 ascii->tab = 0; 524 } 525 } 526 PetscFunctionReturn(0); 527 } 528 529 /* ----------------------------------------------------------------------- */ 530 531 #include <../src/sys/fileio/mprint.h> /* defines the queue datastructures and variables */ 532 533 #undef __FUNCT__ 534 #define __FUNCT__ "PetscViewerASCIIPrintf" 535 /*@C 536 PetscViewerASCIIPrintf - Prints to a file, only from the first 537 processor in the PetscViewer 538 539 Not Collective, but only first processor in set has any effect 540 541 Input Parameters: 542 + viewer - optained with PetscViewerASCIIOpen() 543 - format - the usual printf() format string 544 545 Level: developer 546 547 Fortran Note: 548 The call sequence is PetscViewerASCIIPrintf(PetscViewer, character(*), int ierr) from Fortran. 549 That is, you can only pass a single character string from Fortran. 550 551 Concepts: PetscViewerASCII^printing 552 Concepts: printing^to file 553 Concepts: printf 554 555 .seealso: PetscPrintf(), PetscSynchronizedPrintf(), PetscViewerASCIIOpen(), 556 PetscViewerASCIIPushTab(), PetscViewerASCIIPopTab(), PetscViewerASCIISynchronizedPrintf(), 557 PetscViewerCreate(), PetscViewerDestroy(), PetscViewerSetType(), PetscViewerASCIIGetPointer(), PetscViewerASCIISynchronizedAllow() 558 @*/ 559 PetscErrorCode PetscViewerASCIIPrintf(PetscViewer viewer,const char format[],...) 560 { 561 PetscViewer_ASCII *ascii = (PetscViewer_ASCII*)viewer->data; 562 PetscMPIInt rank; 563 PetscInt tab; 564 PetscErrorCode ierr; 565 FILE *fd = ascii->fd; 566 PetscBool iascii; 567 int err; 568 569 PetscFunctionBegin; 570 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 571 PetscValidCharPointer(format,2); 572 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 573 if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); 574 575 ierr = MPI_Comm_rank(((PetscObject)viewer)->comm,&rank);CHKERRQ(ierr); 576 if (!rank) { 577 va_list Argp; 578 if (ascii->bviewer) { 579 petsc_printfqueuefile = fd; 580 } 581 582 tab = ascii->tab; 583 while (tab--) {ierr = PetscFPrintf(PETSC_COMM_SELF,fd," ");CHKERRQ(ierr);} 584 585 va_start(Argp,format); 586 ierr = (*PetscVFPrintf)(fd,format,Argp);CHKERRQ(ierr); 587 err = fflush(fd); 588 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 589 if (petsc_history) { 590 va_start(Argp,format); 591 tab = ascii->tab; 592 while (tab--) {ierr = PetscFPrintf(PETSC_COMM_SELF,fd," ");CHKERRQ(ierr);} 593 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 594 err = fflush(petsc_history); 595 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 596 } 597 va_end(Argp); 598 } 599 PetscFunctionReturn(0); 600 } 601 602 #undef __FUNCT__ 603 #define __FUNCT__ "PetscViewerFileSetName" 604 /*@C 605 PetscViewerFileSetName - Sets the name of the file the PetscViewer uses. 606 607 Collective on PetscViewer 608 609 Input Parameters: 610 + viewer - the PetscViewer; either ASCII or binary 611 - name - the name of the file it should use 612 613 Level: advanced 614 615 .seealso: PetscViewerCreate(), PetscViewerSetType(), PetscViewerASCIIOpen(), PetscViewerBinaryOpen(), PetscViewerDestroy(), 616 PetscViewerASCIIGetPointer(), PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedPrintf() 617 618 @*/ 619 PetscErrorCode PetscViewerFileSetName(PetscViewer viewer,const char name[]) 620 { 621 PetscErrorCode ierr; 622 623 PetscFunctionBegin; 624 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 625 PetscValidCharPointer(name,2); 626 ierr = PetscTryMethod(viewer,"PetscViewerFileSetName_C",(PetscViewer,const char[]),(viewer,name));CHKERRQ(ierr); 627 PetscFunctionReturn(0); 628 } 629 630 #undef __FUNCT__ 631 #define __FUNCT__ "PetscViewerFileGetName" 632 /*@C 633 PetscViewerFileGetName - Gets the name of the file the PetscViewer uses. 634 635 Not Collective 636 637 Input Parameter: 638 . viewer - the PetscViewer; either ASCII or binary 639 640 Output Parameter: 641 . name - the name of the file it is using 642 643 Level: advanced 644 645 .seealso: PetscViewerCreate(), PetscViewerSetType(), PetscViewerASCIIOpen(), PetscViewerBinaryOpen(), PetscViewerFileSetName() 646 647 @*/ 648 PetscErrorCode PetscViewerFileGetName(PetscViewer viewer,const char **name) 649 { 650 PetscErrorCode ierr; 651 652 PetscFunctionBegin; 653 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 654 ierr = PetscTryMethod(viewer,"PetscViewerFileGetName_C",(PetscViewer,const char **),(viewer,name));CHKERRQ(ierr); 655 PetscFunctionReturn(0); 656 } 657 658 EXTERN_C_BEGIN 659 #undef __FUNCT__ 660 #define __FUNCT__ "PetscViewerFileGetName_ASCII" 661 PetscErrorCode PetscViewerFileGetName_ASCII(PetscViewer viewer,const char **name) 662 { 663 PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data; 664 665 PetscFunctionBegin; 666 *name = vascii->filename; 667 PetscFunctionReturn(0); 668 } 669 EXTERN_C_END 670 671 672 EXTERN_C_BEGIN 673 #undef __FUNCT__ 674 #define __FUNCT__ "PetscViewerFileSetName_ASCII" 675 PetscErrorCode PetscViewerFileSetName_ASCII(PetscViewer viewer,const char name[]) 676 { 677 PetscErrorCode ierr; 678 size_t len; 679 char fname[PETSC_MAX_PATH_LEN],*gz; 680 PetscViewer_ASCII *vascii = (PetscViewer_ASCII*)viewer->data; 681 PetscBool isstderr,isstdout; 682 PetscMPIInt rank; 683 684 PetscFunctionBegin; 685 ierr = PetscViewerFileClose_ASCII(viewer);CHKERRQ(ierr); 686 if (!name) PetscFunctionReturn(0); 687 ierr = PetscStrallocpy(name,&vascii->filename);CHKERRQ(ierr); 688 689 /* Is this file to be compressed */ 690 vascii->storecompressed = PETSC_FALSE; 691 ierr = PetscStrstr(vascii->filename,".gz",&gz);CHKERRQ(ierr); 692 if (gz) { 693 ierr = PetscStrlen(gz,&len);CHKERRQ(ierr); 694 if (len == 3) { 695 *gz = 0; 696 vascii->storecompressed = PETSC_TRUE; 697 } 698 } 699 ierr = MPI_Comm_rank(((PetscObject)viewer)->comm,&rank);CHKERRQ(ierr); 700 if (!rank) { 701 ierr = PetscStrcmp(name,"stderr",&isstderr);CHKERRQ(ierr); 702 ierr = PetscStrcmp(name,"stdout",&isstdout);CHKERRQ(ierr); 703 /* empty filename means stdout */ 704 if (name[0] == 0) isstdout = PETSC_TRUE; 705 if (isstderr) vascii->fd = PETSC_STDERR; 706 else if (isstdout) vascii->fd = PETSC_STDOUT; 707 else { 708 709 710 ierr = PetscFixFilename(name,fname);CHKERRQ(ierr); 711 switch(vascii->mode) { 712 case FILE_MODE_READ: 713 vascii->fd = fopen(fname,"r"); 714 break; 715 case FILE_MODE_WRITE: 716 vascii->fd = fopen(fname,"w"); 717 break; 718 case FILE_MODE_APPEND: 719 vascii->fd = fopen(fname,"a"); 720 break; 721 case FILE_MODE_UPDATE: 722 vascii->fd = fopen(fname,"r+"); 723 if (!vascii->fd) { 724 vascii->fd = fopen(fname,"w+"); 725 } 726 break; 727 case FILE_MODE_APPEND_UPDATE: 728 /* I really want a file which is opened at the end for updating, 729 not a+, which opens at the beginning, but makes writes at the end. 730 */ 731 vascii->fd = fopen(fname,"r+"); 732 if (!vascii->fd) { 733 vascii->fd = fopen(fname,"w+"); 734 } else { 735 ierr = fseek(vascii->fd, 0, SEEK_END);CHKERRQ(ierr); 736 } 737 break; 738 default: 739 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Invalid file mode %d", vascii->mode); 740 } 741 if (!vascii->fd) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_FILE_OPEN,"Cannot open PetscViewer file: %s",fname); 742 } 743 } 744 #if defined(PETSC_USE_LOG) 745 PetscLogObjectState((PetscObject)viewer,"File: %s",name); 746 #endif 747 PetscFunctionReturn(0); 748 } 749 EXTERN_C_END 750 751 #undef __FUNCT__ 752 #define __FUNCT__ "PetscViewerGetSingleton_ASCII" 753 PetscErrorCode PetscViewerGetSingleton_ASCII(PetscViewer viewer,PetscViewer *outviewer) 754 { 755 PetscMPIInt rank; 756 PetscErrorCode ierr; 757 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data,*ovascii; 758 const char *name; 759 760 PetscFunctionBegin; 761 if (vascii->sviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Singleton already obtained from PetscViewer and not restored"); 762 ierr = PetscViewerCreate(PETSC_COMM_SELF,outviewer);CHKERRQ(ierr); 763 ierr = PetscViewerSetType(*outviewer,PETSCVIEWERASCII);CHKERRQ(ierr); 764 ovascii = (PetscViewer_ASCII*)(*outviewer)->data; 765 ovascii->fd = vascii->fd; 766 ovascii->tab = vascii->tab; 767 768 vascii->sviewer = *outviewer; 769 770 (*outviewer)->format = viewer->format; 771 (*outviewer)->iformat = viewer->iformat; 772 773 ierr = PetscObjectGetName((PetscObject)viewer,&name);CHKERRQ(ierr); 774 ierr = PetscObjectSetName((PetscObject)(*outviewer),name);CHKERRQ(ierr); 775 776 ierr = MPI_Comm_rank(((PetscObject)viewer)->comm,&rank);CHKERRQ(ierr); 777 ((PetscViewer_ASCII*)((*outviewer)->data))->bviewer = viewer; 778 (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII_Singleton; 779 if (rank) { 780 (*outviewer)->ops->flush = 0; 781 } else { 782 (*outviewer)->ops->flush = PetscViewerFlush_ASCII_Singleton_0; 783 } 784 PetscFunctionReturn(0); 785 } 786 787 #undef __FUNCT__ 788 #define __FUNCT__ "PetscViewerRestoreSingleton_ASCII" 789 PetscErrorCode PetscViewerRestoreSingleton_ASCII(PetscViewer viewer,PetscViewer *outviewer) 790 { 791 PetscErrorCode ierr; 792 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)(*outviewer)->data; 793 PetscViewer_ASCII *ascii = (PetscViewer_ASCII *)viewer->data; 794 795 PetscFunctionBegin; 796 if (!ascii->sviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Singleton never obtained from PetscViewer"); 797 if (ascii->sviewer != *outviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"This PetscViewer did not generate singleton"); 798 799 ascii->sviewer = 0; 800 vascii->fd = PETSC_STDOUT; 801 (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII; 802 ierr = PetscViewerDestroy(outviewer);CHKERRQ(ierr); 803 ierr = PetscViewerFlush(viewer);CHKERRQ(ierr); 804 PetscFunctionReturn(0); 805 } 806 807 #undef __FUNCT__ 808 #define __FUNCT__ "PetscViewerGetSubcomm_ASCII" 809 PetscErrorCode PetscViewerGetSubcomm_ASCII(PetscViewer viewer,MPI_Comm subcomm,PetscViewer *outviewer) 810 { 811 PetscErrorCode ierr; 812 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data,*ovascii; 813 const char *name; 814 815 PetscFunctionBegin; 816 if (vascii->sviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Subcomm viewer already obtained from PetscViewer and not restored"); 817 /* Note that we need to open vascii->filename for the subcomm: 818 we can't count on reusing viewer's fd since the root in comm and subcomm may differ. 819 Further, if the subcomm happens to be the same as comm, PetscViewerASCIIOpen() will 820 will return the current viewer, having increfed it. 821 */ 822 ierr = PetscViewerASCIIOpen(subcomm,vascii->filename, outviewer);CHKERRQ(ierr); 823 if (*outviewer == viewer) PetscFunctionReturn(0); 824 ovascii = (PetscViewer_ASCII*)(*outviewer)->data; 825 826 ovascii->tab = vascii->tab; 827 vascii->sviewer = *outviewer; 828 829 (*outviewer)->format = viewer->format; 830 (*outviewer)->iformat = viewer->iformat; 831 832 ierr = PetscObjectGetName((PetscObject)viewer,&name);CHKERRQ(ierr); 833 ierr = PetscObjectSetName((PetscObject)(*outviewer),name);CHKERRQ(ierr); 834 835 ((PetscViewer_ASCII*)((*outviewer)->data))->bviewer = viewer; 836 (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII_Subcomm; 837 PetscFunctionReturn(0); 838 } 839 840 #undef __FUNCT__ 841 #define __FUNCT__ "PetscViewerRestoreSubcomm_ASCII" 842 PetscErrorCode PetscViewerRestoreSubcomm_ASCII(PetscViewer viewer,MPI_Comm subcomm,PetscViewer *outviewer) 843 { 844 PetscErrorCode ierr; 845 PetscViewer_ASCII *oascii = (PetscViewer_ASCII *)(*outviewer)->data; 846 PetscViewer_ASCII *ascii = (PetscViewer_ASCII *)viewer->data; 847 848 PetscFunctionBegin; 849 if (!ascii->sviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Subcomm never obtained from PetscViewer"); 850 if (ascii->sviewer != *outviewer) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"The given PetscViewer did not generate this subcomm viewer"); 851 852 ascii->sviewer = 0; 853 oascii->fd = PETSC_STDOUT; 854 (*outviewer)->ops->destroy = PetscViewerDestroy_ASCII; 855 ierr = PetscViewerDestroy(outviewer);CHKERRQ(ierr); 856 ierr = PetscViewerFlush(viewer);CHKERRQ(ierr); 857 PetscFunctionReturn(0); 858 } 859 860 #undef __FUNCT__ 861 #define __FUNCT__ "PetscViewerView_ASCII" 862 PetscErrorCode PetscViewerView_ASCII(PetscViewer v,PetscViewer viewer) 863 { 864 PetscErrorCode ierr; 865 PetscViewer_ASCII *ascii = (PetscViewer_ASCII *)v->data; 866 867 PetscFunctionBegin; 868 if (ascii->filename) { 869 ierr = PetscViewerASCIIPrintf(viewer,"Filename: %s\n",ascii->filename);CHKERRQ(ierr); 870 } 871 PetscFunctionReturn(0); 872 } 873 874 EXTERN_C_BEGIN 875 #undef __FUNCT__ 876 #define __FUNCT__ "PetscViewerCreate_ASCII" 877 PetscErrorCode PetscViewerCreate_ASCII(PetscViewer viewer) 878 { 879 PetscViewer_ASCII *vascii; 880 PetscErrorCode ierr; 881 882 PetscFunctionBegin; 883 ierr = PetscNewLog(viewer,PetscViewer_ASCII,&vascii);CHKERRQ(ierr); 884 viewer->data = (void*)vascii; 885 886 viewer->ops->destroy = PetscViewerDestroy_ASCII; 887 viewer->ops->flush = PetscViewerFlush_ASCII; 888 viewer->ops->getsingleton = PetscViewerGetSingleton_ASCII; 889 viewer->ops->restoresingleton = PetscViewerRestoreSingleton_ASCII; 890 viewer->ops->getsubcomm = PetscViewerGetSubcomm_ASCII; 891 viewer->ops->restoresubcomm = PetscViewerRestoreSubcomm_ASCII; 892 viewer->ops->view = PetscViewerView_ASCII; 893 894 /* defaults to stdout unless set with PetscViewerFileSetName() */ 895 vascii->fd = PETSC_STDOUT; 896 vascii->mode = FILE_MODE_WRITE; 897 vascii->bviewer = 0; 898 vascii->sviewer = 0; 899 viewer->format = PETSC_VIEWER_DEFAULT; 900 viewer->iformat = 0; 901 vascii->tab = 0; 902 vascii->tab_store = 0; 903 vascii->filename = 0; 904 vascii->closefile = PETSC_TRUE; 905 906 ierr = PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerFileSetName_C","PetscViewerFileSetName_ASCII", 907 PetscViewerFileSetName_ASCII);CHKERRQ(ierr); 908 ierr = PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerFileGetName_C","PetscViewerFileGetName_ASCII", 909 PetscViewerFileGetName_ASCII);CHKERRQ(ierr); 910 ierr = PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerFileGetMode_C","PetscViewerFileGetMode_ASCII", 911 PetscViewerFileGetMode_ASCII);CHKERRQ(ierr); 912 ierr = PetscObjectComposeFunctionDynamic((PetscObject)viewer,"PetscViewerFileSetMode_C","PetscViewerFileSetMode_ASCII", 913 PetscViewerFileSetMode_ASCII);CHKERRQ(ierr); 914 915 PetscFunctionReturn(0); 916 } 917 EXTERN_C_END 918 919 920 #undef __FUNCT__ 921 #define __FUNCT__ "PetscViewerASCIISynchronizedPrintf" 922 /*@C 923 PetscViewerASCIISynchronizedPrintf - Prints synchronized output to the specified file from 924 several processors. Output of the first processor is followed by that of the 925 second, etc. 926 927 Not Collective, must call collective PetscViewerFlush() to get the results out 928 929 Input Parameters: 930 + viewer - the ASCII PetscViewer 931 - format - the usual printf() format string 932 933 Level: intermediate 934 935 Notes: You must have previously called PetscViewerASCIISynchronizeAllow() to allow this routine to be called. 936 937 Fortran Note: 938 Can only print a single character* string 939 940 .seealso: PetscSynchronizedPrintf(), PetscSynchronizedFlush(), PetscFPrintf(), 941 PetscFOpen(), PetscViewerFlush(), PetscViewerASCIIGetPointer(), PetscViewerDestroy(), PetscViewerASCIIOpen(), 942 PetscViewerASCIIPrintf(), PetscViewerASCIISynchronizedAllow() 943 944 @*/ 945 PetscErrorCode PetscViewerASCIISynchronizedPrintf(PetscViewer viewer,const char format[],...) 946 { 947 PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data; 948 PetscErrorCode ierr; 949 PetscMPIInt rank,size; 950 PetscInt tab = vascii->tab; 951 MPI_Comm comm; 952 FILE *fp; 953 PetscBool iascii; 954 int err; 955 956 PetscFunctionBegin; 957 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 958 PetscValidCharPointer(format,2); 959 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 960 if (!iascii) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not ASCII PetscViewer"); 961 ierr = MPI_Comm_size(((PetscObject)viewer)->comm,&size);CHKERRQ(ierr); 962 if (size > 1 && !vascii->allowsynchronized) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"First call PetscViewerASCIISynchronizedAllow() to allow this call"); 963 if (!viewer->ops->flush) PetscFunctionReturn(0); /* This viewer obtained via PetscViewerGetSubcomm_ASCII(), should not participate. */ 964 965 comm = ((PetscObject)viewer)->comm; 966 fp = vascii->fd; 967 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 968 969 /* First processor prints immediately to fp */ 970 if (!rank) { 971 va_list Argp; 972 973 while (tab--) {ierr = PetscFPrintf(PETSC_COMM_SELF,fp," ");CHKERRQ(ierr);} 974 975 va_start(Argp,format); 976 ierr = (*PetscVFPrintf)(fp,format,Argp);CHKERRQ(ierr); 977 err = fflush(fp); 978 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 979 petsc_printfqueuefile = fp; 980 if (petsc_history) { 981 va_start(Argp,format); 982 ierr = (*PetscVFPrintf)(petsc_history,format,Argp);CHKERRQ(ierr); 983 err = fflush(petsc_history); 984 if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fflush() failed on file"); 985 } 986 va_end(Argp); 987 } else { /* other processors add to local queue */ 988 char *string; 989 va_list Argp; 990 size_t fullLength; 991 PrintfQueue next; 992 993 ierr = PetscNew(struct _PrintfQueue,&next);CHKERRQ(ierr); 994 if (petsc_printfqueue) {petsc_printfqueue->next = next; petsc_printfqueue = next;} 995 else {petsc_printfqueuebase = petsc_printfqueue = next;} 996 petsc_printfqueuelength++; 997 next->size = QUEUESTRINGSIZE; 998 ierr = PetscMalloc(next->size*sizeof(char), &next->string);CHKERRQ(ierr); 999 ierr = PetscMemzero(next->string,next->size);CHKERRQ(ierr); 1000 string = next->string; 1001 tab *= 2; 1002 while (tab--) {*string++ = ' ';} 1003 va_start(Argp,format); 1004 ierr = PetscVSNPrintf(string,next->size-2*vascii->tab,format,&fullLength,Argp); 1005 va_end(Argp); 1006 } 1007 PetscFunctionReturn(0); 1008 } 1009 1010 1011