Here's a corrected patch for 0005 that supersedes the one in my
previous message.

Vladimir

2009/11/16 Vladimir Sedach <[email protected]>:
> Hello,
>
> Here are some patches that make it easier to just use the multiplexer
> object without having to go through the provided event loop/timer
> machinery. This is done in three steps: make the monitor/harvest etc.
> methods on multiplexer accept just file descriptors as well as
> FD-ENTRYs (note that I've only done that for epoll in this set of
> patches, others to come!), export the handler methods, and add an
> optional flags parameter to the MONITOR-FD method (really useful for
> epoll, the other backends I'm not sure about).
>
> Let me know what you think. I'd like to get these patches (or at least
> the equivalent functionality of being able to use the multiplexer
> without having to make FD-ENTRYs) into IOlib as I'm about to release
> some software that uses it.
>
> Thanks,
> Vladimir
>
From 683a127a19bbca5d270fa96299d06c5fc58d3820 Mon Sep 17 00:00:00 2001
From: Vladimir Sedach <[email protected]>
Date: Mon, 16 Nov 2009 02:52:42 -0500
Subject: [PATCH] Made epoll multiplexer take a simple integer file descriptor in
 addition to the FD-ENTRY structure.

---
 src/multiplex/backend-epoll.lisp |   99 +++++++++++++++++++-------------------
 1 files changed, 50 insertions(+), 49 deletions(-)

diff --git a/src/multiplex/backend-epoll.lisp b/src/multiplex/backend-epoll.lisp
index 091e916..39c9cf5 100644
--- a/src/multiplex/backend-epoll.lisp
+++ b/src/multiplex/backend-epoll.lisp
@@ -21,64 +21,65 @@
                                        &key (size +epoll-default-size-hint+))
   (setf (slot-value mux 'fd) (isys:%sys-epoll-create size)))
 
-(defun calc-epoll-flags (fd-entry)
-  (logior (if (fd-entry-read-handler fd-entry)
-              isys:epollin
-              0)
-          (if (fd-entry-write-handler fd-entry)
-              isys:epollout
-              0)
-          isys:epollpri))
-
-(defmethod monitor-fd ((mux epoll-multiplexer) fd-entry)
-  (assert fd-entry (fd-entry) "Must supply an FD-ENTRY!")
-  (let ((flags (calc-epoll-flags fd-entry))
-        (fd (fd-entry-fd fd-entry)))
-    (with-foreign-object (ev 'isys:epoll-event)
-      (isys:%sys-bzero ev isys:size-of-epoll-event)
-      (setf (foreign-slot-value ev 'isys:epoll-event 'isys:events) flags)
-      (setf (foreign-slot-value
-             (foreign-slot-value ev 'isys:epoll-event 'isys:data)
-             'isys:epoll-data 'isys:fd)
-            fd)
-      (handler-case
-          (isys:%sys-epoll-ctl (fd-of mux) isys:epoll-ctl-add fd ev)
-        (isys:ebadf ()
-          (warn "FD ~A is invalid, cannot monitor it." fd))
-        (isys:eexist ()
-          (warn "FD ~A is already monitored." fd))))))
-
-(defmethod update-fd ((mux epoll-multiplexer) fd-entry event-type edge-change)
-  (declare (ignore event-type edge-change))
-  (assert fd-entry (fd-entry) "Must supply an FD-ENTRY!")
-  (let ((flags (calc-epoll-flags fd-entry))
-        (fd (fd-entry-fd fd-entry)))
-    (with-foreign-object (ev 'isys:epoll-event)
-      (isys:%sys-bzero ev isys:size-of-epoll-event)
-      (setf (foreign-slot-value ev 'isys:epoll-event 'isys:events) flags)
-      (setf (foreign-slot-value
-             (foreign-slot-value ev 'isys:epoll-event 'isys:data)
-             'isys:epoll-data 'isys:fd)
-            fd)
-      (handler-case
-          (isys:%sys-epoll-ctl (fd-of mux) isys:epoll-ctl-mod fd ev)
-        (isys:ebadf ()
-          (warn "FD ~A is invalid, cannot update its status." fd))
-        (isys:enoent ()
-          (warn "FD ~A was not monitored, cannot update its status." fd))))
-    (values fd-entry)))
-
-(defmethod unmonitor-fd ((mux epoll-multiplexer) fd-entry)
+(defun calc-epoll-flags (flags)
+  (logior (if (member :read flags) isys:epollin 0)
+          (if (member :write flags) isys:epollout 0)
+          (if (member :epoll-oneshot flags) isys:epolloneshot 0)
+          isys:epollpri)) ;; what to do about EPOLLPRI?
+
+(defmethod monitor-fd ((mux epoll-multiplexer) (fd-entry fd-entry) &optional flags)
+  (declare (ignore flags))
+  (monitor-fd mux
+              (fd-entry-fd fd-entry)
+              (list (when (fd-entry-read-handler fd-entry) :read)
+                    (when (fd-entry-write-handler fd-entry) :write))))
+
+(defmacro with-epoll-event ((ev fd flags) &body body)
+  `(with-foreign-object (,ev 'isys:epoll-event)
+     (isys:%sys-bzero ,ev isys:size-of-epoll-event)
+     (setf (foreign-slot-value ,ev 'isys:epoll-event 'isys:events)
+           (calc-epoll-flags ,flags)
+           (foreign-slot-value
+            (foreign-slot-value ,ev 'isys:epoll-event 'isys:data)
+            'isys:epoll-data 'isys:fd)
+           ,fd)
+     ,@body))
+
+(defmethod monitor-fd ((mux epoll-multiplexer) (fd integer) &optional flags)
+  (with-epoll-event (ev fd flags)
+    (handler-case
+        (isys:%sys-epoll-ctl (fd-of mux) isys:epoll-ctl-add fd ev)
+      (isys:ebadf ()
+        (warn "FD ~A is invalid, cannot monitor it." fd))
+      (isys:eexist ()
+        (warn "FD ~A is already monitored." fd)))))
+
+(defmethod update-fd ((mux epoll-multiplexer) (fd-entry fd-entry) flags edge-change)
+  (update-fd mux (fd-entry-fd fd-entry) flags edge-change))
+
+(defmethod update-fd ((mux epoll-multiplexer) (fd integer) flags edge-change)
+  (declare (ignore edge-change))
+  (with-epoll-event (ev fd flags)
+    (handler-case
+        (isys:%sys-epoll-ctl (fd-of mux) isys:epoll-ctl-mod fd ev)
+      (isys:ebadf ()
+        (warn "FD ~A is invalid, cannot update its status." fd))
+      (isys:enoent ()
+        (warn "FD ~A was not monitored, cannot update its status." fd)))))
+
+(defmethod unmonitor-fd ((mux epoll-multiplexer) (fd-entry fd-entry))
+  (unmonitor-fd mux (fd-entry-fd fd-entry)))
+
+(defmethod unmonitor-fd ((mux epoll-multiplexer) (fd integer))
   (handler-case
       (isys:%sys-epoll-ctl (fd-of mux)
                            isys:epoll-ctl-del
-                           (fd-entry-fd fd-entry)
+                           fd
                            (null-pointer))
     (isys:ebadf ()
-      (warn "FD ~A is invalid, cannot unmonitor it." (fd-entry-fd fd-entry)))
+      (warn "FD ~A is invalid, cannot unmonitor it." fd))
     (isys:enoent ()
-      (warn "FD ~A was not monitored, cannot unmonitor it."
-            (fd-entry-fd fd-entry)))))
+      (warn "FD ~A was not monitored, cannot unmonitor it." fd))))
 
 (defmethod harvest-events ((mux epoll-multiplexer) timeout)
   (with-foreign-object (events 'isys:epoll-event +epoll-max-events+)
-- 
1.6.3.3

_______________________________________________
IOLib-devel mailing list
[email protected]
http://common-lisp.net/cgi-bin/mailman/listinfo/iolib-devel

Reply via email to