Path: utzoo!utgpu!jarvis.csri.toronto.edu!rutgers!cmcl2!adm!xadmx!keith@fstohp.crd.ge.com From: keith@fstohp.crd.ge.com (Keith D Gregory) Newsgroups: comp.unix.wizards Subject: Apparent bug in fclose()-exec()-freopen() sequence Message-ID: <20032@adm.BRL.MIL> Date: 16 Jun 89 18:03:57 GMT Sender: news@adm.BRL.MIL Lines: 70 In short, if one attempts to fclose() files, exec() another program, and freopen() the same files, the freopen() appears to fail. In the specific case, we ran the following programs on an HP-9000 (HP-UX 6.2) and a Mac-2 (A/UX 1.1 beta). The second program failed on the second call to fprintf() (the first completed), leaving beind a core dump. The _iob for StdErr appeared to be in pretty bad shape (as I recall, the character pointers were trashed). As a guess, the startup code in P2 is initalizing its _iob array, and the call to fclose() (as part of freopen()) is thinking that the structure refers to a valid stream. Is this what is happening? Is there any reason (documented) that we should not close a file before exec()ing a program? The obvious workaround (leave them open) is in place, but this application is to run in the background (after a foreground launch), and I don't particularly want any ill-behave programs to start sending data to an unclosed StdFile. Please mail any responses; you will need to explicitly use CRDGW1 as a gateway. Thanks Keith D Gregory keith%fstohp@crdgw1.ge.com # Program 1 Start, Cut here ################################################### #include void main() { fclose( stdin ); fclose( stdout ); fclose( stderr ); execl( "p2", "p2", NULL ); } # Program 2 Start, Cut here ################################################### #include 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 ); if (freopen( "/etc/passwd", "r", stdin) == NULL) perror( "Unable to freopen StdIn" ); else fprintf( stderr, "Reopened StdIn, Flags = %d, FileNo = %d\n", stdin->_flag, stdin->_file ); fflush( stderr ); if (freopen( "/tmp/ix", "w", stdout) == NULL) perror( "Unable to freopen StdOut" ); else fprintf( stderr, "Reopened StdOut, Flags = %d, FileNo = %d\n", stdout->_flag, stdout->_file ); fflush( stderr ); } # Program 2 End, Cut here #####################################################