From cf4ce59b3b70238352c7f1729f0f7223214828ad Mon Sep 17 00:00:00 2001 From: hc <hc@nodka.com> Date: Fri, 20 Sep 2024 01:46:19 +0000 Subject: [PATCH] rtl88x2CE_WiFi_linux add concurrent mode --- kernel/drivers/input/input.c | 89 +++++++++++++++++++++++++++++++------------- 1 files changed, 62 insertions(+), 27 deletions(-) diff --git a/kernel/drivers/input/input.c b/kernel/drivers/input/input.c index f96c40a..49504dc 100644 --- a/kernel/drivers/input/input.c +++ b/kernel/drivers/input/input.c @@ -1,14 +1,10 @@ +// SPDX-License-Identifier: GPL-2.0-only /* * The input core * * Copyright (c) 1999-2002 Vojtech Pavlik */ -/* - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License version 2 as published by - * the Free Software Foundation. - */ #define pr_fmt(fmt) KBUILD_BASENAME ": " fmt @@ -28,6 +24,7 @@ #include <linux/mutex.h> #include <linux/rcupdate.h> #include "input-compat.h" +#include "input-poller.h" MODULE_AUTHOR("Vojtech Pavlik <vojtech@suse.cz>"); MODULE_DESCRIPTION("Input core"); @@ -49,6 +46,17 @@ static DEFINE_MUTEX(input_mutex); static const struct input_value input_value_sync = { EV_SYN, SYN_REPORT, 1 }; + +static const unsigned int input_max_code[EV_CNT] = { + [EV_KEY] = KEY_MAX, + [EV_REL] = REL_MAX, + [EV_ABS] = ABS_MAX, + [EV_MSC] = MSC_MAX, + [EV_SW] = SW_MAX, + [EV_LED] = LED_MAX, + [EV_SND] = SND_MAX, + [EV_FF] = FF_MAX, +}; static inline int is_event_supported(unsigned int code, unsigned long *bm, unsigned int max) @@ -615,19 +623,30 @@ handle->open++; - if (!dev->users++ && dev->open) - retval = dev->open(dev); + if (dev->users++) { + /* + * Device is already opened, so we can exit immediately and + * report success. + */ + goto out; + } - if (retval) { - dev->users--; - if (!--handle->open) { + if (dev->open) { + retval = dev->open(dev); + if (retval) { + dev->users--; + handle->open--; /* * Make sure we are not delivering any more events * through this handle */ synchronize_rcu(); + goto out; } } + + if (dev->poller) + input_dev_poller_start(dev->poller); out: mutex_unlock(&dev->mutex); @@ -667,8 +686,13 @@ __input_release_device(handle); - if (!--dev->users && dev->close) - dev->close(dev); + if (!--dev->users) { + if (dev->poller) + input_dev_poller_stop(dev->poller); + + if (dev->close) + dev->close(dev); + } if (!--handle->open) { /* @@ -1204,13 +1228,12 @@ return seq_open(file, &input_devices_seq_ops); } -static const struct file_operations input_devices_fileops = { - .owner = THIS_MODULE, - .open = input_proc_devices_open, - .poll = input_proc_devices_poll, - .read = seq_read, - .llseek = seq_lseek, - .release = seq_release, +static const struct proc_ops input_devices_proc_ops = { + .proc_open = input_proc_devices_open, + .proc_poll = input_proc_devices_poll, + .proc_read = seq_read, + .proc_lseek = seq_lseek, + .proc_release = seq_release, }; static void *input_handlers_seq_start(struct seq_file *seq, loff_t *pos) @@ -1268,12 +1291,11 @@ return seq_open(file, &input_handlers_seq_ops); } -static const struct file_operations input_handlers_fileops = { - .owner = THIS_MODULE, - .open = input_proc_handlers_open, - .read = seq_read, - .llseek = seq_lseek, - .release = seq_release, +static const struct proc_ops input_handlers_proc_ops = { + .proc_open = input_proc_handlers_open, + .proc_read = seq_read, + .proc_lseek = seq_lseek, + .proc_release = seq_release, }; static int __init input_proc_init(void) @@ -1285,12 +1307,12 @@ return -ENOMEM; entry = proc_create("devices", 0, proc_bus_input_dir, - &input_devices_fileops); + &input_devices_proc_ops); if (!entry) goto fail1; entry = proc_create("handlers", 0, proc_bus_input_dir, - &input_handlers_fileops); + &input_handlers_proc_ops); if (!entry) goto fail2; @@ -1520,6 +1542,7 @@ &input_dev_attr_group, &input_dev_id_attr_group, &input_dev_caps_attr_group, + &input_poller_attribute_group, NULL }; @@ -1529,6 +1552,7 @@ input_ff_destroy(dev); input_mt_destroy_slots(dev); + kfree(dev->poller); kfree(dev->absinfo); kfree(dev->vals); kfree(dev); @@ -1963,6 +1987,14 @@ */ void input_set_capability(struct input_dev *dev, unsigned int type, unsigned int code) { + if (type < EV_CNT && input_max_code[type] && + code > input_max_code[type]) { + pr_err("%s: invalid code %u for type %u\n", __func__, code, + type); + dump_stack(); + return; + } + switch (type) { case EV_KEY: __set_bit(code, dev->keybit); @@ -2193,6 +2225,9 @@ if (!dev->setkeycode) dev->setkeycode = input_default_setkeycode; + if (dev->poller) + input_dev_poller_finalize(dev->poller); + error = device_add(&dev->dev); if (error) goto err_free_vals; -- Gitblit v1.6.2