This is the mail archive of the
mailing list for the GDB project.
Re: [PATCH] Unbuffer stdout and stderr on windows
- From: Pedro Alves <palves at redhat dot com>
- To: palves at redhat dot com, gdb-patches at sourceware dot org, brobecker at adacore dot com, yao at codesourcery dot com, Eli Zaretskii <eliz at gnu dot org>
- Date: Fri, 16 Aug 2013 12:46:17 +0100
- Subject: Re: [PATCH] Unbuffer stdout and stderr on windows
- References: <51EE23F8 dot 1070905 at codesourcery dot com> <83wqohw4ee dot fsf at gnu dot org> <20130729192559 dot GA5348 at ednor dot casa dot cgf dot cx> <83d2q1xiyv dot fsf at gnu dot org> <51F6C7B2 dot 3020400 at redhat dot com> <20130731034045 dot GA5565 at ednor dot casa dot cgf dot cx> <20130812211105 dot GA11128 at adacore dot com> <8361v9piop dot fsf at gnu dot org> <20130815173618 dot GA6955 at ednor dot casa dot cgf dot cx> <83eh9uonlg dot fsf at gnu dot org> <20130815175940 dot GD6955 at ednor dot casa dot cgf dot cx>
Sorry for chiming in so late...
On 08/15/2013 06:59 PM, Christopher Faylor wrote:
> On Thu, Aug 15, 2013 at 08:44:43PM +0300, Eli Zaretskii wrote:
>> On Thu, 15 Aug 2013 13:36:18 -0400, Christopher Faylor wrote:
>>> I thought that "unbuffered" normally means something like "every output
>>> operation gets immediately sent as a block" rather than "flush after
>>> every character".
>> AFAIK, unbuffered always meant the latter.
>>> If the mingw "unbuffered" mode means that everything is o n e c h a r a
>>> c t e r a t a t i m e
>> It does mean that. Doesn't it work like that in Cygwin?
> Cygwin uses newlib which, AFAICT, writes a block at a time without
> storing the block in a buffer first.
> fwrite (foo, 27, 1, stdout);
> writes 27 bytes to stdout in one shot, without buffering.
> I only got this from looking at the code so I could be wrong.
>>> The other alternative would be to use line buffering for gdb. I don't
>>> see why cygwin pipes (whether they are "ptys" or actual pipes) are a
>>> special case here. stdout is usually line buffered isn't it? Why not
>>> just force that behavior for gdb?
>> That's what I suggested, but Yao says that using line buffering still
>> fails some tests.
> Sorry, I missed that you'd already suggested that.
Quoting that part of previous discussion:
On 08/01/2013 09:05 AM, Yao Qi wrote:
> On 07/29/2013 11:42 PM, Eli Zaretskii wrote:
>>>> + setvbuf (stdout, NULL, _IONBF, BUFSIZ);
>>>> + setvbuf (stderr, NULL, _IONBF, BUFSIZ);
>> How about using line buffering instead on both streams? Or at least
>> leave stdout line-buffered? Did you try that, and if so, did that
>> have the same problems that triggered these patches?
> I tried line-buffering for stdout, but get some regressions in python
> related testing,
That's because there's no such thing as line-buffering on Windows.
For some systems, this provides line buffering. However, for Win32, the behavior
is the same as _IOFBF - Full Buffering.
Also, ISO C (C99/TC3/N1256, 7.19.3 Files, point 7) says:
"As initially opened, the standard error stream is not fully buffered;
the standard input and standard output streams are fully buffered if
and only if the stream can be determined not to refer to an interactive
Note that stderr might be either unbuffered or line buffered,
but _never_ fully buffered. And most implementations default to leaving
stderr always unbuffered (so that error output comes out immediately).
However, the Windows runtime, in its infinite wisdom, makes stderr
fully buffered if connected to a pipe.
So all this makes me very much question the desire to detect
if a native Win32 GDB is running under Cygwin.
IMO, stderr should _always_ be forced to unbuffered.
I can't really imagine that leaving stdout fully buffered to
ever be good (which the cygwin detection seems to want to preserve),
even for frontends, given GDB is an interactive program, and even
MI is text/line based.
So I think the "in cygwin" detection is really not necessary
or desirable, and this patch should go back to its original form:
+ /* A Cygwin ssh session may not look like a terminal to the Windows
+ runtime; ensure unbuffered output. */
+ setvbuf (stdout, NULL, _IONBF, BUFSIZ);
+ setvbuf (stderr, NULL, _IONBF, BUFSIZ);