On Mon, Oct 23, 2023 at 10:12:44PM +0200, Thomas Schmitt wrote: > The one pointed to by Max Nikulin: > > > https://stackoverflow.com/questions/2530663/printf-anomaly-after-fork > > fork clones stdout buffer and child exit flushes its content. > > would halfways explain what i see with unwritten data in the stdout > buffer. But i am not sure that this is what man 2 fork means by: > > * The child inherits copies of the parent's set of open file descripâ > tors. Each file descriptor in the child refers to the same open > file description (see open(2)) as the corresponding file descriptor > in the parent. This means that the two descriptors share open file > status flags, current file offset, and signal-driven I/O attributes > (see the description of F_SETOWN and F_SETSIG in fcntl(2)). > > Further i wonder why i never had such problems with fork() during the > last decades. Will have to inspect my own programs what exactly they do > with stdout around forking.
I feel I only have a partial understanding as well. The fork(2) man page, at least this section, is talking only about the kernel's behavior. The data structure which the kernel maintains for each open file, which is referred to by numeric file descriptor, acts as the man page specifies. This is independent of the memory buffers that the stdio library uses. If a program which is using buffered stdout (printf and friends) calls fork(), with unflushed data still in the output buffer, the buffer gets copied to the child. When the child exits, that buffer gets flushed, which can cause duplication of output once the parent also flushes its copy. What I still don't understand, however, is why sometimes stdin gets rewound (lseek backwards) by the child process. Since the parent and child DO share the kernel's open file structure (as cited in the man page above), when the child rewinds stdin, this affects the parent's file descriptor as well. Thus, the parent re-reads input. This is what's causing the loop to iterate more times than it should, and to re-process input. I believe that was the original question that prompted this thread (note the words "repeat" and "endlessly" in the Subject:), and unfortunately I don't have an answer for it yet.