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