Subject: bug#12447: 24.1.50; Stuck in garbage collection on OS X

From: Dmitry Gutov <[email-masked]>
Date: Sun, 16 Sep 2012 14:44:30 +0400

On 16.09.2012 14:31, Eli Zaretskii wrote:
>> Date: Sun, 16 Sep 2012 13:15:52 +0400
>> From: Dmitry Gutov <[email-masked]>
>> CC: [email-masked], [email-masked]
>>
>> Eli Zaretskii <[email-masked]> writes:
>>
>>   >> Date: Sat, 15 Sep 2012 16:23:53 +0200 (CEST)
>>   >> Cc: [email-masked], [email-masked]
>>   >> From: Harald Hanche-Olsen <[email-masked]>
>>   >>
>>   >> For example: Is it okay to set a timer in a timer callback?
>>   >
>>   > I don't see why not.  Setting up a timer just creates a Lisp object
>>   > and adds it to the list of timers.  The timer will be run the next
>>   > time the low-level mechanism, which is part of the Emacs exec loop,
>>   > determines that it's ripe.
>>
>> In js2-mode's case, the problem is that 'run-with-idle-timer' makes the
>> created timer run now, not the "next time".  Here's an example:
>>
>>     (defvar counter 0)
>>
>>     (defun foo ()
>>       (message (format  "foo %s" counter))
>>       (incf counter)
>>       (run-with-idle-timer 1 nil #'foo))
>>
>>     (foo)
>
> The code above does not run the timer, it just schedules it to run
> after at least 1 sec of idleness time.

Yes. And 1 second later, Emacs effectively freezes (while still 
continuing to show the increasing counter in the message area).

>> I'd expect that either timer would fire once every second (as long as
>> I'm not touching my keyboard), or at least stop firing when I do touch
>> my keyboard (seeing as otherwise Emacs is idle), but instead I just see
>> the timer firing many times a second, the counter runs in the message
>> area, and Emacs doesn't respond to any commands.
>
> Then there's a bug, because an idle timer should only fire when
> there's no other input.  If there's keyboard input, Emacs should
> process it first.
>
> I don't think the bug is related to the fact that the timer handler
> re-schedules itself.  That is something many timers do.  There's
> something else at work here, and that something is most probably on
> the C level.

Like I wrote in 12326, AFAICT, the problem is that timer_check_2 doesn't 
at any point check that Emacs is still idle. When run-with-idle-timer 
calls (timer-activate-when-idle timer t), the new timer is added to the 
list, timer_check_2 reaches is and runs it immediately because 
'timer_idleness_start_time' still has the same value.