1 (in-package #:cl-notify)
3 (defbitfield (inotify-flags :uint32)
4 (:in-access #.in-access)
5 (:in-modify #.in-modify)
6 (:in-attrib #.in-attrib)
7 (:in-close-write #.in-close-write)
8 (:in-close-nowrite #.in-close-nowrite)
11 (:in-moved-from #.in-moved-from)
12 (:in-moved-to #.in-moved-to)
14 (:in-create #.in-create)
15 (:in-delete #.in-delete)
16 (:in-delete-self #.in-delete-self)
17 (:in-move-self #.in-move-self)
18 (:in-unmount #.in-unmount)
19 (:in-q-overflow #.in-q-overflow)
20 (:in-ignored #.in-ignored)
21 (:in-onlydir #.in-onlydir)
22 (:in-dont-follow #.in-dont-follow)
23 (:in-mask-add #.in-mask-add)
24 (:in-isdir #.in-isdir)
25 (:in-oneshot #.in-oneshot)
26 (:in-all-events #.in-all-events))
28 (defcfun "inotify_init" :int)
30 (defcfun "inotify_add_watch" :int
35 (defcfun "inotify_rm_watch" :int
39 (binary-types:define-signed int #.(cffi:foreign-type-size :int))
41 (binary-types:define-binary-struct inotify-event ()
42 (wd 0 :binary-type int)
43 (mask 0 :binary-type binary-types:u32)
44 (cookie 0 :binary-type binary-types:u32)
47 (defstruct (inotify-instance (:constructor make-inotify-instance (fd stream)))
52 (setf binary-types:*endian*
53 #+little-endian :little-endian
54 #+big-endian :big-endian
55 #-(or little-endian big-endian) (error "unknown endianess")))
59 (defun inotify-read-raw-event (stream)
60 (let* ((event (binary-types:read-binary 'inotify-event stream))
61 (len (binary-types:read-binary 'binary-types:u32 stream)))
63 (with-slots (name) event
65 (binary-types:read-binary-string stream :size len :terminators '(0)))))
68 (defun inotify-read-event (stream)
69 (let ((event (inotify-read-raw-event stream)))
70 (with-slots (mask) event
71 (setf mask (foreign-bitfield-symbols 'inotify-flags mask)))
75 (let* ((fd (inotify-init)))
77 (error "inotify_init failed: ~A" fd))
78 ;; file descriptor is collected with auto-close
79 (make-inotify-instance
81 (sb-sys:make-fd-stream fd
83 :element-type '(unsigned-byte 8)
84 :name (format NIL "inotify event queue ~A" fd)
87 (defun close-notify (notify)
88 (close (inotify-instance-stream notify))
91 (defun watch (notify pathname flags)
92 (let ((path (princ-to-string pathname))
95 (inotify-add-watch (inotify-instance-fd notify)
98 (foreign-bitfield-value 'inotify-flags flags)
101 (error "inotify_add_watch failed: ~A" result))
104 (defun unwatch (notify handle)
105 (let ((result (inotify-rm-watch (inotify-instance-fd notify) handle)))
107 (error "inotify_rm_watch failed: ~A" result))