aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Albinus2015-09-23 20:34:22 +0200
committerMichael Albinus2015-09-23 20:34:22 +0200
commitcad8aef3241efa0873fb0c003b563cf31a4c0f2e (patch)
tree1649ac34fcef3f59900b6860360460d230e3f7b6
parent4c0fed13e5ca1826bab52cd9c3fc31ad0e5c765c (diff)
downloademacs-cad8aef3241efa0873fb0c003b563cf31a4c0f2e.tar.gz
emacs-cad8aef3241efa0873fb0c003b563cf31a4c0f2e.zip
Continue gfilenotify.c implementation of missing parts
* lisp/filenotify.el (file-notify-add-watch): Append `flags' to `gfile-add-watch' call. (file-notify-rm-watch): Modify `file-notify-descriptors' only after calling the low level functions. * src/gfilenotify.c (dir_monitor_callback): Check, whether event_type is expected. (Fgfile_add_watch): Allow also `change'and `attribute-change' for FLAGS. (Fgfile_rm_watch): Fix typo. (syms_of_gfilenotify): Declare Qchange and Qattribute_change.
-rw-r--r--lisp/filenotify.el34
-rw-r--r--src/gfilenotify.c61
2 files changed, 54 insertions, 41 deletions
diff --git a/lisp/filenotify.el b/lisp/filenotify.el
index e2c0af0d1b7..d48d3f94bc6 100644
--- a/lisp/filenotify.el
+++ b/lisp/filenotify.el
@@ -291,7 +291,7 @@ FILE is the name of the file whose event is being reported."
291 291
292 ;; Determine respective flags. 292 ;; Determine respective flags.
293 (if (eq file-notify--library 'gfilenotify) 293 (if (eq file-notify--library 'gfilenotify)
294 (setq l-flags '(watch-mounts send-moved)) 294 (setq l-flags (append '(watch-mounts send-moved) flags))
295 (when (memq 'change flags) 295 (when (memq 'change flags)
296 (setq 296 (setq
297 l-flags 297 l-flags
@@ -330,7 +330,21 @@ DESCRIPTOR should be an object returned by `file-notify-add-watch'."
330 handler registered) 330 handler registered)
331 331
332 (when (stringp dir) 332 (when (stringp dir)
333 ;; Call low-level function.
333 (setq handler (find-file-name-handler dir 'file-notify-rm-watch)) 334 (setq handler (find-file-name-handler dir 'file-notify-rm-watch))
335 (condition-case nil
336 (if handler
337 ;; A file name handler could exist even if there is no
338 ;; local file notification support.
339 (funcall handler 'file-notify-rm-watch desc)
340
341 (funcall
342 (cond
343 ((eq file-notify--library 'gfilenotify) 'gfile-rm-watch)
344 ((eq file-notify--library 'inotify) 'inotify-rm-watch)
345 ((eq file-notify--library 'w32notify) 'w32notify-rm-watch))
346 desc))
347 (file-notify-error nil))
334 348
335 ;; Modify `file-notify-descriptors'. 349 ;; Modify `file-notify-descriptors'.
336 (if (not file) 350 (if (not file)
@@ -341,23 +355,7 @@ DESCRIPTOR should be an object returned by `file-notify-add-watch'."
341 (delete (assoc file (cdr registered)) (cdr registered))) 355 (delete (assoc file (cdr registered)) (cdr registered)))
342 (if (null (cdr registered)) 356 (if (null (cdr registered))
343 (remhash desc file-notify-descriptors) 357 (remhash desc file-notify-descriptors)
344 (puthash desc registered file-notify-descriptors))) 358 (puthash desc registered file-notify-descriptors))))))
345
346 ;; Call low-level function.
347 (when (null (cdr registered))
348 (condition-case nil
349 (if handler
350 ;; A file name handler could exist even if there is no local
351 ;; file notification support.
352 (funcall handler 'file-notify-rm-watch desc)
353
354 (funcall
355 (cond
356 ((eq file-notify--library 'gfilenotify) 'gfile-rm-watch)
357 ((eq file-notify--library 'inotify) 'inotify-rm-watch)
358 ((eq file-notify--library 'w32notify) 'w32notify-rm-watch))
359 desc))
360 (file-notify-error nil))))))
361 359
362(defun file-notify-valid-p (descriptor) 360(defun file-notify-valid-p (descriptor)
363 "Check a watch specified by its DESCRIPTOR. 361 "Check a watch specified by its DESCRIPTOR.
diff --git a/src/gfilenotify.c b/src/gfilenotify.c
index 1439666f5f8..b5baa30d7a4 100644
--- a/src/gfilenotify.c
+++ b/src/gfilenotify.c
@@ -29,7 +29,7 @@ along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
29#include "process.h" 29#include "process.h"
30 30
31 31
32/* This is a list, elements are triples (DESCRIPTOR FILE CALLBACK) */ 32/* This is a list, elements are triples (DESCRIPTOR FILE FLAGS CALLBACK) */
33static Lisp_Object watch_list; 33static Lisp_Object watch_list;
34 34
35/* This is the callback function for arriving signals from 35/* This is the callback function for arriving signals from
@@ -42,7 +42,7 @@ dir_monitor_callback (GFileMonitor *monitor,
42 GFileMonitorEvent event_type, 42 GFileMonitorEvent event_type,
43 gpointer user_data) 43 gpointer user_data)
44{ 44{
45 Lisp_Object symbol, monitor_object, watch_object; 45 Lisp_Object symbol, monitor_object, watch_object, flags;
46 char *name = g_file_get_parse_name (file); 46 char *name = g_file_get_parse_name (file);
47 char *oname = other_file ? g_file_get_parse_name (other_file) : NULL; 47 char *oname = other_file ? g_file_get_parse_name (other_file) : NULL;
48 48
@@ -84,26 +84,35 @@ dir_monitor_callback (GFileMonitor *monitor,
84 84
85 if (CONSP (watch_object)) 85 if (CONSP (watch_object))
86 { 86 {
87 /* Construct an event. */
88 struct input_event event; 87 struct input_event event;
89 Lisp_Object otail = oname ? list1 (build_string (oname)) : Qnil; 88 Lisp_Object otail = oname ? list1 (build_string (oname)) : Qnil;
90 EVENT_INIT (event); 89
91 event.kind = FILE_NOTIFY_EVENT; 90 /* Check, whether event_type is expected. */
92 event.frame_or_window = Qnil; 91 flags = XCAR (XCDR (XCDR (watch_object)));
93 event.arg = list2 (Fcons (monitor_object, 92 if ((!NILP (Fmember (Qchange, flags)) &&
94 Fcons (symbol, 93 !NILP (Fmember (symbol, list5 (Qchanged, Qchanges_done_hint,
95 Fcons (build_string (name), 94 Qdeleted, Qcreated, Qmoved)))) ||
96 otail))), 95 (!NILP (Fmember (Qattribute_change, flags)) &&
97 XCAR (XCDR (XCDR (watch_object)))); 96 ((EQ (symbol, Qattribute_changed)))))
98 97 {
99 /* Store it into the input event queue. */ 98 /* Construct an event. */
100 kbd_buffer_store_event (&event); 99 EVENT_INIT (event);
100 event.kind = FILE_NOTIFY_EVENT;
101 event.frame_or_window = Qnil;
102 event.arg = list2 (Fcons (monitor_object,
103 Fcons (symbol,
104 Fcons (build_string (name),
105 otail))),
106 XCAR (XCDR (XCDR (XCDR (watch_object)))));
107
108 /* Store it into the input event queue. */
109 kbd_buffer_store_event (&event);
110 // XD_DEBUG_MESSAGE ("%s", XD_OBJECT_TO_STRING (event.arg));
111 }
101 112
102 /* Cancel monitor if file or directory is deleted. */ 113 /* Cancel monitor if file or directory is deleted. */
103 if (((event_type == G_FILE_MONITOR_EVENT_DELETED) || 114 if (!NILP (Fmember (symbol, list2 (Qdeleted, Qmoved))) &&
104 (event_type == G_FILE_MONITOR_EVENT_MOVED)) && 115 !g_file_monitor_is_cancelled (monitor))
105 (strcmp (name, SSDATA (XCAR (XCDR (watch_object)))) == 0) &&
106 (!g_file_monitor_is_cancelled (monitor)))
107 g_file_monitor_cancel (monitor); 116 g_file_monitor_cancel (monitor);
108 } 117 }
109 118
@@ -127,9 +136,13 @@ watched for some reason, this function signals a `file-notify-error' error.
127FLAGS is a list of conditions to set what will be watched for. It can 136FLAGS is a list of conditions to set what will be watched for. It can
128include the following symbols: 137include the following symbols:
129 138
130 `watch-mounts' -- watch for mount events 139 `change' -- watch for file changes
131 `send-moved' -- pair `deleted' and `created' events caused by file 140 `attribute-change' -- watch for file attributes changes, like
132 renames and send a single `renamed' event instead 141 permissions or modification time
142 `watch-mounts' -- watch for mount events
143 `send-moved' -- pair `deleted' and `created' events caused by
144 file renames and send a single `renamed' event
145 instead
133 146
134When any event happens, Emacs will call the CALLBACK function passing 147When any event happens, Emacs will call the CALLBACK function passing
135it a single argument EVENT, which is of the form 148it a single argument EVENT, which is of the form
@@ -206,13 +219,13 @@ will be reported only in case of the `moved' event. */)
206 (GCallback) dir_monitor_callback, NULL); 219 (GCallback) dir_monitor_callback, NULL);
207 220
208 /* Store watch object in watch list. */ 221 /* Store watch object in watch list. */
209 watch_object = list3 (watch_descriptor, file, callback); 222 watch_object = list4 (watch_descriptor, file, flags, callback);
210 watch_list = Fcons (watch_object, watch_list); 223 watch_list = Fcons (watch_object, watch_list);
211 224
212 return watch_descriptor; 225 return watch_descriptor;
213} 226}
214 227
215DEFUN ("gfile-rm-watc", Fgfile_rm_watch, Sgfile_rm_watch, 1, 1, 0, 228DEFUN ("gfile-rm-watch", Fgfile_rm_watch, Sgfile_rm_watch, 1, 1, 0,
216 doc: /* Remove an existing WATCH-DESCRIPTOR. 229 doc: /* Remove an existing WATCH-DESCRIPTOR.
217 230
218WATCH-DESCRIPTOR should be an object returned by `gfile-add-watch'. */) 231WATCH-DESCRIPTOR should be an object returned by `gfile-add-watch'. */)
@@ -279,6 +292,8 @@ syms_of_gfilenotify (void)
279 defsubr (&Sgfile_valid_p); 292 defsubr (&Sgfile_valid_p);
280 293
281 /* Filter objects. */ 294 /* Filter objects. */
295 DEFSYM (Qchange, "change");
296 DEFSYM (Qattribute_change, "attribute-change");
282 DEFSYM (Qwatch_mounts, "watch-mounts"); /* G_FILE_MONITOR_WATCH_MOUNTS */ 297 DEFSYM (Qwatch_mounts, "watch-mounts"); /* G_FILE_MONITOR_WATCH_MOUNTS */
283 DEFSYM (Qsend_moved, "send-moved"); /* G_FILE_MONITOR_SEND_MOVED */ 298 DEFSYM (Qsend_moved, "send-moved"); /* G_FILE_MONITOR_SEND_MOVED */
284 299