xref: /petsc/src/sys/classes/viewer/interface/dupl.c (revision 0ea77eda237b1068ff0d8bfa28c3463dc2087695)
1 
2 #include <petsc/private/viewerimpl.h> /*I "petscviewer.h" I*/
3 
4 /*@C
5    PetscViewerGetSubViewer - Creates a new `PetscViewer` (same type as the old)
6     that lives on a subcommunicator
7 
8     Collective on viewer
9 
10    Input Parameter:
11 .  viewer - the `PetscViewer` to be reproduced
12 
13    Output Parameter:
14 .  outviewer - new `PetscViewer`
15 
16    Level: advanced
17 
18    Notes:
19     The output of the subviewers is synchronized against the original viewer. For example, if a
20     viewer on two MPI ranks is decomposed into two subviewers, the output from the first viewer is
21     all printed before the output from the second viewer. You must call `PetscViewerFlush()` after
22     the call to `PetscViewerRestoreSubViewer()`.
23 
24     Call `PetscViewerRestoreSubViewer()` to destroy this `PetscViewer`, NOT `PetscViewerDestroy()`
25 
26      This is most commonly used to view a sequential object that is part of a
27     parallel object. For example `PCView()` on a `PCBJACOBI` could use this to obtain a
28     `PetscViewer` that is used with the sequential `KSP` on one block of the preconditioner.
29 
30     Between the calls to `PetscViewerGetSubViewer()` and `PetscViewerRestoreSubViewer()` the original
31     viewer should not be used
32 
33     `PETSCVIEWERDRAW` and `PETSCVIEWERBINARY` only support returning a singleton viewer on rank 0,
34     all other ranks will return a NULL viewer
35 
36   Developer Notes:
37     There is currently incomplete error checking that the user does not use the original viewer between the
38     the calls to `PetscViewerGetSubViewer()` and `PetscViewerRestoreSubViewer()`. If the user does there
39     could be errors in the viewing that go undetected or crash the code.
40 
41     It would be nice if the call to `PetscViewerFlush()` was not required and was handled by
42     `PetscViewerRestoreSubViewer()`
43 
44 .seealso: `PetscViewerSocketOpen()`, `PetscViewerASCIIOpen()`, `PetscViewerDrawOpen()`, `PetscViewerRestoreSubViewer()`
45 @*/
46 PetscErrorCode PetscViewerGetSubViewer(PetscViewer viewer, MPI_Comm comm, PetscViewer *outviewer) {
47   PetscFunctionBegin;
48   PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID, 1);
49   PetscValidPointer(outviewer, 3);
50   PetscUseTypeMethod(viewer, getsubviewer, comm, outviewer);
51   PetscFunctionReturn(0);
52 }
53 
54 /*@C
55    PetscViewerRestoreSubViewer - Restores a new `PetscViewer` obtained with `PetscViewerGetSubViewer()`.
56 
57     Collective on viewer
58 
59    Input Parameters:
60 +  viewer - the `PetscViewer` that was reproduced
61 -  outviewer - the subviewer to be returned `PetscViewer`
62 
63    Level: advanced
64 
65 .seealso: `PetscViewerSocketOpen()`, `PetscViewerASCIIOpen()`, `PetscViewerDrawOpen()`, `PetscViewerGetSubViewer()`
66 @*/
67 PetscErrorCode PetscViewerRestoreSubViewer(PetscViewer viewer, MPI_Comm comm, PetscViewer *outviewer) {
68   PetscFunctionBegin;
69   PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID, 1);
70 
71   PetscUseTypeMethod(viewer, restoresubviewer, comm, outviewer);
72   PetscFunctionReturn(0);
73 }
74