]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
eventpoll: add epoll_sendevents() helper
authorJens Axboe <axboe@kernel.dk>
Wed, 19 Feb 2025 17:22:26 +0000 (10:22 -0700)
committerChristian Brauner <brauner@kernel.org>
Thu, 20 Feb 2025 09:18:37 +0000 (10:18 +0100)
Basic helper that copies ready events to the specified userspace
address. The event checking is quick and racy, it's up to the caller
to ensure it retries appropriately in case 0 events are copied.

Signed-off-by: Jens Axboe <axboe@kernel.dk>
Link: https://lore.kernel.org/r/20250219172552.1565603-4-axboe@kernel.dk
Signed-off-by: Christian Brauner <brauner@kernel.org>
fs/eventpoll.c
include/linux/eventpoll.h

index 14466765b85d6dddbd0a67b446cd7efd92e7c2f0..94b87aaad0f6e74735debab2f11e4cb8802e29bf 100644 (file)
@@ -2474,6 +2474,26 @@ static int ep_check_params(struct file *file, struct epoll_event __user *evs,
        return 0;
 }
 
+int epoll_sendevents(struct file *file, struct epoll_event __user *events,
+                    int maxevents)
+{
+       struct eventpoll *ep;
+       int ret;
+
+       ret = ep_check_params(file, events, maxevents);
+       if (unlikely(ret))
+               return ret;
+
+       ep = file->private_data;
+       /*
+        * Racy call, but that's ok - it should get retried based on
+        * poll readiness anyway.
+        */
+       if (ep_events_available(ep))
+               return ep_try_send_events(ep, events, maxevents);
+       return 0;
+}
+
 /*
  * Implement the event wait interface for the eventpoll file. It is the kernel
  * part of the user space epoll_wait(2).
index 0c0d00fcd131f9ebfdbabdb1917f01e870435595..ccb478eb174bc2e4454cee59f805f10cfd5bb5fb 100644 (file)
@@ -25,6 +25,10 @@ struct file *get_epoll_tfile_raw_ptr(struct file *file, int tfd, unsigned long t
 /* Used to release the epoll bits inside the "struct file" */
 void eventpoll_release_file(struct file *file);
 
+/* Copy ready events to userspace */
+int epoll_sendevents(struct file *file, struct epoll_event __user *events,
+                    int maxevents);
+
 /*
  * This is called from inside fs/file_table.c:__fput() to unlink files
  * from the eventpoll interface. We need to have this facility to cleanup