--- Begin Message ---
Subject: |
25.0.50; auto-revert-mode reacts slowly even if using an event-driven backend |
Date: |
Wed, 05 Nov 2014 11:01:12 -0800 |
This is a tracker entry for a report and patch in an emacs-devel mailing
list thread:
http://lists.gnu.org/archive/html/emacs-devel/2014-10/msg00727.html
The issue is that auto-revert-mode reacts to modifications on a timer,
even if its backend is event-driven. There is a prototype patch in that
thread, attached here also.
On Linux, the two available backends have issues, so this patch wouldn't
be completely effective until those are resolved.
The gfile backend has a problem where emacs isn't using glib correctly,
and the gfile backend itself, in turn, adds artificial delays in how it
deals with inotify. Those are discussed (and partly patched) here:
http://debbugs.gnu.org/cgi/bugreport.cgi?bug=18861
The inotify backend has an issue where it doesn't deal with more than
one monitored file in a directory correctly:
http://debbugs.gnu.org/cgi/bugreport.cgi?bug=18880
>From 567d8469dfb143786890c65de58bf2ce887e9ebd Mon Sep 17 00:00:00 2001
From: Dima Kogan <address@hidden>
Date: Fri, 24 Oct 2014 19:44:43 -0700
Subject: [PATCH] auto-revert-mode can now revert immediately in response to a
change event
If we have file notifications, we want to update the auto-revert buffers
immediately when a notification occurs. Since file updates can happen very
often, we want to skip some revert operations so that we don't spend all our
time reverting the buffer.
We do this by reverting immediately in response to the first in a flurry of
notifications. We suppress subsequent notifications until the next time
`auto-revert-buffers' is called (this happens on a timer with a period set by
`auto-revert-interval').
---
lisp/autorevert.el | 40 ++++++++++++++++++++++++++++++++++++++++
1 file changed, 40 insertions(+)
diff --git a/lisp/autorevert.el b/lisp/autorevert.el
index f1074e2..7de6ec1 100644
--- a/lisp/autorevert.el
+++ b/lisp/autorevert.el
@@ -531,6 +531,34 @@ will use an up-to-date value of `auto-revert-interval'"
;; Fallback to file checks.
(set (make-local-variable 'auto-revert-use-notify) nil))))
+
+
+;; If we have file notifications, we want to update the auto-revert buffers
+;; immediately when a notification occurs. Since file updates can happen very
+;; often, we want to skip some revert operations so that we don't spend all our
+;; time reverting the buffer.
+;;
+;; We do this by reverting immediately in response to the first in a flurry of
+;; notifications. We suppress subsequent notifications until the next time
+;; `auto-revert-buffers' is called (this happens on a timer with a period set
by
+;; `auto-revert-interval').
+(defvar auto-revert-buffers-counter 1
+ "Incremented each time `auto-revert-buffers' is called")
+(defvar auto-revert-buffers-counter-lockedout 0
+ "Buffer-local value to indicate whether we should immediately
+update the buffer on a notification event or not. If
+
+ (= auto-revert-buffers-counter-lockedout
+ auto-revert-buffers-counter)
+
+then the updates are locked out, and we wait until the next call
+of `auto-revert-buffers' to revert the buffer. If no lockout is
+present, then we revert immediately and set the lockout, so that
+no more reverts are possible until the next call of
+`auto-revert-buffers'")
+(make-variable-buffer-local 'auto-revert-buffers-counter-lockedout)
+
+
(defun auto-revert-notify-handler (event)
"Handle an EVENT returned from file notification."
(with-demoted-errors
@@ -566,6 +594,14 @@ will use an up-to-date value of `auto-revert-interval'"
(file-name-nondirectory buffer-file-name)))))
;; Mark buffer modified.
(setq auto-revert-notify-modified-p t)
+
+ ;; Revert the buffer now if we're not locked out
+ (when (/= auto-revert-buffers-counter-lockedout
+ auto-revert-buffers-counter)
+ (auto-revert-handler)
+ (setq auto-revert-buffers-counter-lockedout
+ auto-revert-buffers-counter))
+
;; No need to check other buffers.
(cl-return)))))))))
@@ -686,6 +722,10 @@ are checked first the next time this function is called.
This function is also responsible for removing buffers no longer in
Auto-Revert mode from `auto-revert-buffer-list', and for canceling
the timer when no buffers need to be checked."
+
+ (setq auto-revert-buffers-counter
+ (1+ auto-revert-buffers-counter))
+
(save-match-data
(let ((bufs (if global-auto-revert-mode
(buffer-list)
--
2.0.0
--- End Message ---
--- Begin Message ---
Subject: |
Re: bug#18958: 25.0.50; auto-revert-mode reacts slowly even if using an event-driven backend |
Date: |
Sun, 22 Feb 2015 10:53:03 +0100 |
User-agent: |
Gnus/5.13 (Gnus v5.13) Emacs/25.0.50 (gnu/linux) |
Dima Kogan <address@hidden> writes:
> Hi. I just tested auto-revert-mode with gfilenotify, and it does appear
> to work. Thank you very much for merging those patches!
I'm marking this bug as closed.
> In a perfect world, this 1-second delay would be removed upstream, and
> we'd use gfilenotify for everything. In the meantime, is gfilenotify
> better in any way on Linux? If the notifications are unavailable for
> some reason (network-mounted file for instance), then emacs simply
> decays to the normal polled notifications, right?
You mean auto-revert, right? And yes, if `file-notify-add-watch' doesn't
return a proper watch descriptor, auto-revert falls back to its polling
mode.
glib is said to use also polling for file systems where you don't have
native file notification support. This would make it superior to inotify
for mounted filesystems, and alike.
Best regards, Michael.
--- End Message ---