Actual source code: mpiuopen.c
1: /*$Id: mpiuopen.c,v 1.38 2001/03/23 23:20:30 balay Exp $*/
2: /*
3: Some PETSc utilites routines to add simple parallel IO capability
4: */
5: #include petsc.h
6: #include petscsys.h
7: #include <stdarg.h>
8: #if defined(PETSC_HAVE_STDLIB_H)
9: #include <stdlib.h>
10: #endif
11: #include "petscfix.h"
13: /*@C
14: PetscFOpen - Has the first process in the communicator open a file;
15: all others do nothing.
17: Collective on MPI_Comm
19: Input Parameters:
20: + comm - the communicator
21: . name - the filename
22: - mode - the mode for fopen(), usually "w"
24: Output Parameter:
25: . fp - the file pointer
27: Level: developer
29: Notes:
30: PETSC_NULL (0), "stderr" or "stdout" may be passed in as the filename
31:
32: Fortran Note:
33: This routine is not supported in Fortran.
35: Concepts: opening ASCII file
36: Concepts: files^opening ASCII
38: .seealso: PetscFClose()
39: @*/
40: int PetscFOpen(MPI_Comm comm,const char name[],const char mode[],FILE **fp)
41: {
42: int rank,ierr;
43: FILE *fd;
44: char fname[256],tname[256];
47: MPI_Comm_rank(comm,&rank);
48: if (!rank) {
49: PetscTruth isstdout,isstderr;
50: PetscStrcmp(name,"stdout",&isstdout);
51: PetscStrcmp(name,"stderr",&isstderr);
52: if (isstdout || !name) {
53: fd = stdout;
54: } else if (isstderr) {
55: fd = stderr;
56: } else {
57: PetscStrreplace(PETSC_COMM_SELF,name,tname,256);
58: PetscFixFilename(tname,fname);
59: PetscLogInfo(0,"Opening file %sn",fname);
60: fd = fopen(fname,mode);
61: }
62: } else fd = 0;
63: *fp = fd;
64: return(0);
65: }
67: /*@C
68: PetscFClose - Has the first processor in the communicator close a
69: file; all others do nothing.
71: Collective on MPI_Comm
73: Input Parameters:
74: + comm - the communicator
75: - fd - the file, opened with PetscFOpen()
77: Level: developer
79: Fortran Note:
80: This routine is not supported in Fortran.
82: Concepts: files^closing ASCII
83: Concepts: closing file
85: .seealso: PetscFOpen()
86: @*/
87: int PetscFClose(MPI_Comm comm,FILE *fd)
88: {
89: int rank,ierr;
92: MPI_Comm_rank(comm,&rank);
93: if (!rank && fd != stdout && fd != stderr) fclose(fd);
94: return(0);
95: }
97: int PetscPClose(MPI_Comm comm,FILE *fd)
98: {
99: int rank,ierr;
102: MPI_Comm_rank(comm,&rank);
103: if (!rank) {
104: char buf[1024];
105: while (fgets(buf,1024,fd)) {;} /* wait till it prints everything */
106: #if defined(PETSC_HAVE_POPEN)
107: pclose(fd);
108: #else
109: SETERRQ(1,"Cannot run programs, no popen()");
110: #endif
111: }
112: return(0);
113: }
115: /*@C
116: PetscPOpen - Runs a program on processor zero and sends either its input or output to
117: a file.
119: Collective on MPI_Comm, but only process 0 runs the command
121: Input Parameters:
122: + comm - MPI communicator, only processor zero runs the program
123: . machine - machine to run command on or PETSC_NULL, or string with 0 in first location
124: . program - name of program to run
125: - mode - either r or w
127: Output Parameter:
128: . fp - the file pointer where program input or output may be read or PETSC_NULL if don't care
130: Level: intermediate
132: Notes:
133: Does not work under Windows
135: The program string may contain ${DISPLAY}, ${HOMEDIRECTORY} or ${WORKINGDIRECTORY}; these
136: will be replaced with relevent values.
138: .seealso: PetscFOpen(), PetscFClose(), PetscPClose()
140: @*/
141: int PetscPOpen(MPI_Comm comm,char *machine,char *program,const char mode[],FILE **fp)
142: {
143: int ierr,rank,i,len,cnt;
144: char commandt[1024],command[1024];
145: #if defined(PETSC_HAVE_POPEN)
146: FILE *fd;
147: #endif
151: /* all processors have to do the string manipulation because PetscStrreplace() is a collective operation */
152: if (machine && machine[0]) {
153: PetscStrcpy(command,"rsh ");
154: PetscStrcat(command,machine);
155: PetscStrcat(command," " setenv DISPLAY ${DISPLAY}; ");
156: /*
157: Copy program into command but protect the " with a in front of it
158: */
159: PetscStrlen(command,&cnt);
160: PetscStrlen(program,&len);
161: for (i=0; i<len; i++) {
162: if (program[i] == '"') {
163: command[cnt++] = '\';
164: }
165: command[cnt++] = program[i];
166: }
167: command[cnt] = 0;
168: PetscStrcat(command,""");
169: } else {
170: PetscStrcpy(command,program);
171: }
173: PetscStrreplace(comm,command,commandt,1024);
174:
175: MPI_Comm_rank(comm,&rank);
176: if (!rank) {
177: PetscLogInfo(0,"Running command :%sn",commandt);
179: #if defined(PETSC_HAVE_POPEN)
180: if (!(fd = popen(commandt,mode))) {
181: SETERRQ1(1,"Cannot run command %s",commandt);
182: }
183: if (fp) *fp = fd;
184: #else
185: SETERRQ(1,"Cannot run programs, no popen()");
186: #endif
187: }
188: return(0);
189: }