diff options
| author | Michael Albinus | 2015-11-09 10:00:56 +0100 |
|---|---|---|
| committer | Michael Albinus | 2015-11-25 15:07:10 +0100 |
| commit | e3354e2265bc442e4c7b84b806be482db88581a2 (patch) | |
| tree | 21c79b24540c150ada3fe3b7c7941985327cc16f /src | |
| parent | c6457cef92342d586d894504fdefc1bec1367725 (diff) | |
| download | emacs-e3354e2265bc442e4c7b84b806be482db88581a2.tar.gz emacs-e3354e2265bc442e4c7b84b806be482db88581a2.zip | |
Add kqueue support
* configure.ac (--with-file-notification): Add kqueue.
(top): Remove special test for "${HAVE_NS}" and
${with_file_notification}, this is handled inside gfilenotify
tests. Add kqueue tests. Use NOTIFY_CFLAGS and NOTIFY_LIBS
instead of library specific variables.
* src/Makefile.in: Use NOTIFY_CFLAGS and NOTIFY_LIBS.
* src/emacs.c (main): Call globals_of_kqueue and syms_of_kqueue.
* src/kqueue.c: New file.
* src/lisp.h: Declare extern globals_of_kqueue and syms_of_kqueue.
Diffstat (limited to 'src')
| -rw-r--r-- | src/Makefile.in | 11 | ||||
| -rw-r--r-- | src/emacs.c | 16 | ||||
| -rw-r--r-- | src/kqueue.c | 339 | ||||
| -rw-r--r-- | src/lisp.h | 16 |
4 files changed, 368 insertions, 14 deletions
diff --git a/src/Makefile.in b/src/Makefile.in index d667c55ee33..d7ad3954579 100644 --- a/src/Makefile.in +++ b/src/Makefile.in | |||
| @@ -160,12 +160,13 @@ SETTINGS_LIBS = @SETTINGS_LIBS@ | |||
| 160 | ## gtkutil.o if USE_GTK, else empty. | 160 | ## gtkutil.o if USE_GTK, else empty. |
| 161 | GTK_OBJ=@GTK_OBJ@ | 161 | GTK_OBJ=@GTK_OBJ@ |
| 162 | 162 | ||
| 163 | ## gfilenotify.o if HAVE_GFILENOTIFY. | ||
| 164 | ## inotify.o if HAVE_INOTIFY. | 163 | ## inotify.o if HAVE_INOTIFY. |
| 164 | ## kqueue.o if HAVE_KQUEUE. | ||
| 165 | ## gfilenotify.o if HAVE_GFILENOTIFY. | ||
| 165 | ## w32notify.o if HAVE_W32NOTIFY. | 166 | ## w32notify.o if HAVE_W32NOTIFY. |
| 166 | NOTIFY_OBJ = @NOTIFY_OBJ@ | 167 | NOTIFY_OBJ = @NOTIFY_OBJ@ |
| 167 | GFILENOTIFY_CFLAGS = @GFILENOTIFY_CFLAGS@ | 168 | NOTIFY_CFLAGS = @NOTIFY_CFLAGS@ |
| 168 | GFILENOTIFY_LIBS = @GFILENOTIFY_LIBS@ | 169 | NOTIFY_LIBS = @NOTIFY_LIBS@ |
| 169 | 170 | ||
| 170 | ## -ltermcap, or -lncurses, or -lcurses, or "". | 171 | ## -ltermcap, or -lncurses, or -lcurses, or "". |
| 171 | LIBS_TERMCAP=@LIBS_TERMCAP@ | 172 | LIBS_TERMCAP=@LIBS_TERMCAP@ |
| @@ -355,7 +356,7 @@ ALL_CFLAGS=-Demacs $(MYCPPFLAGS) -I. -I$(srcdir) \ | |||
| 355 | $(XRANDR_CFLAGS) $(XINERAMA_CFLAGS) $(XFIXES_CFLAGS) \ | 356 | $(XRANDR_CFLAGS) $(XINERAMA_CFLAGS) $(XFIXES_CFLAGS) \ |
| 356 | $(SETTINGS_CFLAGS) $(FREETYPE_CFLAGS) $(FONTCONFIG_CFLAGS) \ | 357 | $(SETTINGS_CFLAGS) $(FREETYPE_CFLAGS) $(FONTCONFIG_CFLAGS) \ |
| 357 | $(LIBOTF_CFLAGS) $(M17N_FLT_CFLAGS) $(DEPFLAGS) \ | 358 | $(LIBOTF_CFLAGS) $(M17N_FLT_CFLAGS) $(DEPFLAGS) \ |
| 358 | $(LIBGNUTLS_CFLAGS) $(GFILENOTIFY_CFLAGS) $(CAIRO_CFLAGS) \ | 359 | $(LIBGNUTLS_CFLAGS) $(NOTIFY_CFLAGS) $(CAIRO_CFLAGS) \ |
| 359 | $(WARN_CFLAGS) $(WERROR_CFLAGS) $(CFLAGS) | 360 | $(WARN_CFLAGS) $(WERROR_CFLAGS) $(CFLAGS) |
| 360 | ALL_OBJC_CFLAGS=$(ALL_CFLAGS) $(GNU_OBJC_CFLAGS) | 361 | ALL_OBJC_CFLAGS=$(ALL_CFLAGS) $(GNU_OBJC_CFLAGS) |
| 361 | 362 | ||
| @@ -468,7 +469,7 @@ LIBES = $(LIBS) $(W32_LIBS) $(LIBS_GNUSTEP) $(LIBX_BASE) $(LIBIMAGE) \ | |||
| 468 | $(LIBS_TERMCAP) $(GETLOADAVG_LIBS) $(SETTINGS_LIBS) $(LIBSELINUX_LIBS) \ | 469 | $(LIBS_TERMCAP) $(GETLOADAVG_LIBS) $(SETTINGS_LIBS) $(LIBSELINUX_LIBS) \ |
| 469 | $(FREETYPE_LIBS) $(FONTCONFIG_LIBS) $(LIBOTF_LIBS) $(M17N_FLT_LIBS) \ | 470 | $(FREETYPE_LIBS) $(FONTCONFIG_LIBS) $(LIBOTF_LIBS) $(M17N_FLT_LIBS) \ |
| 470 | $(LIBGNUTLS_LIBS) $(LIB_PTHREAD) \ | 471 | $(LIBGNUTLS_LIBS) $(LIB_PTHREAD) \ |
| 471 | $(GFILENOTIFY_LIBS) $(LIB_MATH) $(LIBZ) | 472 | $(NOTIFY_LIBS) $(LIB_MATH) $(LIBZ) |
| 472 | 473 | ||
| 473 | $(leimdir)/leim-list.el: bootstrap-emacs$(EXEEXT) | 474 | $(leimdir)/leim-list.el: bootstrap-emacs$(EXEEXT) |
| 474 | $(MAKE) -C ../leim leim-list.el EMACS="$(bootstrap_exe)" | 475 | $(MAKE) -C ../leim leim-list.el EMACS="$(bootstrap_exe)" |
diff --git a/src/emacs.c b/src/emacs.c index b4052b851d7..2e9f950851a 100644 --- a/src/emacs.c +++ b/src/emacs.c | |||
| @@ -1350,6 +1350,10 @@ Using an Emacs configured with --with-x-toolkit=lucid does not have this problem | |||
| 1350 | tzset (); | 1350 | tzset (); |
| 1351 | #endif /* MSDOS */ | 1351 | #endif /* MSDOS */ |
| 1352 | 1352 | ||
| 1353 | #ifdef HAVE_KQUEUE | ||
| 1354 | globals_of_kqueue (); | ||
| 1355 | #endif | ||
| 1356 | |||
| 1353 | #ifdef HAVE_GFILENOTIFY | 1357 | #ifdef HAVE_GFILENOTIFY |
| 1354 | globals_of_gfilenotify (); | 1358 | globals_of_gfilenotify (); |
| 1355 | #endif | 1359 | #endif |
| @@ -1520,14 +1524,18 @@ Using an Emacs configured with --with-x-toolkit=lucid does not have this problem | |||
| 1520 | 1524 | ||
| 1521 | syms_of_gnutls (); | 1525 | syms_of_gnutls (); |
| 1522 | 1526 | ||
| 1523 | #ifdef HAVE_GFILENOTIFY | ||
| 1524 | syms_of_gfilenotify (); | ||
| 1525 | #endif /* HAVE_GFILENOTIFY */ | ||
| 1526 | |||
| 1527 | #ifdef HAVE_INOTIFY | 1527 | #ifdef HAVE_INOTIFY |
| 1528 | syms_of_inotify (); | 1528 | syms_of_inotify (); |
| 1529 | #endif /* HAVE_INOTIFY */ | 1529 | #endif /* HAVE_INOTIFY */ |
| 1530 | 1530 | ||
| 1531 | #ifdef HAVE_KQUEUE | ||
| 1532 | syms_of_kqueue (); | ||
| 1533 | #endif /* HAVE_KQUEUE */ | ||
| 1534 | |||
| 1535 | #ifdef HAVE_GFILENOTIFY | ||
| 1536 | syms_of_gfilenotify (); | ||
| 1537 | #endif /* HAVE_GFILENOTIFY */ | ||
| 1538 | |||
| 1531 | #ifdef HAVE_DBUS | 1539 | #ifdef HAVE_DBUS |
| 1532 | syms_of_dbusbind (); | 1540 | syms_of_dbusbind (); |
| 1533 | #endif /* HAVE_DBUS */ | 1541 | #endif /* HAVE_DBUS */ |
diff --git a/src/kqueue.c b/src/kqueue.c new file mode 100644 index 00000000000..69bf5f61080 --- /dev/null +++ b/src/kqueue.c | |||
| @@ -0,0 +1,339 @@ | |||
| 1 | /* Filesystem notifications support with glib API. | ||
| 2 | Copyright (C) 2013-2015 Free Software Foundation, Inc. | ||
| 3 | |||
| 4 | This file is part of GNU Emacs. | ||
| 5 | |||
| 6 | GNU Emacs is free software: you can redistribute it and/or modify | ||
| 7 | it under the terms of the GNU General Public License as published by | ||
| 8 | the Free Software Foundation, either version 3 of the License, or | ||
| 9 | (at your option) any later version. | ||
| 10 | |||
| 11 | GNU Emacs is distributed in the hope that it will be useful, | ||
| 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 14 | GNU General Public License for more details. | ||
| 15 | |||
| 16 | You should have received a copy of the GNU General Public License | ||
| 17 | along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */ | ||
| 18 | |||
| 19 | #include <config.h> | ||
| 20 | |||
| 21 | #ifdef HAVE_KQUEUE | ||
| 22 | #include <stdio.h> | ||
| 23 | #include <sys/event.h> | ||
| 24 | #include "lisp.h" | ||
| 25 | #include "coding.h" | ||
| 26 | #include "termhooks.h" | ||
| 27 | #include "keyboard.h" | ||
| 28 | |||
| 29 | |||
| 30 | /* File handle for kqueue. */ | ||
| 31 | static int kqueuefd = -1; | ||
| 32 | |||
| 33 | /* This is a list, elements are triples (DESCRIPTOR FILE FLAGS CALLBACK) */ | ||
| 34 | static Lisp_Object watch_list; | ||
| 35 | |||
| 36 | #if 0 | ||
| 37 | /* This is the callback function for arriving signals from | ||
| 38 | g_file_monitor. It shall create a Lisp event, and put it into | ||
| 39 | Emacs input queue. */ | ||
| 40 | static gboolean | ||
| 41 | dir_monitor_callback (GFileMonitor *monitor, | ||
| 42 | GFile *file, | ||
| 43 | GFile *other_file, | ||
| 44 | GFileMonitorEvent event_type, | ||
| 45 | gpointer user_data) | ||
| 46 | { | ||
| 47 | Lisp_Object symbol, monitor_object, watch_object, flags; | ||
| 48 | char *name = g_file_get_parse_name (file); | ||
| 49 | char *oname = other_file ? g_file_get_parse_name (other_file) : NULL; | ||
| 50 | |||
| 51 | /* Determine event symbol. */ | ||
| 52 | switch (event_type) | ||
| 53 | { | ||
| 54 | case G_FILE_MONITOR_EVENT_CHANGED: | ||
| 55 | symbol = Qchanged; | ||
| 56 | break; | ||
| 57 | case G_FILE_MONITOR_EVENT_CHANGES_DONE_HINT: | ||
| 58 | symbol = Qchanges_done_hint; | ||
| 59 | break; | ||
| 60 | case G_FILE_MONITOR_EVENT_DELETED: | ||
| 61 | symbol = Qdeleted; | ||
| 62 | break; | ||
| 63 | case G_FILE_MONITOR_EVENT_CREATED: | ||
| 64 | symbol = Qcreated; | ||
| 65 | break; | ||
| 66 | case G_FILE_MONITOR_EVENT_ATTRIBUTE_CHANGED: | ||
| 67 | symbol = Qattribute_changed; | ||
| 68 | break; | ||
| 69 | case G_FILE_MONITOR_EVENT_PRE_UNMOUNT: | ||
| 70 | symbol = Qpre_unmount; | ||
| 71 | break; | ||
| 72 | case G_FILE_MONITOR_EVENT_UNMOUNTED: | ||
| 73 | symbol = Qunmounted; | ||
| 74 | break; | ||
| 75 | case G_FILE_MONITOR_EVENT_MOVED: | ||
| 76 | symbol = Qmoved; | ||
| 77 | break; | ||
| 78 | default: | ||
| 79 | goto cleanup; | ||
| 80 | } | ||
| 81 | |||
| 82 | /* Determine callback function. */ | ||
| 83 | monitor_object = make_pointer_integer (monitor); | ||
| 84 | eassert (INTEGERP (monitor_object)); | ||
| 85 | watch_object = assq_no_quit (monitor_object, watch_list); | ||
| 86 | |||
| 87 | if (CONSP (watch_object)) | ||
| 88 | { | ||
| 89 | struct input_event event; | ||
| 90 | Lisp_Object otail = oname ? list1 (build_string (oname)) : Qnil; | ||
| 91 | |||
| 92 | /* Check, whether event_type is expected. */ | ||
| 93 | flags = XCAR (XCDR (XCDR (watch_object))); | ||
| 94 | if ((!NILP (Fmember (Qchange, flags)) && | ||
| 95 | !NILP (Fmember (symbol, list5 (Qchanged, Qchanges_done_hint, | ||
| 96 | Qdeleted, Qcreated, Qmoved)))) || | ||
| 97 | (!NILP (Fmember (Qattribute_change, flags)) && | ||
| 98 | ((EQ (symbol, Qattribute_changed))))) | ||
| 99 | { | ||
| 100 | /* Construct an event. */ | ||
| 101 | EVENT_INIT (event); | ||
| 102 | event.kind = FILE_NOTIFY_EVENT; | ||
| 103 | event.frame_or_window = Qnil; | ||
| 104 | event.arg = list2 (Fcons (monitor_object, | ||
| 105 | Fcons (symbol, | ||
| 106 | Fcons (build_string (name), | ||
| 107 | otail))), | ||
| 108 | XCAR (XCDR (XCDR (XCDR (watch_object))))); | ||
| 109 | |||
| 110 | /* Store it into the input event queue. */ | ||
| 111 | kbd_buffer_store_event (&event); | ||
| 112 | // XD_DEBUG_MESSAGE ("%s", XD_OBJECT_TO_STRING (event.arg)); | ||
| 113 | } | ||
| 114 | |||
| 115 | /* Cancel monitor if file or directory is deleted. */ | ||
| 116 | if (!NILP (Fmember (symbol, list2 (Qdeleted, Qmoved))) && | ||
| 117 | (strcmp (name, SSDATA (XCAR (XCDR (watch_object)))) == 0) && | ||
| 118 | !g_file_monitor_is_cancelled (monitor)) | ||
| 119 | g_file_monitor_cancel (monitor); | ||
| 120 | } | ||
| 121 | |||
| 122 | /* Cleanup. */ | ||
| 123 | cleanup: | ||
| 124 | g_free (name); | ||
| 125 | g_free (oname); | ||
| 126 | |||
| 127 | return TRUE; | ||
| 128 | } | ||
| 129 | #endif /* 0 */ | ||
| 130 | |||
| 131 | DEFUN ("kqueue-add-watch", Fkqueue_add_watch, Skqueue_add_watch, 3, 3, 0, | ||
| 132 | doc: /* Add a watch for filesystem events pertaining to FILE. | ||
| 133 | |||
| 134 | This arranges for filesystem events pertaining to FILE to be reported | ||
| 135 | to Emacs. Use `gfile-rm-watch' to cancel the watch. | ||
| 136 | |||
| 137 | Value is a descriptor for the added watch. If the file cannot be | ||
| 138 | watched for some reason, this function signals a `file-notify-error' error. | ||
| 139 | |||
| 140 | FLAGS is a list of conditions to set what will be watched for. It can | ||
| 141 | include the following symbols: | ||
| 142 | |||
| 143 | `change' -- watch for file changes | ||
| 144 | `attribute-change' -- watch for file attributes changes, like | ||
| 145 | permissions or modification time | ||
| 146 | `watch-mounts' -- watch for mount events | ||
| 147 | `send-moved' -- pair `deleted' and `created' events caused by | ||
| 148 | file renames and send a single `renamed' event | ||
| 149 | instead | ||
| 150 | |||
| 151 | When any event happens, Emacs will call the CALLBACK function passing | ||
| 152 | it a single argument EVENT, which is of the form | ||
| 153 | |||
| 154 | (DESCRIPTOR ACTION FILE [FILE1]) | ||
| 155 | |||
| 156 | DESCRIPTOR is the same object as the one returned by this function. | ||
| 157 | ACTION is the description of the event. It could be any one of the | ||
| 158 | following: | ||
| 159 | |||
| 160 | `changed' -- FILE has changed | ||
| 161 | `changes-done-hint' -- a hint that this was probably the last change | ||
| 162 | in a set of changes | ||
| 163 | `deleted' -- FILE was deleted | ||
| 164 | `created' -- FILE was created | ||
| 165 | `attribute-changed' -- a FILE attribute was changed | ||
| 166 | `pre-unmount' -- the FILE location will soon be unmounted | ||
| 167 | `unmounted' -- the FILE location was unmounted | ||
| 168 | `moved' -- FILE was moved to FILE1 | ||
| 169 | |||
| 170 | FILE is the name of the file whose event is being reported. FILE1 | ||
| 171 | will be reported only in case of the `moved' event. */) | ||
| 172 | (Lisp_Object file, Lisp_Object flags, Lisp_Object callback) | ||
| 173 | { | ||
| 174 | Lisp_Object watch_object; | ||
| 175 | GFile *gfile; | ||
| 176 | GFileMonitor *monitor; | ||
| 177 | GFileMonitorFlags gflags = G_FILE_MONITOR_NONE; | ||
| 178 | GError *gerror = NULL; | ||
| 179 | |||
| 180 | /* Check parameters. */ | ||
| 181 | CHECK_STRING (file); | ||
| 182 | file = Fdirectory_file_name (Fexpand_file_name (file, Qnil)); | ||
| 183 | if (NILP (Ffile_exists_p (file))) | ||
| 184 | report_file_error ("File does not exist", file); | ||
| 185 | |||
| 186 | CHECK_LIST (flags); | ||
| 187 | |||
| 188 | if (!FUNCTIONP (callback)) | ||
| 189 | wrong_type_argument (Qinvalid_function, callback); | ||
| 190 | |||
| 191 | /* Create GFile name. */ | ||
| 192 | // gfile = g_file_new_for_path (SSDATA (ENCODE_FILE (file))); | ||
| 193 | |||
| 194 | /* Assemble flags. */ | ||
| 195 | // if (!NILP (Fmember (Qwatch_mounts, flags))) | ||
| 196 | // gflags |= G_FILE_MONITOR_WATCH_MOUNTS; | ||
| 197 | // if (!NILP (Fmember (Qsend_moved, flags))) | ||
| 198 | // gflags |= G_FILE_MONITOR_SEND_MOVED; | ||
| 199 | |||
| 200 | if (kqueuefd < 0) | ||
| 201 | { | ||
| 202 | kqueuefd = kqueue (); | ||
| 203 | if (kqueuefd < 0) | ||
| 204 | report_file_notify_error ("File watching is not available", Qnil); | ||
| 205 | watch_list = Qnil; | ||
| 206 | // add_read_fd (inotifyfd, &inotify_callback, NULL); | ||
| 207 | } | ||
| 208 | |||
| 209 | |||
| 210 | } | ||
| 211 | #if 0 | ||
| 212 | |||
| 213 | mask = aspect_to_inotifymask (aspect); | ||
| 214 | encoded_file_name = ENCODE_FILE (file_name); | ||
| 215 | watchdesc = inotify_add_watch (inotifyfd, SSDATA (encoded_file_name), mask); | ||
| 216 | if (watchdesc == -1) | ||
| 217 | report_file_notify_error ("Could not add watch for file", file_name); | ||
| 218 | |||
| 219 | /* Enable watch. */ | ||
| 220 | monitor = g_file_monitor (gfile, gflags, NULL, &gerror); | ||
| 221 | g_object_unref (gfile); | ||
| 222 | if (gerror) | ||
| 223 | { | ||
| 224 | char msg[1024]; | ||
| 225 | strcpy (msg, gerror->message); | ||
| 226 | g_error_free (gerror); | ||
| 227 | xsignal1 (Qfile_notify_error, build_string (msg)); | ||
| 228 | } | ||
| 229 | if (! monitor) | ||
| 230 | xsignal2 (Qfile_notify_error, build_string ("Cannot watch file"), file); | ||
| 231 | |||
| 232 | Lisp_Object watch_descriptor = make_pointer_integer (monitor); | ||
| 233 | |||
| 234 | /* Check the dicey assumption that make_pointer_integer is safe. */ | ||
| 235 | if (! INTEGERP (watch_descriptor)) | ||
| 236 | { | ||
| 237 | g_object_unref (monitor); | ||
| 238 | xsignal2 (Qfile_notify_error, build_string ("Unsupported file watcher"), | ||
| 239 | file); | ||
| 240 | } | ||
| 241 | |||
| 242 | /* The default rate limit is 800 msec. We adapt this. */ | ||
| 243 | g_file_monitor_set_rate_limit (monitor, 100); | ||
| 244 | |||
| 245 | /* Subscribe to the "changed" signal. */ | ||
| 246 | g_signal_connect (monitor, "changed", | ||
| 247 | (GCallback) dir_monitor_callback, NULL); | ||
| 248 | |||
| 249 | /* Store watch object in watch list. */ | ||
| 250 | watch_object = list4 (watch_descriptor, file, flags, callback); | ||
| 251 | watch_list = Fcons (watch_object, watch_list); | ||
| 252 | |||
| 253 | return watch_descriptor; | ||
| 254 | } | ||
| 255 | |||
| 256 | DEFUN ("gfile-rm-watch", Fgfile_rm_watch, Sgfile_rm_watch, 1, 1, 0, | ||
| 257 | doc: /* Remove an existing WATCH-DESCRIPTOR. | ||
| 258 | |||
| 259 | WATCH-DESCRIPTOR should be an object returned by `gfile-add-watch'. */) | ||
| 260 | (Lisp_Object watch_descriptor) | ||
| 261 | { | ||
| 262 | Lisp_Object watch_object = assq_no_quit (watch_descriptor, watch_list); | ||
| 263 | |||
| 264 | if (! CONSP (watch_object)) | ||
| 265 | xsignal2 (Qfile_notify_error, build_string ("Not a watch descriptor"), | ||
| 266 | watch_descriptor); | ||
| 267 | |||
| 268 | eassert (INTEGERP (watch_descriptor)); | ||
| 269 | GFileMonitor *monitor = XINTPTR (watch_descriptor); | ||
| 270 | if (!g_file_monitor_is_cancelled (monitor) && | ||
| 271 | !g_file_monitor_cancel (monitor)) | ||
| 272 | xsignal2 (Qfile_notify_error, build_string ("Could not rm watch"), | ||
| 273 | watch_descriptor); | ||
| 274 | |||
| 275 | /* Remove watch descriptor from watch list. */ | ||
| 276 | watch_list = Fdelq (watch_object, watch_list); | ||
| 277 | |||
| 278 | /* Cleanup. */ | ||
| 279 | g_object_unref (monitor); | ||
| 280 | |||
| 281 | return Qt; | ||
| 282 | } | ||
| 283 | |||
| 284 | DEFUN ("gfile-valid-p", Fgfile_valid_p, Sgfile_valid_p, 1, 1, 0, | ||
| 285 | doc: /* "Check a watch specified by its WATCH-DESCRIPTOR. | ||
| 286 | |||
| 287 | WATCH-DESCRIPTOR should be an object returned by `gfile-add-watch'. | ||
| 288 | |||
| 289 | A watch can become invalid if the file or directory it watches is | ||
| 290 | deleted, or if the watcher thread exits abnormally for any other | ||
| 291 | reason. Removing the watch by calling `gfile-rm-watch' also makes it | ||
| 292 | invalid. */) | ||
| 293 | (Lisp_Object watch_descriptor) | ||
| 294 | { | ||
| 295 | Lisp_Object watch_object = Fassoc (watch_descriptor, watch_list); | ||
| 296 | if (NILP (watch_object)) | ||
| 297 | return Qnil; | ||
| 298 | else | ||
| 299 | { | ||
| 300 | GFileMonitor *monitor = XINTPTR (watch_descriptor); | ||
| 301 | return g_file_monitor_is_cancelled (monitor) ? Qnil : Qt; | ||
| 302 | } | ||
| 303 | } | ||
| 304 | #endif /* 0 */ | ||
| 305 | |||
| 306 | |||
| 307 | void | ||
| 308 | globals_of_kqueue (void) | ||
| 309 | { | ||
| 310 | watch_list = Qnil; | ||
| 311 | } | ||
| 312 | |||
| 313 | void | ||
| 314 | syms_of_kqueue (void) | ||
| 315 | { | ||
| 316 | defsubr (&Skqueue_add_watch); | ||
| 317 | // defsubr (&Skqueue_rm_watch); | ||
| 318 | // defsubr (&Skqueue_valid_p); | ||
| 319 | |||
| 320 | /* Filter objects. */ | ||
| 321 | DEFSYM (Qchange, "change"); | ||
| 322 | DEFSYM (Qattribute_change, "attribute-change"); | ||
| 323 | DEFSYM (Qwatch_mounts, "watch-mounts"); /* G_FILE_MONITOR_WATCH_MOUNTS */ | ||
| 324 | DEFSYM (Qsend_moved, "send-moved"); /* G_FILE_MONITOR_SEND_MOVED */ | ||
| 325 | |||
| 326 | /* Event types. */ | ||
| 327 | DEFSYM (Qdelete, "delete"); /* NOTE_DELETE */ | ||
| 328 | DEFSYM (Qwrite, "write"); /* NOTE_WRITE */ | ||
| 329 | DEFSYM (Qextend, "extend"); /* NOTE_EXTEND */ | ||
| 330 | DEFSYM (Qattrib, "attrib"); /* NOTE_ATTRIB */ | ||
| 331 | DEFSYM (Qlink, "link"); /* NOTE_LINK */ | ||
| 332 | DEFSYM (Qrename, "rename"); /* NOTE_RENAME */ | ||
| 333 | |||
| 334 | staticpro (&watch_list); | ||
| 335 | |||
| 336 | Fprovide (intern_c_string ("kqueue"), Qnil); | ||
| 337 | } | ||
| 338 | |||
| 339 | #endif /* HAVE_KQUEUE */ | ||
diff --git a/src/lisp.h b/src/lisp.h index 3efa492e0e8..426b6c949e9 100644 --- a/src/lisp.h +++ b/src/lisp.h | |||
| @@ -4257,17 +4257,23 @@ extern void init_font (void); | |||
| 4257 | extern void syms_of_fontset (void); | 4257 | extern void syms_of_fontset (void); |
| 4258 | #endif | 4258 | #endif |
| 4259 | 4259 | ||
| 4260 | /* Defined in inotify.c */ | ||
| 4261 | #ifdef HAVE_INOTIFY | ||
| 4262 | extern void syms_of_inotify (void); | ||
| 4263 | #endif | ||
| 4264 | |||
| 4265 | /* Defined in kqueue.c */ | ||
| 4266 | #ifdef HAVE_KQUEUE | ||
| 4267 | extern void globals_of_kqueue (void); | ||
| 4268 | extern void syms_of_kqueue (void); | ||
| 4269 | #endif | ||
| 4270 | |||
| 4260 | /* Defined in gfilenotify.c */ | 4271 | /* Defined in gfilenotify.c */ |
| 4261 | #ifdef HAVE_GFILENOTIFY | 4272 | #ifdef HAVE_GFILENOTIFY |
| 4262 | extern void globals_of_gfilenotify (void); | 4273 | extern void globals_of_gfilenotify (void); |
| 4263 | extern void syms_of_gfilenotify (void); | 4274 | extern void syms_of_gfilenotify (void); |
| 4264 | #endif | 4275 | #endif |
| 4265 | 4276 | ||
| 4266 | /* Defined in inotify.c */ | ||
| 4267 | #ifdef HAVE_INOTIFY | ||
| 4268 | extern void syms_of_inotify (void); | ||
| 4269 | #endif | ||
| 4270 | |||
| 4271 | #ifdef HAVE_W32NOTIFY | 4277 | #ifdef HAVE_W32NOTIFY |
| 4272 | /* Defined on w32notify.c. */ | 4278 | /* Defined on w32notify.c. */ |
| 4273 | extern void syms_of_w32notify (void); | 4279 | extern void syms_of_w32notify (void); |