|
File system and file I/O
Is there any way in OS/400 to redirect printf output from the console log to a file?
Printf output goes to STDOUT. In OS/400 PASE, STDOUT meets typical UNIX expectations (to the terminal for interactive or piped to a file). For the ILE environment, STDOUT can be made to override to a file where output is to be redirected using OVRDBF.
OVRDBF FILE(STDOUT) TOFILE(MYLIB/MYFILE)
You can replace STDOUT with STDERR or STDIN, and MYFILE with a *PRTF like QSYSPRT.
Another alternative in ILE would be to use freopen() function which closes a file associated with a file pointer and reassigns that file pointer to the other file specified. It is prototyped as FILE *freopen(const char *filename, const char *mode, FILE *stream);
Is there any way to redirect input from a file rather than reading from STDIN (e.g. mypgm < myfile)?
In the OS/400 PASE shells, the standard redirection is used. For the ILE environment, STDIN can be made to override to the file from which input is to be taken using OVRDBF.
OVRDBF FILE(STDIN) TOFILE(MYLIB/MYFILE) MBR(MYMBR)
Another alternative in ILE would be to use freopen() function which closes a file associated with a file pointer and reassigns that file pointer to the other file specified. It is prototyped as FILE *freopen(const char *filename, const char *mode, FILE *stream);
==> cat file1 > file2
==> grep abc < file2
Does OS/400 support a UNIX-like (POSIX) hierarchical file structure?
Yes, since Version 3, Release 1 OS/400 has supported POSIX I/O calls to the OS/400 integrated file system (IFS). Within the IFS, the file system referred to as QOpenSys is case-sensitive, like UNIX file systems.
In ILE, when I tried fopen(), fclose(), etc. on IFS stream files in QOpenSys they do not seem to work, but the low level calls do not have any problems. Is there any difference in these two types of calls?
Yes. The two types of calls are different in the ILE environment. The calls like fopen(), fclose(), fread() work on the database files whereas low-level calls like open(), close(), read() work on the stream files. The low level calls can work on the database files by specifying the full qualified name (i.e. /qsys.lib/< library>.lib/< file>.file/< mbr>.mbr). Calls like fopen(), fclose, and fread() can also work on the stream files in QOpenSys if *IFSIO is specified for "System Interface Option" on CRTCMOD command. Once the program is created with *IFSIO option absolute or relative path names can be specified with fopen(), fclose() etc calls. However, after specifying *IFSIO these call will not work on the native database file system even if fully qualified path name is specified.
How can I binary open *PGM or *MODULE types? The following statement doesn't work:
fd = open("/qsys.lib/mylib.lib/mypgm.pgm", O_RDONLY, 0);
I receive message "The value specified for the argument is not correct." I can use open() command for all *MBR types without problems. On what kind of other object types can I expect troubles?
In order to open() a binary program object, the program object must reside in the hierarchical name space (e.g. QOpenSys). For objects stored in user libraries, e.g. /qsys.lib/mylib.lib, open() (and all IFS interfaces) only work against user spaces, program described physical files, and source files.
Are there ILE C APIs for I/O operation on record files?
Yes. There are APIs like _Ropen, _Rread, _Rformat for record-oriented file I/O.
Does OS/400 support standard file descriptors 0 (standard input), 1 (standard output), and 2 (standard error)?
Yes. In OS/400 PASE, descriptors 0,1 and 2 are supported as STDIN, STDOUT and STDERR. See the OS/400 PASE Redbook for more information about data conversion for these descriptors.
However, to enable descriptor based standard streams an application must set environment variable QIBM_USE_DESCRIPTOR_STDIO equal to "Y".
Descriptor based standard streams (with use of QIBM_USE_DESCRIPTOR_STDIO environment variable) is implemented into the C language runtime for V4R2. The descriptor based standard streams is available in V4R1 with PTF 5769SS1 SF46810. With earlier releases of the C runtime 0, 1 and 2 are not reserved for STDIN, STDOUT, and STDERR.
Without setting QIBM_USE_DESCRIPTOR_STDIO equal to "Y" the iSeries default behavior supports STDIN,STDOUT and STDERR but these are file pointers. File descriptors 0, 1 and 2 are not reserved.
Are file descriptors closed implicitly when a program ends?
Yes, file descriptors are closed when a job ends. However, in OS/400 when a interactive program is called, it does not run in a new, separate job. The interactive program simply calls the program and it is added to the interactive job's call stack. When the called program exits, the original job remains. Only when this job ends (at signoff), are the file descriptors closed. Otherwise, the file descriptors are not closed implicitly and should be closed explicitly. When running programs in an interactive job, descriptors are not implicitly closed until you signoff. When running programs from a UNIX shell, the shell forks another process to run the program. When the program ends, the second process ends and all open descriptors are implicitly closed by the system. The descriptors opened by the program are not available in the process running the shell. Within qsh, the OS/400 qshell, a new process (job) is spawned for each command that is run. Therefore, from qsh, descriptors are closed when the program exits, because that program was running in its own job.
For OS/400 PASE, descriptors opened by an OS/40 PASE program during a call to QP2TERM or QP2SHELL are closed when a program execution completes.
[BACK]
|