zsh-workers
 help / color / mirror / code / Atom feed
From: Roman Perepelitsa <roman.perepelitsa@gmail.com>
To: zsh-workers@zsh.org
Subject: Functions registered with zle -F stop being run after a job finishes
Date: Sat, 23 Mar 2019 14:55:40 +0100	[thread overview]
Message-ID: <CAN=4vMp8fkVKWXKXop7WjEWJYxhfkK3nEq0C4V8rj76Gs2XsXg@mail.gmail.com> (raw)

[-- Attachment #1: Type: text/plain, Size: 2306 bytes --]

Hi,

tl;dr: There appears to be a bug in zsh. When a background job finishes,
functions registered with zle -F stop running until the user presses a key
(say, [enter] or [esc]) or the shell receives a signal (any signal at all).

Assuming the pristine environment granted by zsh -df, consider the
following piece of code.

mkfifo /tmp/fifoexec {fd}<>/tmp/fifo
( for ((i=1;;++i)); do sleep 1; echo $i; done ) >&$fd &
function f() { zle -I && read -eu $fd }
zle -F $fd f
sleep 5&
( sleep 10; kill -WINCH $$ ) &

It creates a fifo, to which a background job writes consecutive numbers
once a second. It then uses zle -F to register a function that gets called
whenever there is something in the fifo. The function reads and prints the
content of the fifo.

This part of the code produces the following output:

adam%
1
adam%
2
adam%
3

And so on, with one line every second. The code also creates a background
job that doesn’t do anything and finishes after 5 seconds. The expected
behavior is that we’ll keep seeing consecutive numbers on the screen after
this job finishes but that’s not what happens. In fact, the output stops.

adam%
4
adam%
[2]  + done       sleep 5
adam%

If we hit [esc] or [enter] at this point, the missing numbers will appear
all at once and the new numbers will continue being printed once a second.

Instead of pressing a key we can send our shell a signal. It’ll have the
same effect. Any signal will do as long as it doesn’t kill the process. For
example, we can define a signal handler for SIGUSR1 and execute kill -USR1
$pid from another shell. Or, like the code snippet does, we can send
SIGWINCH, taking advantage of its having the default handler that does
nothing.

Here’s the complete output where you can see everything in action:

adam% mkfifo /tmp/fifo
exec {fd}<>/tmp/fifo
( for ((i=1;;++i)); do sleep 1; echo $i; done ) >&$fd &
function f() { zle -I && read -eu $fd }
zle -F $fd f
sleep 5&
( sleep 10; kill -WINCH $$ ) &
[1] 9468
[2] 9469
[3] 9471
adam%
1
adam%
2
adam%
3
adam%
4
adam%
[2]  - done       sleep 5
adam%
5
[3]  + done       ( sleep 10; kill -WINCH $$; )
adam% adam%
6
adam%
7
adam%
8
adam%
9
adam%
10
adam%
11
adam%
12
adam%

And so on.

Roman.

             reply	other threads:[~2019-03-23 13:56 UTC|newest]

Thread overview: 7+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-03-23 13:55 Roman Perepelitsa [this message]
2019-03-23 18:30 ` Peter Stephenson
2019-03-27 19:01   ` Peter Stephenson
2019-03-28 10:31     ` Roman Perepelitsa
2019-03-25 22:11 ` Roman Perepelitsa
2019-03-26  9:22   ` Peter Stephenson
2019-03-26  9:36     ` Roman Perepelitsa

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='CAN=4vMp8fkVKWXKXop7WjEWJYxhfkK3nEq0C4V8rj76Gs2XsXg@mail.gmail.com' \
    --to=roman.perepelitsa@gmail.com \
    --cc=zsh-workers@zsh.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.vuxu.org/mirror/zsh/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).