Apparent bug in fclose()-exec()-freopen() sequence

John C. Schettino Jr. john at prcrs.UUCP
Mon Jun 19 22:19:41 AEST 1989


In article <20032 at adm.BRL.MIL>, keith at fstohp.crd.ge.com (Keith D Gregory) writes:
> 
> In short, if one attempts to fclose() files, exec() another program,
> and freopen() the same files, the freopen() appears to fail.  In the
....
> #include <stdio.h>
> 
> void main()
> {
>     fclose( stdin );
>     fclose( stdout );
>     fclose( stderr );
> 
>     execl( "p2", "p2", NULL );
> }

When you exec a program, that program takes its stdin, stdout, and stderr from
the current executable image (this is howe the shell supports redirection.) So
in the example above, "p2" is started with stdin, stdout, and stderr closed,
ie there are no valid file pointers or file descriptors available.

> #include <stdio.h>
> 
> void main()
> {
>     if (freopen( "/dev/tty", "w", stderr) == NULL)
>         exit( -1 );
>     else
>         fprintf( stderr, "Reopened StdErr, Flags = %d, FileNo = %d\n",
>                          stderr->_flag, stderr->_file );
> 
>     fflush( stderr );
> 
>     < ADDITIONAL EXAMPLES REMOVED>
> }

Ok, so program p2 trys to freopen a closed file pointer. The first thing it
does is close a file descriptor which is NOT open. This is "not good", and
your behavior is undefined. Your "work around" of leaving the files open
is actually correct.

Remember that an exec() call starts up an executable which takes many
things from the current executable:
	- open file descriptors (without the close-on-exec flag set, see fcntl)
	- COPY of the environment
	- file pointers for stdin, stdout, stderr (and in PC-DOS, stdprn)
	- current userid, groupid, etc.

Hope this helps...
---------------------
John Schettino : uunet!prcrs!john
[no snappy saying or disclaimer]



More information about the Comp.unix.wizards mailing list