Subject: Re: bug#46388: 27.1; emacs -batch does not output messages immediately when invoked outside of the command prompt

From: Eli Zaretskii <[email-masked]>
Date: Wed, 10 Feb 2021 17:57:15 +0200

> From: Ioannis Kappas <[email-masked]>
> Date: Wed, 10 Feb 2021 12:48:38 +0000
> 
>     I think I now understand where you are coming from.
> 
>     Let me summarize once more where we are, introducing buffering in
>     the description (assuming MESSAGE length is < 2048):
> 
>     | # | System     | emacs -batch invoked from | MESSAGE behavior
> 
>         |
>     |---+------------+---------------------------+----------------------------------------------------------------------------------------------------|
>     | 1 | Linux      | bash                      | any MESSAGE is
> immediately printed, i.e. stderr is unbuffered
>               |
>     | 2 | Linux      | emacs eshell/shell etc    | >>

Did you try this 2nd item when the connection type for the subprocess
is 'pipe'?  Because otherwise we are comparing apples to oranges.

>     I think I've just realized what you were saying from the
>     beginning. That the difference in behavior is expected, since
>     it is the parent process which decides the buffering regime to be
>     used for the subprocess. Thus in #5, it is emacs on windows that
>     decided to invoke emacs -batch as a subprocess using pipes, which
>     has resulted in emacs -batch's stderr to be buffered.

That is correct.  As we don't support PTYs on Windows, we can only use
pipes for communicating with subprocesses there.

Btw, did you try to play with the value of w32-pipe-buffer-size,
e.g. setting it to a small value?

>     If the current behavior is indeed the correct expected behavior, how do I
>     flush text message to stderr (or even stdout) from an emacs
>     -batch script/eval?

My reading of the code is that we already fflush stderr after emitting
a message, so this should already happen.  See message_to_stderr.  If
that still doesn't help, then there's some buffering in the OS (for
example, in the pipe machinery itself), which we cannot control.

There were some changes in this area lately (that's the discussion
from 2019 I mentioned before): we now try to make a buffered variant
of stderr, and use that for error messages.  The reason, in a
nutshell, is that when you build Emacs with "make -jN", several copies
of the Emacs process can work in parallel, so it was deemed better to
have their messages be emitted atomically, instead of being
interspersed with one another, which produces an illegible mess.
However, that change makes a line-buffered variant of stderr, and on
Windows line buffering is the same as full buffering.  So maybe we
would need more changes in that area, for example some variable to
control this behavior instead of making it unconditional.