This is the mail archive of the cygwin mailing list for the Cygwin project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: fork() + file descriptor bug in 1.7.27(0.271/5/3) 2013-12-09 11:54


In message <20140115163354.GA30234@calimero.vinschen.de>you write:
>--ew6BAiZeqk4r7MaW
>Content-Type: text/plain; charset=utf-8
>Content-Disposition: inline
>Content-Transfer-Encoding: quoted-printable
>
>On Jan 15 10:28, tednolan@bellsouth.net wrote:
>> In message <52D63CE2.9060308@lysator.liu.se>you write:
>> >On 2014-01-15 05:53, Lord Laraby wrote:
>> >> On Tue, Jan 14, 2014 at 10:50 AM, Ted Nolan wrote:
>> >>> In message <52D55D96.8070407@redhat.com> you write:
>> >>>>
>> >>>> Your program may be violating POSIX, which would trigger undefined b=
>ehavio
>> >r.
>> >>>>
>> >>>> Quoting POSIX:
>> >>>> pubs.opengroup.org/onlinepubs/9699919799/functions/V2_chap02.html#ta=
>g_15_0
>> >5
>> >>>>
>> >>>
>> >>> [long quote elided]
>> >>>
>> >>> Yikes!  That's pretty impenatrable.  And if it says what I think it s=
>ays,
>> >>> it seems to violate the way I've understood Unix fork() and how fds
>> >>> (and stdio buffers) are inherited since forever.
>> >>>
>> >>> However..
>> >>>
>> >>> Do I understand that to say that if the first thing my child does is
>> >>>
>> >>>         fclose(fp);
>> >>>
>> >>> everything should be hunky-dory?
>> >>>
>> >>> Because I just tried that, and it's still not.
>> >>=20
>> >> My two cents say, since the child is not referencing 'fp' at all,
>> >> there is no violation of the POSIX semantics in this situation. It
>> >> actually does seem, however, that the fork is closing, or at least
>> >> forgetting the stdio file position of, fp when it forks. A possible
>> >> memory corruption during fork from which fgets can not recover?
>> >
>> >Let me requote one little bit quoted by Eric:
>> >
>> >	                           (If the only action performed by one of the
>> >	processes is one of the exec functions or _exit() (not exit()), the
>> >	handle is never accessed in that process.)
>> >
>> >Ted is using exit() in the children, not _exit(), and the above indicates
>> >that exit() in fact "accesses the handle". My guess would be that fclose=
>(3)
>> >also "accesses the handle".
>> >
>> >But, reading about _exit(), it seems that handle accesses are implementa=
>tion
>> >defined, so I'm not sure it will help in all situations.
>> >
>> >Cheers,
>> >Peter
>>=20
>> Well, all I can say in this instance, is that arguably conforming to
>> the bare letter of the standard (if that's in fact what is happening)
>> is not "the right thing".  People certainly don't expect that stdio
>> file pointers that exist at fork() time and which are never "used" by a
>> child will be reset in the parent.  I mean, if they can't even be fclose(=
>)-ed
>> to take them out of the picture, what chance have you got? -:)
>>=20
>> FWIW, FreeBSD, Linux and Solaris all compile and run the test program
>> with the behavoir I expect..
>
>Just for completeness:  I can test on Linux, but not on FreeBSD and
>Solaris.  Does the testcase also work as expected on both of them,
>after you added fclose to the child?  On Linux it does.
>
>
>Thanks,
>Corinna
>

Well, it appears I spoke too soon about Solaris.  I saw that it terminated
rather than running forever, and assumed it was working correctly.
That turns out not to be the case: For 3 lines in the input file, it somehow
gets up to 8 processes before terminating.

Here's what I can say per OS:

FreeBSD 4.9
FreeBSD 8.1
FreeBSD 9.1

	Original test case works.
	Test case with fclose() works
	Test case with _exit() instead of exit() works

Solaris 9:

	Original test case fails (but terminates)
	Test case with fclose() fails
	Test case with _exit() instead of exit() works

Cygwin:
	Original test case fails (never terminates)
	Test case with fclose() fails
	Test case with _exit() instead of exit() works

Gentoo Linux:
	Original test case works
	Test case with fclose() -- don't have access right now
	Test case with _exit() instead of exit() -- don't have access rght now

So, as per other posters, exit() is wrong and should be _exit().  I accept
that, and will fix it, but it still seems to be that the Linux and FreeBSD
behavior is better here.  If the spec allows "spooky action at a distance",
that's not the same as encouraging it..

--
Problem reports:       http://cygwin.com/problems.html
FAQ:                   http://cygwin.com/faq/
Documentation:         http://cygwin.com/docs.html
Unsubscribe info:      http://cygwin.com/ml/#unsubscribe-simple


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]