Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit cbf05413 authored by Ryan Mallon's avatar Ryan Mallon Committed by Dmitry Torokhov
Browse files

Input: uinput - support injecting multiple events in one write() call



Rework the code in uinput_inject_event so that it matches the code in
evdev_write and allows injecting more than one event, or zero events.

Signed-off-by: default avatarRyan Mallon <rmallon@gmail.com>
Signed-off-by: default avatarDmitry Torokhov <dmitry.torokhov@gmail.com>
parent 8474cadd
Loading
Loading
Loading
Loading
+18 −8
Original line number Original line Diff line number Diff line
@@ -430,20 +430,30 @@ static int uinput_setup_device(struct uinput_device *udev,
	return retval;
	return retval;
}
}


static ssize_t uinput_inject_event(struct uinput_device *udev,
static ssize_t uinput_inject_events(struct uinput_device *udev,
				    const char __user *buffer, size_t count)
				    const char __user *buffer, size_t count)
{
{
	struct input_event ev;
	struct input_event ev;
	size_t bytes = 0;


	if (count < input_event_size())
	if (count != 0 && count < input_event_size())
		return -EINVAL;
		return -EINVAL;


	if (input_event_from_user(buffer, &ev))
	while (bytes + input_event_size() <= count) {
		/*
		 * Note that even if some events were fetched successfully
		 * we are still going to return EFAULT instead of partial
		 * count to let userspace know that it got it's buffers
		 * all wrong.
		 */
		if (input_event_from_user(buffer + bytes, &ev))
			return -EFAULT;
			return -EFAULT;


		input_event(udev->dev, ev.type, ev.code, ev.value);
		input_event(udev->dev, ev.type, ev.code, ev.value);
		bytes += input_event_size();
	}


	return input_event_size();
	return bytes;
}
}


static ssize_t uinput_write(struct file *file, const char __user *buffer,
static ssize_t uinput_write(struct file *file, const char __user *buffer,
@@ -460,7 +470,7 @@ static ssize_t uinput_write(struct file *file, const char __user *buffer,
		return retval;
		return retval;


	retval = udev->state == UIST_CREATED ?
	retval = udev->state == UIST_CREATED ?
			uinput_inject_event(udev, buffer, count) :
			uinput_inject_events(udev, buffer, count) :
			uinput_setup_device(udev, buffer, count);
			uinput_setup_device(udev, buffer, count);


	mutex_unlock(&udev->mutex);
	mutex_unlock(&udev->mutex);