for-linus-2023030901
-----BEGIN PGP SIGNATURE----- iQJSBAABCAA8FiEEoEVH9lhNrxiMPSyI7MXwXhnZSjYFAmQJ8eweHGJlbmphbWlu LnRpc3NvaXJlc0ByZWRoYXQuY29tAAoJEOzF8F4Z2Uo2ff4P/j4zp6J7wfstWL5g Ma3u3RqRpM0HKw0tO5PeigLYGout40oW8xAH7n8ERu2o45yQAd5ZbgXVey25FTSd QEVd7zwN/ADMMTTujGQAfzpE6O7eaALVDgtgjOcNS8uRLeyqcDSCgBRaB8sNwLy7 ZhHU5OWKvRCiiwTQyG7gvY9+cTre6wNjdKR2Ei+xra5IS78gp3OZ1NJOjT3iHDxe Zxo4kpkEaBJmVNYbC41sZfkzuZ84SfKXUC14V3BBiXmvnYU6x3WmuXxFvCgBEjgz agmKugHrdABa+oooONdKztHSOfa5saeYy11FO+q8txIEZqSiodr1anmk2U77Yu9O f4E8sQQszHMWyaqac5+dwUCaupgmKtPZOoMRjbGfGjwLObYkhxnJu6AamWYZl7DG E6AaO+ZV0SQcl89GpJ4+SiXSbSxUopYljzkUnvrnrOqPe4AkdWVTuCexBgGkOKqa DDQb+OYcI5N2aFMTOx8dkmZ6MPU7Mtot7UPTC1rv5Cgi8xFCH215dLauskDyatmt XQw5+9hzb1q3ZFFw6E/IhBkRcNLeAga1lsSxeqIGKkCHeEAOuCaO9ev454LD4oKk 7nTqyKKAx+Roaw3dwCyU+U2v12B+PoYBq6BGnJtm/EnF0VuJRi8kV8J9uMXoo30j v4Fo/IsHUlgIiuJo556tmjcTetUm =XVs0 -----END PGP SIGNATURE----- Merge tag 'for-linus-2023030901' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid Pull HID fixes from Benjamin Tissoires: - fix potential out of bound write of zeroes in HID core with a specially crafted uhid device (Lee Jones) - fix potential use-after-free in work function in intel-ish-hid (Reka Norman) - selftests config fixes (Benjamin Tissoires) - few device small fixes and support * tag 'for-linus-2023030901' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid: HID: intel-ish-hid: ipc: Fix potential use-after-free in work function HID: logitech-hidpp: Add support for Logitech MX Master 3S mouse HID: cp2112: Fix driver not registering GPIO IRQ chip as threaded selftest: hid: fix hid_bpf not set in config HID: uhid: Over-ride the default maximum data buffer value with our own HID: core: Provide new max_buffer_size attribute to over-ride the default
This commit is contained in:
commit
2653e3fe33
|
@ -256,6 +256,7 @@ static int hid_add_field(struct hid_parser *parser, unsigned report_type, unsign
|
|||
{
|
||||
struct hid_report *report;
|
||||
struct hid_field *field;
|
||||
unsigned int max_buffer_size = HID_MAX_BUFFER_SIZE;
|
||||
unsigned int usages;
|
||||
unsigned int offset;
|
||||
unsigned int i;
|
||||
|
@ -286,8 +287,11 @@ static int hid_add_field(struct hid_parser *parser, unsigned report_type, unsign
|
|||
offset = report->size;
|
||||
report->size += parser->global.report_size * parser->global.report_count;
|
||||
|
||||
if (parser->device->ll_driver->max_buffer_size)
|
||||
max_buffer_size = parser->device->ll_driver->max_buffer_size;
|
||||
|
||||
/* Total size check: Allow for possible report index byte */
|
||||
if (report->size > (HID_MAX_BUFFER_SIZE - 1) << 3) {
|
||||
if (report->size > (max_buffer_size - 1) << 3) {
|
||||
hid_err(parser->device, "report is too long\n");
|
||||
return -1;
|
||||
}
|
||||
|
@ -1963,6 +1967,7 @@ int hid_report_raw_event(struct hid_device *hid, enum hid_report_type type, u8 *
|
|||
struct hid_report_enum *report_enum = hid->report_enum + type;
|
||||
struct hid_report *report;
|
||||
struct hid_driver *hdrv;
|
||||
int max_buffer_size = HID_MAX_BUFFER_SIZE;
|
||||
u32 rsize, csize = size;
|
||||
u8 *cdata = data;
|
||||
int ret = 0;
|
||||
|
@ -1978,10 +1983,13 @@ int hid_report_raw_event(struct hid_device *hid, enum hid_report_type type, u8 *
|
|||
|
||||
rsize = hid_compute_report_size(report);
|
||||
|
||||
if (report_enum->numbered && rsize >= HID_MAX_BUFFER_SIZE)
|
||||
rsize = HID_MAX_BUFFER_SIZE - 1;
|
||||
else if (rsize > HID_MAX_BUFFER_SIZE)
|
||||
rsize = HID_MAX_BUFFER_SIZE;
|
||||
if (hid->ll_driver->max_buffer_size)
|
||||
max_buffer_size = hid->ll_driver->max_buffer_size;
|
||||
|
||||
if (report_enum->numbered && rsize >= max_buffer_size)
|
||||
rsize = max_buffer_size - 1;
|
||||
else if (rsize > max_buffer_size)
|
||||
rsize = max_buffer_size;
|
||||
|
||||
if (csize < rsize) {
|
||||
dbg_hid("report %d is too short, (%d < %d)\n", report->id,
|
||||
|
@ -2396,7 +2404,12 @@ int hid_hw_raw_request(struct hid_device *hdev,
|
|||
unsigned char reportnum, __u8 *buf,
|
||||
size_t len, enum hid_report_type rtype, enum hid_class_request reqtype)
|
||||
{
|
||||
if (len < 1 || len > HID_MAX_BUFFER_SIZE || !buf)
|
||||
unsigned int max_buffer_size = HID_MAX_BUFFER_SIZE;
|
||||
|
||||
if (hdev->ll_driver->max_buffer_size)
|
||||
max_buffer_size = hdev->ll_driver->max_buffer_size;
|
||||
|
||||
if (len < 1 || len > max_buffer_size || !buf)
|
||||
return -EINVAL;
|
||||
|
||||
return hdev->ll_driver->raw_request(hdev, reportnum, buf, len,
|
||||
|
@ -2415,7 +2428,12 @@ EXPORT_SYMBOL_GPL(hid_hw_raw_request);
|
|||
*/
|
||||
int hid_hw_output_report(struct hid_device *hdev, __u8 *buf, size_t len)
|
||||
{
|
||||
if (len < 1 || len > HID_MAX_BUFFER_SIZE || !buf)
|
||||
unsigned int max_buffer_size = HID_MAX_BUFFER_SIZE;
|
||||
|
||||
if (hdev->ll_driver->max_buffer_size)
|
||||
max_buffer_size = hdev->ll_driver->max_buffer_size;
|
||||
|
||||
if (len < 1 || len > max_buffer_size || !buf)
|
||||
return -EINVAL;
|
||||
|
||||
if (hdev->ll_driver->output_report)
|
||||
|
|
|
@ -1354,6 +1354,7 @@ static int cp2112_probe(struct hid_device *hdev, const struct hid_device_id *id)
|
|||
girq->parents = NULL;
|
||||
girq->default_type = IRQ_TYPE_NONE;
|
||||
girq->handler = handle_simple_irq;
|
||||
girq->threaded = true;
|
||||
|
||||
ret = gpiochip_add_data(&dev->gc, dev);
|
||||
if (ret < 0) {
|
||||
|
|
|
@ -4399,6 +4399,8 @@ static const struct hid_device_id hidpp_devices[] = {
|
|||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb02a) },
|
||||
{ /* MX Master 3 mouse over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb023) },
|
||||
{ /* MX Master 3S mouse over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb034) },
|
||||
{}
|
||||
};
|
||||
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
* Copyright (c) 2014-2016, Intel Corporation.
|
||||
*/
|
||||
|
||||
#include <linux/devm-helpers.h>
|
||||
#include <linux/sched.h>
|
||||
#include <linux/spinlock.h>
|
||||
#include <linux/delay.h>
|
||||
|
@ -621,7 +622,6 @@ static void recv_ipc(struct ishtp_device *dev, uint32_t doorbell_val)
|
|||
case MNG_RESET_NOTIFY:
|
||||
if (!ishtp_dev) {
|
||||
ishtp_dev = dev;
|
||||
INIT_WORK(&fw_reset_work, fw_reset_work_fn);
|
||||
}
|
||||
schedule_work(&fw_reset_work);
|
||||
break;
|
||||
|
@ -940,6 +940,7 @@ struct ishtp_device *ish_dev_init(struct pci_dev *pdev)
|
|||
{
|
||||
struct ishtp_device *dev;
|
||||
int i;
|
||||
int ret;
|
||||
|
||||
dev = devm_kzalloc(&pdev->dev,
|
||||
sizeof(struct ishtp_device) + sizeof(struct ish_hw),
|
||||
|
@ -975,6 +976,12 @@ struct ishtp_device *ish_dev_init(struct pci_dev *pdev)
|
|||
list_add_tail(&tx_buf->link, &dev->wr_free_list);
|
||||
}
|
||||
|
||||
ret = devm_work_autocancel(&pdev->dev, &fw_reset_work, fw_reset_work_fn);
|
||||
if (ret) {
|
||||
dev_err(dev->devc, "Failed to initialise FW reset work\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
dev->ops = &ish_hw_ops;
|
||||
dev->devc = &pdev->dev;
|
||||
dev->mtu = IPC_PAYLOAD_SIZE - sizeof(struct ishtp_msg_hdr);
|
||||
|
|
|
@ -395,6 +395,7 @@ static const struct hid_ll_driver uhid_hid_driver = {
|
|||
.parse = uhid_hid_parse,
|
||||
.raw_request = uhid_hid_raw_request,
|
||||
.output_report = uhid_hid_output_report,
|
||||
.max_buffer_size = UHID_DATA_MAX,
|
||||
};
|
||||
|
||||
#ifdef CONFIG_COMPAT
|
||||
|
|
|
@ -834,6 +834,7 @@ struct hid_driver {
|
|||
* @output_report: send output report to device
|
||||
* @idle: send idle request to device
|
||||
* @may_wakeup: return if device may act as a wakeup source during system-suspend
|
||||
* @max_buffer_size: over-ride maximum data buffer size (default: HID_MAX_BUFFER_SIZE)
|
||||
*/
|
||||
struct hid_ll_driver {
|
||||
int (*start)(struct hid_device *hdev);
|
||||
|
@ -859,6 +860,8 @@ struct hid_ll_driver {
|
|||
|
||||
int (*idle)(struct hid_device *hdev, int report, int idle, int reqtype);
|
||||
bool (*may_wakeup)(struct hid_device *hdev);
|
||||
|
||||
unsigned int max_buffer_size;
|
||||
};
|
||||
|
||||
extern bool hid_is_usb(const struct hid_device *hdev);
|
||||
|
|
|
@ -17,5 +17,6 @@ CONFIG_FTRACE_SYSCALLS=y
|
|||
CONFIG_FUNCTION_TRACER=y
|
||||
CONFIG_HIDRAW=y
|
||||
CONFIG_HID=y
|
||||
CONFIG_HID_BPF=y
|
||||
CONFIG_INPUT_EVDEV=y
|
||||
CONFIG_UHID=y
|
||||
|
|
Loading…
Reference in New Issue