xref: /petsc/src/sys/classes/viewer/impls/ascii/vcreatea.c (revision 20f4b53cbb5e9bd9ef12b76a8697d60d197cda17)
15c6c1daeSBarry Smith 
2f5860696SSatish Balay #include <../src/sys/classes/viewer/impls/ascii/asciiimpl.h> /*I     "petscviewer.h"   I*/
35c6c1daeSBarry Smith 
4e2dcd6d3SBarry Smith /*
5e2dcd6d3SBarry Smith     The variable Petsc_Viewer_Stdout_keyval is used to indicate an MPI attribute that
6e2dcd6d3SBarry Smith   is attached to a communicator, in this case the attribute is a PetscViewer.
7e2dcd6d3SBarry Smith */
8d4c7638eSBarry Smith PetscMPIInt Petsc_Viewer_Stdout_keyval = MPI_KEYVAL_INVALID;
9e2dcd6d3SBarry Smith 
109c5ded49SBarry Smith /*@
11811af0c4SBarry Smith    PetscViewerASCIIGetStdout - Creates a `PETSCVIEWERASCII` `PetscViewer` shared by all processors
12811af0c4SBarry Smith                     in a communicator. Error returning version of `PETSC_VIEWER_STDOUT_()`
135c6c1daeSBarry Smith 
14d083f849SBarry Smith    Collective
155c6c1daeSBarry Smith 
165c6c1daeSBarry Smith    Input Parameter:
17811af0c4SBarry Smith .  comm - the MPI communicator to share the `PetscViewer`
185c6c1daeSBarry Smith 
195c6c1daeSBarry Smith    Level: beginner
205c6c1daeSBarry Smith 
21811af0c4SBarry Smith    Note:
223f423023SBarry Smith      This should be used in all PETSc source code instead of `PETSC_VIEWER_STDOUT_()` since it allows error checking
235c6c1daeSBarry Smith 
24d1f92df0SBarry Smith .seealso: [](sec_viewers), `PETSC_VIEWER_DRAW_()`, `PetscViewerASCIIOpen()`, `PETSC_VIEWER_STDERR_`, `PETSC_VIEWER_STDOUT_WORLD`,
25db781477SPatrick Sanan           `PETSC_VIEWER_STDOUT_SELF`
265c6c1daeSBarry Smith @*/
27d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscViewerASCIIGetStdout(MPI_Comm comm, PetscViewer *viewer)
28d71ae5a4SJacob Faibussowitsch {
29e2dcd6d3SBarry Smith   PetscBool flg;
30e2dcd6d3SBarry Smith   MPI_Comm  ncomm;
315c6c1daeSBarry Smith 
325c6c1daeSBarry Smith   PetscFunctionBegin;
339566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockLock(&PetscViewerASCIISpinLockStdout));
349566063dSJacob Faibussowitsch   PetscCall(PetscCommDuplicate(comm, &ncomm, NULL));
3548a46eb9SPierre Jolivet   if (Petsc_Viewer_Stdout_keyval == MPI_KEYVAL_INVALID) PetscCallMPI(MPI_Comm_create_keyval(MPI_COMM_NULL_COPY_FN, MPI_COMM_NULL_DELETE_FN, &Petsc_Viewer_Stdout_keyval, NULL));
369566063dSJacob Faibussowitsch   PetscCallMPI(MPI_Comm_get_attr(ncomm, Petsc_Viewer_Stdout_keyval, (void **)viewer, (PetscMPIInt *)&flg));
37e2dcd6d3SBarry Smith   if (!flg) { /* PetscViewer not yet created */
389566063dSJacob Faibussowitsch     PetscCall(PetscViewerASCIIOpen(ncomm, "stdout", viewer));
399566063dSJacob Faibussowitsch     PetscCall(PetscObjectRegisterDestroy((PetscObject)*viewer));
409566063dSJacob Faibussowitsch     PetscCallMPI(MPI_Comm_set_attr(ncomm, Petsc_Viewer_Stdout_keyval, (void *)*viewer));
41e2dcd6d3SBarry Smith   }
429566063dSJacob Faibussowitsch   PetscCall(PetscCommDestroy(&ncomm));
439566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockUnlock(&PetscViewerASCIISpinLockStdout));
443ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
455c6c1daeSBarry Smith }
465c6c1daeSBarry Smith 
475c6c1daeSBarry Smith /*@C
48811af0c4SBarry Smith    PETSC_VIEWER_STDOUT_ - Creates a ASCII `PetscViewer` shared by all processors
495c6c1daeSBarry Smith                     in a communicator.
505c6c1daeSBarry Smith 
51d083f849SBarry Smith    Collective
525c6c1daeSBarry Smith 
535c6c1daeSBarry Smith    Input Parameter:
54811af0c4SBarry Smith .  comm - the MPI communicator to share the `PetscViewer`
555c6c1daeSBarry Smith 
565c6c1daeSBarry Smith    Level: beginner
575c6c1daeSBarry Smith 
58811af0c4SBarry Smith    Note:
595c6c1daeSBarry Smith    Unlike almost all other PETSc routines, this does not return
605c6c1daeSBarry Smith    an error code. Usually used in the form
615c6c1daeSBarry Smith $      XXXView(XXX object,PETSC_VIEWER_STDOUT_(comm));
625c6c1daeSBarry Smith 
63d1f92df0SBarry Smith .seealso: [](sec_viewers), `PETSC_VIEWER_DRAW_()`, `PetscViewerASCIIOpen()`, `PETSC_VIEWER_STDERR_`, `PETSC_VIEWER_STDOUT_WORLD`,
64db781477SPatrick Sanan           `PETSC_VIEWER_STDOUT_SELF`
655c6c1daeSBarry Smith @*/
66d71ae5a4SJacob Faibussowitsch PetscViewer PETSC_VIEWER_STDOUT_(MPI_Comm comm)
67d71ae5a4SJacob Faibussowitsch {
685c6c1daeSBarry Smith   PetscErrorCode ierr;
695c6c1daeSBarry Smith   PetscViewer    viewer;
705c6c1daeSBarry Smith 
715c6c1daeSBarry Smith   PetscFunctionBegin;
725c6c1daeSBarry Smith   ierr = PetscViewerASCIIGetStdout(comm, &viewer);
739371c9d4SSatish Balay   if (ierr) {
743ba16761SJacob Faibussowitsch     ierr = PetscError(PETSC_COMM_SELF, __LINE__, "PETSC_VIEWER_STDOUT_", __FILE__, PETSC_ERR_PLIB, PETSC_ERROR_INITIAL, " ");
759371c9d4SSatish Balay     PetscFunctionReturn(NULL);
769371c9d4SSatish Balay   }
775c6c1daeSBarry Smith   PetscFunctionReturn(viewer);
785c6c1daeSBarry Smith }
795c6c1daeSBarry Smith 
80e2dcd6d3SBarry Smith /*
81e2dcd6d3SBarry Smith     The variable Petsc_Viewer_Stderr_keyval is used to indicate an MPI attribute that
82e2dcd6d3SBarry Smith   is attached to a communicator, in this case the attribute is a PetscViewer.
83e2dcd6d3SBarry Smith */
84d4c7638eSBarry Smith PetscMPIInt Petsc_Viewer_Stderr_keyval = MPI_KEYVAL_INVALID;
85e2dcd6d3SBarry Smith 
869c5ded49SBarry Smith /*@
87811af0c4SBarry Smith    PetscViewerASCIIGetStderr - Creates a `PETSCVIEWERASCII` `PetscViewer` shared by all processors
88811af0c4SBarry Smith                     in a communicator. Error returning version of `PETSC_VIEWER_STDERR_()`
895c6c1daeSBarry Smith 
90d083f849SBarry Smith    Collective
915c6c1daeSBarry Smith 
925c6c1daeSBarry Smith    Input Parameter:
93811af0c4SBarry Smith .  comm - the MPI communicator to share the `PetscViewer`
945c6c1daeSBarry Smith 
955c6c1daeSBarry Smith    Level: beginner
965c6c1daeSBarry Smith 
97811af0c4SBarry Smith    Note:
983f423023SBarry Smith      This should be used in all PETSc source code instead of `PETSC_VIEWER_STDERR_()` since it allows error checking
995c6c1daeSBarry Smith 
100d1f92df0SBarry Smith .seealso: [](sec_viewers), `PETSC_VIEWER_DRAW_()`, `PetscViewerASCIIOpen()`, `PETSC_VIEWER_STDERR_`, `PETSC_VIEWER_STDERR_WORLD`,
101db781477SPatrick Sanan           `PETSC_VIEWER_STDERR_SELF`
1025c6c1daeSBarry Smith @*/
103d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscViewerASCIIGetStderr(MPI_Comm comm, PetscViewer *viewer)
104d71ae5a4SJacob Faibussowitsch {
105e2dcd6d3SBarry Smith   PetscBool flg;
106e2dcd6d3SBarry Smith   MPI_Comm  ncomm;
107e2dcd6d3SBarry Smith 
108e2dcd6d3SBarry Smith   PetscFunctionBegin;
1099566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockLock(&PetscViewerASCIISpinLockStderr));
1109566063dSJacob Faibussowitsch   PetscCall(PetscCommDuplicate(comm, &ncomm, NULL));
11148a46eb9SPierre Jolivet   if (Petsc_Viewer_Stderr_keyval == MPI_KEYVAL_INVALID) PetscCallMPI(MPI_Comm_create_keyval(MPI_COMM_NULL_COPY_FN, MPI_COMM_NULL_DELETE_FN, &Petsc_Viewer_Stderr_keyval, NULL));
1129566063dSJacob Faibussowitsch   PetscCallMPI(MPI_Comm_get_attr(ncomm, Petsc_Viewer_Stderr_keyval, (void **)viewer, (PetscMPIInt *)&flg));
113e2dcd6d3SBarry Smith   if (!flg) { /* PetscViewer not yet created */
1149566063dSJacob Faibussowitsch     PetscCall(PetscViewerASCIIOpen(ncomm, "stderr", viewer));
1159566063dSJacob Faibussowitsch     PetscCall(PetscObjectRegisterDestroy((PetscObject)*viewer));
1169566063dSJacob Faibussowitsch     PetscCallMPI(MPI_Comm_set_attr(ncomm, Petsc_Viewer_Stderr_keyval, (void *)*viewer));
117e2dcd6d3SBarry Smith   }
1189566063dSJacob Faibussowitsch   PetscCall(PetscCommDestroy(&ncomm));
1199566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockUnlock(&PetscViewerASCIISpinLockStderr));
1203ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
1215c6c1daeSBarry Smith }
1225c6c1daeSBarry Smith 
1235c6c1daeSBarry Smith /*@C
124811af0c4SBarry Smith    PETSC_VIEWER_STDERR_ - Creates a `PETSCVIEWERASCII` `PetscViewer` shared by all processors
1255c6c1daeSBarry Smith                     in a communicator.
1265c6c1daeSBarry Smith 
127d083f849SBarry Smith    Collective
1285c6c1daeSBarry Smith 
1295c6c1daeSBarry Smith    Input Parameter:
130811af0c4SBarry Smith .  comm - the MPI communicator to share the `PetscViewer`
1315c6c1daeSBarry Smith 
1325c6c1daeSBarry Smith    Level: beginner
1335c6c1daeSBarry Smith 
1343f423023SBarry Smith    Notes:
1355c6c1daeSBarry Smith    Unlike almost all other PETSc routines, this does not return
1365c6c1daeSBarry Smith    an error code. Usually used in the form
1375c6c1daeSBarry Smith $      XXXView(XXX object,PETSC_VIEWER_STDERR_(comm));
1385c6c1daeSBarry Smith 
1393f423023SBarry Smith    `PetscViewerASCIIGetStderr()` is preferred  since it allows error checking
1403f423023SBarry Smith 
141d1f92df0SBarry Smith .seealso: [](sec_viewers), `PETSC_VIEWER_DRAW_`, `PetscViewerASCIIOpen()`, `PETSC_VIEWER_STDOUT_`, `PETSC_VIEWER_STDOUT_WORLD`,
142db781477SPatrick Sanan           `PETSC_VIEWER_STDOUT_SELF`, `PETSC_VIEWER_STDERR_WORLD`, `PETSC_VIEWER_STDERR_SELF`
1435c6c1daeSBarry Smith @*/
144d71ae5a4SJacob Faibussowitsch PetscViewer PETSC_VIEWER_STDERR_(MPI_Comm comm)
145d71ae5a4SJacob Faibussowitsch {
1465c6c1daeSBarry Smith   PetscErrorCode ierr;
1475c6c1daeSBarry Smith   PetscViewer    viewer;
1485c6c1daeSBarry Smith 
1495c6c1daeSBarry Smith   PetscFunctionBegin;
1505c6c1daeSBarry Smith   ierr = PetscViewerASCIIGetStderr(comm, &viewer);
1519371c9d4SSatish Balay   if (ierr) {
1523ba16761SJacob Faibussowitsch     ierr = PetscError(PETSC_COMM_SELF, __LINE__, "PETSC_VIEWER_STDERR_", __FILE__, PETSC_ERR_PLIB, PETSC_ERROR_INITIAL, " ");
1539371c9d4SSatish Balay     PetscFunctionReturn(NULL);
1549371c9d4SSatish Balay   }
1555c6c1daeSBarry Smith   PetscFunctionReturn(viewer);
1565c6c1daeSBarry Smith }
1575c6c1daeSBarry Smith 
1585c6c1daeSBarry Smith PetscMPIInt Petsc_Viewer_keyval = MPI_KEYVAL_INVALID;
1595c6c1daeSBarry Smith /*
1603f423023SBarry Smith    Called with MPI_Comm_free() is called on a communicator that has a viewer as an attribute. The viewer is not actually destroyed
1613f423023SBarry Smith    because that is managed by PetscObjectDestroyRegisterAll(). PetscViewerASCIIGetStdout() registers the viewer with PetscObjectDestroyRegister() to be destroyed when PetscFinalize() is called.
1625c6c1daeSBarry Smith 
1635c6c1daeSBarry Smith   This is called by MPI, not by users.
1645c6c1daeSBarry Smith 
1655c6c1daeSBarry Smith */
166d71ae5a4SJacob Faibussowitsch PETSC_EXTERN PetscMPIInt MPIAPI Petsc_DelViewer(MPI_Comm comm, PetscMPIInt keyval, void *attr_val, void *extra_state)
167d71ae5a4SJacob Faibussowitsch {
1685c6c1daeSBarry Smith   PetscFunctionBegin;
1699566063dSJacob Faibussowitsch   PetscCallMPI(PetscInfo(NULL, "Removing viewer data attribute in an MPI_Comm %ld\n", (long)comm));
1705c6c1daeSBarry Smith   PetscFunctionReturn(MPI_SUCCESS);
1715c6c1daeSBarry Smith }
1725c6c1daeSBarry Smith 
1735c6c1daeSBarry Smith /*@C
174811af0c4SBarry Smith    PetscViewerASCIIOpen - Opens an ASCII file for writing as a `PetscViewer`.
1755c6c1daeSBarry Smith 
176d083f849SBarry Smith    Collective
1775c6c1daeSBarry Smith 
1785c6c1daeSBarry Smith    Input Parameters:
1795c6c1daeSBarry Smith +  comm - the communicator
1805c6c1daeSBarry Smith -  name - the file name
1815c6c1daeSBarry Smith 
1825c6c1daeSBarry Smith    Output Parameter:
1833f423023SBarry Smith .  lab - the `PetscViewer` to use with the specified file
1845c6c1daeSBarry Smith 
1855c6c1daeSBarry Smith    Level: beginner
1865c6c1daeSBarry Smith 
1875c6c1daeSBarry Smith    Notes:
188f8859db6SBarry Smith    To open a ASCII file as a viewer for reading one must use the sequence
189811af0c4SBarry Smith .vb
190811af0c4SBarry Smith    PetscViewerCreate(comm,&lab);
191811af0c4SBarry Smith    PetscViewerSetType(lab,PETSCVIEWERASCII);
192811af0c4SBarry Smith    PetscViewerFileSetMode(lab,FILE_MODE_READ);
193811af0c4SBarry Smith    PetscViewerFileSetName(lab,name);
194811af0c4SBarry Smith .ve
195f8859db6SBarry Smith 
196811af0c4SBarry Smith    This `PetscViewer` can be destroyed with `PetscViewerDestroy()`.
1975c6c1daeSBarry Smith 
1982ea3bc1cSBarry Smith    The MPI communicator used here must match that used by the object one is viewing. For example if the
199811af0c4SBarry Smith    Mat was created with a `PETSC_COMM_WORLD`, then the Viewer must be created with `PETSC_COMM_WORLD`
2005c6c1daeSBarry Smith 
201811af0c4SBarry Smith    As shown below, `PetscViewerASCIIOpen()` is useful in conjunction with
202811af0c4SBarry Smith    `MatView()` and `VecView()`
2035c6c1daeSBarry Smith .vb
2045c6c1daeSBarry Smith      PetscViewerASCIIOpen(PETSC_COMM_WORLD,"mat.output",&viewer);
2055c6c1daeSBarry Smith      MatView(matrix,viewer);
2065c6c1daeSBarry Smith .ve
2075c6c1daeSBarry Smith 
208d1f92df0SBarry Smith .seealso: [](sec_viewers), `MatView()`, `VecView()`, `PetscViewerDestroy()`, `PetscViewerBinaryOpen()`, `PetscViewerASCIIRead()`, `PETSCVIEWERASCII`
209db781477SPatrick Sanan           `PetscViewerASCIIGetPointer()`, `PetscViewerPushFormat()`, `PETSC_VIEWER_STDOUT_`, `PETSC_VIEWER_STDERR_`,
210db781477SPatrick Sanan           `PETSC_VIEWER_STDOUT_WORLD`, `PETSC_VIEWER_STDOUT_SELF`,
2115c6c1daeSBarry Smith @*/
212d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscViewerASCIIOpen(MPI_Comm comm, const char name[], PetscViewer *lab)
213d71ae5a4SJacob Faibussowitsch {
2145c6c1daeSBarry Smith   PetscViewerLink *vlink, *nv;
2155c6c1daeSBarry Smith   PetscBool        flg, eq;
2165c6c1daeSBarry Smith   size_t           len;
2175c6c1daeSBarry Smith 
2185c6c1daeSBarry Smith   PetscFunctionBegin;
2199566063dSJacob Faibussowitsch   PetscCall(PetscStrlen(name, &len));
2205c6c1daeSBarry Smith   if (!len) {
2219566063dSJacob Faibussowitsch     PetscCall(PetscViewerASCIIGetStdout(comm, lab));
2229566063dSJacob Faibussowitsch     PetscCall(PetscObjectReference((PetscObject)*lab));
2233ba16761SJacob Faibussowitsch     PetscFunctionReturn(PETSC_SUCCESS);
2245c6c1daeSBarry Smith   }
2259566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockLock(&PetscViewerASCIISpinLockOpen));
22648a46eb9SPierre Jolivet   if (Petsc_Viewer_keyval == MPI_KEYVAL_INVALID) PetscCallMPI(MPI_Comm_create_keyval(MPI_COMM_NULL_COPY_FN, Petsc_DelViewer, &Petsc_Viewer_keyval, (void *)0));
2272bf49c77SBarry Smith   /*
2282bf49c77SBarry Smith        It would be better to move this code to PetscFileSetName() but since it must return a preexiting communicator
2292bf49c77SBarry Smith      we cannot do that, since PetscFileSetName() takes a communicator that already exists.
2302bf49c77SBarry Smith 
2312bf49c77SBarry Smith       Plus if the original communicator that created the file has since been close this will not detect the old
2322bf49c77SBarry Smith       communictor and hence will overwrite the old data. It may be better to simply remove all this code
2332bf49c77SBarry Smith   */
2345c6c1daeSBarry Smith   /* make sure communicator is a PETSc communicator */
2359566063dSJacob Faibussowitsch   PetscCall(PetscCommDuplicate(comm, &comm, NULL));
2365c6c1daeSBarry Smith   /* has file already been opened into a viewer */
2379566063dSJacob Faibussowitsch   PetscCallMPI(MPI_Comm_get_attr(comm, Petsc_Viewer_keyval, (void **)&vlink, (PetscMPIInt *)&flg));
2385c6c1daeSBarry Smith   if (flg) {
2395c6c1daeSBarry Smith     while (vlink) {
2409566063dSJacob Faibussowitsch       PetscCall(PetscStrcmp(name, ((PetscViewer_ASCII *)(vlink->viewer->data))->filename, &eq));
2415c6c1daeSBarry Smith       if (eq) {
2429566063dSJacob Faibussowitsch         PetscCall(PetscObjectReference((PetscObject)vlink->viewer));
2435c6c1daeSBarry Smith         *lab = vlink->viewer;
2449566063dSJacob Faibussowitsch         PetscCall(PetscCommDestroy(&comm));
2459566063dSJacob Faibussowitsch         PetscCall(PetscSpinlockUnlock(&PetscViewerASCIISpinLockOpen));
2463ba16761SJacob Faibussowitsch         PetscFunctionReturn(PETSC_SUCCESS);
2475c6c1daeSBarry Smith       }
2485c6c1daeSBarry Smith       vlink = vlink->next;
2495c6c1daeSBarry Smith     }
2505c6c1daeSBarry Smith   }
2519566063dSJacob Faibussowitsch   PetscCall(PetscViewerCreate(comm, lab));
2529566063dSJacob Faibussowitsch   PetscCall(PetscViewerSetType(*lab, PETSCVIEWERASCII));
2531baa6e33SBarry Smith   if (name) PetscCall(PetscViewerFileSetName(*lab, name));
2545c6c1daeSBarry Smith   /* save viewer into communicator if needed later */
2559566063dSJacob Faibussowitsch   PetscCall(PetscNew(&nv));
2565c6c1daeSBarry Smith   nv->viewer = *lab;
2575c6c1daeSBarry Smith   if (!flg) {
2589566063dSJacob Faibussowitsch     PetscCallMPI(MPI_Comm_set_attr(comm, Petsc_Viewer_keyval, nv));
2595c6c1daeSBarry Smith   } else {
2609566063dSJacob Faibussowitsch     PetscCallMPI(MPI_Comm_get_attr(comm, Petsc_Viewer_keyval, (void **)&vlink, (PetscMPIInt *)&flg));
2615c6c1daeSBarry Smith     if (vlink) {
2625c6c1daeSBarry Smith       while (vlink->next) vlink = vlink->next;
2635c6c1daeSBarry Smith       vlink->next = nv;
2645c6c1daeSBarry Smith     } else {
2659566063dSJacob Faibussowitsch       PetscCallMPI(MPI_Comm_set_attr(comm, Petsc_Viewer_keyval, nv));
2665c6c1daeSBarry Smith     }
2675c6c1daeSBarry Smith   }
2689566063dSJacob Faibussowitsch   PetscCall(PetscCommDestroy(&comm));
2699566063dSJacob Faibussowitsch   PetscCall(PetscSpinlockUnlock(&PetscViewerASCIISpinLockOpen));
2703ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
2715c6c1daeSBarry Smith }
2725c6c1daeSBarry Smith 
2735c6c1daeSBarry Smith /*@C
2743f423023SBarry Smith    PetscViewerASCIIOpenWithFILE - Given an open file creates an `PETSCVIEWERASCII` viewer that prints to it.
2755c6c1daeSBarry Smith 
276d083f849SBarry Smith    Collective
2775c6c1daeSBarry Smith 
2785c6c1daeSBarry Smith    Input Parameters:
2795c6c1daeSBarry Smith +  comm - the communicator
280*20f4b53cSBarry Smith -  fd - the `FILE` pointer
2815c6c1daeSBarry Smith 
2825c6c1daeSBarry Smith    Output Parameter:
283811af0c4SBarry Smith .  lab - the `PetscViewer` to use with the specified file
2845c6c1daeSBarry Smith 
2855c6c1daeSBarry Smith    Level: beginner
2865c6c1daeSBarry Smith 
2875c6c1daeSBarry Smith    Notes:
288811af0c4SBarry Smith    This `PetscViewer` can be destroyed with `PetscViewerDestroy()`, but the fd will NOT be closed.
2895c6c1daeSBarry Smith 
290811af0c4SBarry Smith    If a multiprocessor communicator is used (such as `PETSC_COMM_WORLD`),
2915c6c1daeSBarry Smith    then only the first processor in the group uses the file.  All other
2925c6c1daeSBarry Smith    processors send their data to the first processor to print.
2935c6c1daeSBarry Smith 
294d1f92df0SBarry Smith .seealso: [](sec_viewers), `MatView()`, `VecView()`, `PetscViewerDestroy()`, `PetscViewerBinaryOpen()`,
295db781477SPatrick Sanan           `PetscViewerASCIIGetPointer()`, `PetscViewerPushFormat()`, `PETSC_VIEWER_STDOUT_`, `PETSC_VIEWER_STDERR_`,
296811af0c4SBarry Smith           `PETSC_VIEWER_STDOUT_WORLD`, `PETSC_VIEWER_STDOUT_SELF`, `PetscViewerASCIIOpen()`, `PetscViewerASCIISetFILE()`, `PETSCVIEWERASCII`
2975c6c1daeSBarry Smith @*/
298d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscViewerASCIIOpenWithFILE(MPI_Comm comm, FILE *fd, PetscViewer *lab)
299d71ae5a4SJacob Faibussowitsch {
3005c6c1daeSBarry Smith   PetscFunctionBegin;
3019566063dSJacob Faibussowitsch   PetscCall(PetscViewerCreate(comm, lab));
3029566063dSJacob Faibussowitsch   PetscCall(PetscViewerSetType(*lab, PETSCVIEWERASCII));
3039566063dSJacob Faibussowitsch   PetscCall(PetscViewerASCIISetFILE(*lab, fd));
3043ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
3055c6c1daeSBarry Smith }
3065c6c1daeSBarry Smith 
307811af0c4SBarry Smith /*@C
3083f423023SBarry Smith    PetscViewerASCIISetFILE - Given an open file sets the `PETSCVIEWERASCII` viewer to use the file for output
309811af0c4SBarry Smith 
310*20f4b53cSBarry Smith    Not Collective
311811af0c4SBarry Smith 
312811af0c4SBarry Smith    Input Parameters:
313811af0c4SBarry Smith +  viewer - the `PetscViewer` to use with the specified file
314*20f4b53cSBarry Smith -  fd - the `FILE` pointer
315811af0c4SBarry Smith 
316811af0c4SBarry Smith    Level: beginner
317811af0c4SBarry Smith 
318811af0c4SBarry Smith    Notes:
319811af0c4SBarry Smith    This `PetscViewer` can be destroyed with `PetscViewerDestroy()`, but the fd will NOT be closed.
320811af0c4SBarry Smith 
321811af0c4SBarry Smith    If a multiprocessor communicator is used (such as `PETSC_COMM_WORLD`),
322811af0c4SBarry Smith    then only the first processor in the group uses the file.  All other
323811af0c4SBarry Smith    processors send their data to the first processor to print.
324811af0c4SBarry Smith 
325811af0c4SBarry Smith .seealso: `MatView()`, `VecView()`, `PetscViewerDestroy()`, `PetscViewerBinaryOpen()`,
326811af0c4SBarry Smith           `PetscViewerASCIIGetPointer()`, `PetscViewerPushFormat()`, `PETSC_VIEWER_STDOUT_`, `PETSC_VIEWER_STDERR_`,
327811af0c4SBarry Smith           `PETSC_VIEWER_STDOUT_WORLD`, `PETSC_VIEWER_STDOUT_SELF`, `PetscViewerASCIIOpen()`, `PetscViewerASCIIOpenWithFILE()`, `PETSCVIEWERASCII`
328811af0c4SBarry Smith @*/
329d71ae5a4SJacob Faibussowitsch PetscErrorCode PetscViewerASCIISetFILE(PetscViewer viewer, FILE *fd)
330d71ae5a4SJacob Faibussowitsch {
3315c6c1daeSBarry Smith   PetscViewer_ASCII *vascii = (PetscViewer_ASCII *)viewer->data;
3325c6c1daeSBarry Smith 
3335c6c1daeSBarry Smith   PetscFunctionBegin;
3345c6c1daeSBarry Smith   vascii->fd        = fd;
3355c6c1daeSBarry Smith   vascii->closefile = PETSC_FALSE;
3363ba16761SJacob Faibussowitsch   PetscFunctionReturn(PETSC_SUCCESS);
3375c6c1daeSBarry Smith }
338