[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <613a66cd-4309-4bce-a4f7-2905f9bce0c9@rowland.harvard.edu>
Date: Wed, 23 Jul 2025 10:37:04 -0400
From: Alan Stern <stern@...land.harvard.edu>
To: Benjamin Tissoires <bentiss@...nel.org>
Cc: syzbot <syzbot+b63d677d63bcac06cf90@...kaller.appspotmail.com>,
jikos@...nel.org, linux-input@...r.kernel.org,
linux-kernel@...r.kernel.org, linux-usb@...r.kernel.org,
syzkaller-bugs@...glegroups.com
Subject: [PATCH] HID: core: Harden s32ton() against conversion to 0 bits
Testing by the syzbot fuzzer showed that the HID core gets a
shift-out-of-bounds exception when it tries to convert a 32-bit
quantity to a 0-bit quantity. Ideally this should never occur, but
there are buggy devices and some might have a report field with size
set to zero; we shouldn't reject the report or the device just because
of that.
Instead, harden the s32ton() routine so that it returns a reasonable
result instead of crashing when it is called with the number of bits
set to 0 -- the same as what snto32() does.
Signed-off-by: Alan Stern <stern@...land.harvard.edu>
Reported-by: syzbot+b63d677d63bcac06cf90@...kaller.appspotmail.com
Closes: https://lore.kernel.org/linux-usb/68753a08.050a0220.33d347.0008.GAE@google.com/
Tested-by: syzbot+b63d677d63bcac06cf90@...kaller.appspotmail.com
Fixes: dde5845a529f ("[PATCH] Generic HID layer - code split")
Cc: stable@...r.kernel.org
---
The commit listed in the Fixes tag is not really the right one. But
code motion made tracking it back any further more difficult than I
wanted to deal with, so I stopped there. That commit is from 2006,
which is already far enough in the past.
drivers/hid/hid-core.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
Index: usb-devel/drivers/hid/hid-core.c
===================================================================
--- usb-devel.orig/drivers/hid/hid-core.c
+++ usb-devel/drivers/hid/hid-core.c
@@ -66,8 +66,12 @@ static s32 snto32(__u32 value, unsigned
static u32 s32ton(__s32 value, unsigned int n)
{
- s32 a = value >> (n - 1);
+ s32 a;
+ if (!value || !n)
+ return 0;
+
+ a = value >> (n - 1);
if (a && a != -1)
return value < 0 ? 1 << (n - 1) : (1 << (n - 1)) - 1;
return value & ((1 << n) - 1);
Powered by blists - more mailing lists