From: sashiko-bot@kernel.org
To: "Griffin Kroah-Hartman" <griffin@kroah.com>
Cc: linux-input@vger.kernel.org, dmitry.torokhov@gmail.com
Subject: Re: [PATCH 3/3] Input: xpad - add sdata_check() to xpad360 branches
Date: Mon, 03 Aug 2026 16:05:11 +0000 [thread overview]
Message-ID: <20260803160512.730DF1F000E9@smtp.kernel.org> (raw)
In-Reply-To: <20260803-xpadone_packet_fix-v1-3-280da203f15c@kroah.com>
Thank you for your contribution! Sashiko AI review found 4 potential issue(s) to consider:
New issues:
- [Medium] Zero-length packets incorrectly pass validation and are processed as valid empty states, spuriously releasing all controller buttons.
Pre-existing issues:
- [High] Blocking USB APIs and GFP_KERNEL allocations are unsafely invoked from the atomic URB completion handler.
- [High] Error paths during initialization destroy the input device while leaving a dangling pointer for presence_work to dereference.
- [Medium] 16-bit multi-byte reads and direct array modifications completely bypass the new length validation, leading to stale data leakage.
--
--- Patch [3]: [PATCH 3/3] Input: xpad - add sdata_check() to xpad360 branches ---
commit 0a84609d4ff81bead2c2c2c26f83c5c8f9cc506a
Author: Griffin Kroah-Hartman <griffin@kroah.com>
Input: xpad - add sdata_check() to xpad360 branches
This commit adds the sdata_check() safety wrapper to the xpad360_process_packet()
and xpad360w_process_packet() functions. It bounds-checks array accesses to prevent
out-of-bounds reads on the controller data buffer.
> diff --git a/drivers/input/joystick/xpad.c b/drivers/input/joystick/xpad.c
> index 319a4c4a695fe..304229782e455 100644
> --- a/drivers/input/joystick/xpad.c
> +++ b/drivers/input/joystick/xpad.c
> @@ -891,19 +891,24 @@ static void xpad_process_packet(struct usb_xpad *xpad, u16 cmd, unsigned char *d
> */
>
> static void xpad360_process_packet(struct usb_xpad *xpad, struct input_dev *dev,
> - u16 cmd, unsigned char *data)
> + u16 cmd, unsigned char *data, u32 len)
> {
> + struct safe_data sdata;
> +
> + sdata.data = data;
> + sdata.len = len;
> +
> /* valid pad data */
> - if (data[0] != 0x00)
> + if (sdata_check(&sdata, 0) != 0x00)
> return;
[Severity: Medium]
Does this inadvertently allow zero-length packets to be treated as valid
pad data? Because sdata_check() safely returns 0 when the index is out of
bounds, a zero-length packet will successfully pass this != 0x00 check
and spuriously release all controller buttons.
>
> /* digital pad */
> if (xpad->mapping & MAP_DPAD_TO_BUTTONS) {
[ ... ]
> @@ -915,27 +920,29 @@ static void xpad360_process_packet(struct usb_xpad *xpad, struct input_dev *dev,
> if (!(xpad->mapping & MAP_DPAD_TO_BUTTONS) ||
> xpad->xtype == XTYPE_XBOX360W) {
[ ... ]
> /* buttons A,B,X,Y,TL,TR and MODE */
> - input_report_key(dev, BTN_A, data[3] & BIT(4));
> - input_report_key(dev, BTN_B, data[3] & BIT(5));
> - input_report_key(dev, BTN_X, data[3] & BIT(6));
> - input_report_key(dev, BTN_Y, data[3] & BIT(7));
> - input_report_key(dev, BTN_TL, data[3] & BIT(0));
> - input_report_key(dev, BTN_TR, data[3] & BIT(1));
> - input_report_key(dev, BTN_MODE, data[3] & BIT(2));
> + input_report_key(dev, BTN_A, sdata_check(&sdata, 3) & BIT(4));
> + input_report_key(dev, BTN_B, sdata_check(&sdata, 3) & BIT(5));
> + input_report_key(dev, BTN_X, sdata_check(&sdata, 3) & BIT(6));
> + input_report_key(dev, BTN_Y, sdata_check(&sdata, 3) & BIT(7));
> + input_report_key(dev, BTN_TL, sdata_check(&sdata, 3) & BIT(0));
> + input_report_key(dev, BTN_TR, sdata_check(&sdata, 3) & BIT(1));
> + input_report_key(dev, BTN_MODE, sdata_check(&sdata, 3) & BIT(2));
>
> if (!(xpad->mapping & MAP_STICKS_TO_NULL)) {
> /* left stick */
[Severity: Medium]
This isn't a bug introduced by this patch, but will the 16-bit stick axis
reads immediately following this code bypass the new length checks?
xpad_process_packet(), xpad360_process_packet(), and xpadone_process_packet()
read multi-byte values using le16_to_cpup() directly against the raw data
buffer:
input_report_abs(dev, ABS_X,
(__s16) le16_to_cpup((__le16 *)(data + 6)));
A short packet would still cause out-of-bounds reads here since these
accesses completely bypass the sdata_check() wrapper, potentially leaking
uninitialized DMA memory into input events.
[ ... ]
> @@ -1019,14 +1026,18 @@ static void xpad_presence_work(struct work_struct *work)
> * 01.1 - Pad state (Bytes 4+) valid
> *
> */
> -static void xpad360w_process_packet(struct usb_xpad *xpad, u16 cmd, unsigned char *data)
> +static void xpad360w_process_packet(struct usb_xpad *xpad, u16 cmd, unsigned char *data, u32 len)
> {
> struct input_dev *dev;
> + struct safe_data sdata;
> bool present;
>
> + sdata.data = data;
> + sdata.len = len;
> +
> /* Presence change */
> - if (data[0] & 0x08) {
> - present = (data[1] & 0x80) != 0;
> + if (sdata_check(&sdata, 0) & 0x08) {
> + present = (sdata_check(&sdata, 1) & 0x80) != 0;
>
> if (xpad->pad_present != present) {
> xpad->pad_present = present;
> schedule_work(&xpad->work);
[Severity: High]
This is a pre-existing issue, but can the xpad_presence_work thread
dereference a freed pointer if initialization fails?
If xpad_init_input() encounters an error (like during device registration),
it takes the err_free_input path:
xpad_init_input() {
...
err_free_input:
input_free_device(input_dev);
return error;
}
This frees the device but leaves xpad->dev pointing to the freed memory.
When xpad_presence_work() processes the failure, it logs the error:
xpad_presence_work() {
...
dev_err(&xpad->dev->dev, "unable to init device: %d\n", error);
}
Could this use-after-free lead to memory corruption or a crash?
[ ... ]
> @@ -1262,10 +1273,10 @@ static void xpad_irq_in(struct urb *urb)
>
> switch (xpad->xtype) {
> case XTYPE_XBOX360:
> - xpad360_process_packet(xpad, xpad->dev, 0, xpad->idata);
> + xpad360_process_packet(xpad, xpad->dev, 0, xpad->idata, urb->actual_length);
> break;
> case XTYPE_XBOX360W:
> - xpad360w_process_packet(xpad, 0, xpad->idata);
> + xpad360w_process_packet(xpad, 0, xpad->idata, urb->actual_length);
> break;
> case XTYPE_XBOXONE:
> xpadone_process_packet(xpad, 0, xpad->idata, urb->actual_length);
[Severity: High]
This is a pre-existing issue, but does xpadone_process_packet() execute
blocking calls and GFP_KERNEL allocations from an atomic context?
When xpad_irq_in() processes an Xbox One GIP_CMD_ANNOUNCE packet from
interrupt context, it follows this call chain:
xpad_irq_in()
xpadone_process_packet()
xpad_start_input()
usb_submit_urb(xpad->irq_in, GFP_KERNEL)
xpad_start_input() also calls xpad_start_xbox_one(), which invokes
usb_set_interface(), a synchronous and blocking USB API. Calling these
from the atomic URB completion handler could lead to scheduling while
atomic warnings and potential deadlocks.
--
Sashiko AI review · https://sashiko.dev/#/patchset/20260803-xpadone_packet_fix-v1-0-280da203f15c@kroah.com?part=3
prev parent reply other threads:[~2026-08-03 16:05 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-08-03 15:07 [PATCH 0/3] XPAD safety strengthening Griffin Kroah-Hartman
2026-08-03 15:07 ` [PATCH 1/3] Input: xpad - add safer data access framework Griffin Kroah-Hartman
2026-08-03 15:27 ` sashiko-bot
2026-08-03 16:23 ` Dmitry Torokhov
2026-08-04 8:02 ` Griffin Kroah-Hartman
2026-08-03 15:07 ` [PATCH 2/3] Input: xpad - add sdata_check() to xpad controllers Griffin Kroah-Hartman
2026-08-03 15:46 ` sashiko-bot
2026-08-03 15:07 ` [PATCH 3/3] Input: xpad - add sdata_check() to xpad360 branches Griffin Kroah-Hartman
2026-08-03 16:05 ` sashiko-bot [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260803160512.730DF1F000E9@smtp.kernel.org \
--to=sashiko-bot@kernel.org \
--cc=dmitry.torokhov@gmail.com \
--cc=griffin@kroah.com \
--cc=linux-input@vger.kernel.org \
--cc=sashiko-reviews@lists.linux.dev \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox