summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDima Zavin2011-12-31 00:16:44 +0100
committerDmitry Torokhov2011-12-31 00:26:35 +0100
commit509f87c5f564627b6b9fc763e74ef3608213d610 (patch)
treec5034b38b7c49d75726ed24411a4bd9c57bc1f73
parentInput: evdev - if no events and non-block, return EAGAIN not 0 (diff)
downloadkernel-qcow2-linux-509f87c5f564627b6b9fc763e74ef3608213d610.tar.gz
kernel-qcow2-linux-509f87c5f564627b6b9fc763e74ef3608213d610.tar.xz
kernel-qcow2-linux-509f87c5f564627b6b9fc763e74ef3608213d610.zip
Input: evdev - do not block waiting for an event if fd is nonblock
If there is a full packet in the buffer, and we overflow that buffer right after checking for that condition, it would have been possible for us to block indefinitely (rather, until the next full packet) even if the file was marked as O_NONBLOCK. Cc: Jeff Brown <jeffbrown@android.com> Signed-off-by: Dima Zavin <dima@android.com> Signed-off-by: Dmitry Torokhov <dtor@mail.ru>
-rw-r--r--drivers/input/evdev.c15
1 files changed, 7 insertions, 8 deletions
diff --git a/drivers/input/evdev.c b/drivers/input/evdev.c
index a9d871651ce7..76457d50bc34 100644
--- a/drivers/input/evdev.c
+++ b/drivers/input/evdev.c
@@ -391,14 +391,13 @@ static ssize_t evdev_read(struct file *file, char __user *buffer,
if (count < input_event_size())
return -EINVAL;
- if (client->packet_head == client->tail && evdev->exist &&
- (file->f_flags & O_NONBLOCK))
- return -EAGAIN;
-
- retval = wait_event_interruptible(evdev->wait,
- client->packet_head != client->tail || !evdev->exist);
- if (retval)
- return retval;
+ if (!(file->f_flags & O_NONBLOCK)) {
+ retval = wait_event_interruptible(evdev->wait,
+ client->packet_head != client->tail ||
+ !evdev->exist);
+ if (retval)
+ return retval;
+ }
if (!evdev->exist)
return -ENODEV;