Re: mutt/2194: mutt hanging in endless loop
The following reply was made to PR mutt/2194; it has been noted by GNATS.
From: Rocco Rutte <pdmef@xxxxxxx>
To: bug-any@xxxxxxxxxxxxx
Cc:
Subject: Re: mutt/2194: mutt hanging in endless loop
Date: Tue, 9 May 2006 11:41:21 +0000
Hi,
* hadmut@xxxxxxxxxx [06-03-08 18:39:26 +0100] wrote:
>An ltrace shows that mutt runs in an endless loop:
>__xstat64(3, "restmail", 0xbfc64cfc) = 0
>wmove(0x812ccc8, 22, 2) = 0
>wrefresh(0x812ccc8, 0, 0xbfc653e8, 0x8063389, 0x812ccc8) = 0
>wtimeout(0x812ccc8, 600000, 0x80fe3f8, 0xb7f4838c, 0x812ccc8) = 600000
>memset(0xbfc64c98, '\000', 140) = 0xbfc64c98
>sigaction(2, 0xbfc64c98, NULL) = 0
>wgetch(0x812ccc8, 0xb7f49554, 0, 0x440d5afe, 0x8180f78) = -1
>memset(0xbfc64c98, '\000', 140) = 0xbfc64c98
>sigaction(2, 0xbfc64c98, NULL) = 0
>wtimeout(0x812ccc8, -1, 0x80fe3f8, 0xb7f4838c, 0x812ccc8) = -1
>__xstat64(3, "restmail", 0xbfc64cfc) = 0
This is the km_dokey() function in keymap.c just right behind the start
of the FOREVER loop.
>It seems as if mutt used the wgetch function of the curses library, but does
>not properly deal with the return value -1 (= ERR)
No, it does:
/* ncurses doesn't return on resized screen when timeout is set to zero */
if (menu != MENU_EDITOR)
timeout ((Timeout > 0 ? Timeout : 60) * 1000);
tmp = mutt_getch();
if (menu != MENU_EDITOR)
timeout (-1); /* restore blocking operation */
LastKey = tmp.ch;
if (LastKey == -1)
return -1;
mutt_getch() properly catches the error and looks okay to me as do all
calls of it (plus getch()).
I'm not a curses expert so this is a wild guess. The first timeout()
call should set a block for later reads (getch() in mutt_getch()) but
since the terminal is closed, the getch() call returns immediately and
mutt thus checks for new mail all the time (I guess 'restmail' is a
mailbox). So it's not really an infinite loop but a loop carried just
way too fast since mutt is supposed to do the same thing anyway.
Since I don't know much about curses, I don't know how to test a
terminal for being present. Really ugly approaches would be to go by
time or write() out some data to stdout which doesn't cause harm and
test the returned value or...
bye, Rocco
--
:wq!