All of lore.kernel.org
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Chengyu Liu" <lui2012qwq@gmail.com>
Cc: linux-input@vger.kernel.org, dmitry.torokhov@gmail.com
Subject: Re: [PATCH 2/2] Input: cyapa - clamp SMBus block reads to the caller's buffer
Date: Tue, 03 Nov 2026 13:22:31 +0000	[thread overview]
Message-ID: <sashiko-outbox-195329@kernel.org> (raw)
In-Reply-To: <20261103131127.1585884-3-lui2012qwq@gmail.com>

Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
- [High] Input: cyapa - cyapa_smbus_read_block() returns full len on short block reads
--

commit 17f2cef41b86752525f835330272cc728242a63c
Author: Chengyu Liu <lui2012qwq@gmail.com>

Input: cyapa - clamp SMBus block reads to the caller's buffer

This commit bounces SMBus block reads in cyapa_smbus_read_block() through
a temporary I2C_SMBUS_BLOCK_MAX buffer and clamps the copy size to the
caller's requested length to prevent buffer overruns.

> diff --git a/drivers/input/mouse/cyapa_gen3.c b/drivers/input/mouse/cyapa_gen3.c
> index fc3fb954523b7..cd80ae51f4e52 100644
> --- a/drivers/input/mouse/cyapa_gen3.c
> +++ b/drivers/input/mouse/cyapa_gen3.c
> @@ -254,20 +254,30 @@ ssize_t cyapa_smbus_read_block(struct cyapa *cyapa, u8 cmd, size_t len,
>  		return -EINVAL;
>  
>  	if (SMBUS_GROUP_BLOCK_CMD_MASK & cmd) {
> +		u8 tmp[I2C_SMBUS_BLOCK_MAX];
> +
>  		/* read specific block registers command. */
>  		smbus_cmd = SMBUS_ENCODE_RW(cmd, SMBUS_READ);
> -		ret = i2c_smbus_read_block_data(client, smbus_cmd, values);
> +		ret = i2c_smbus_read_block_data(client, smbus_cmd, tmp);
> +		if (ret > 0)
> +			/* never trust the device-provided count */
> +			memcpy(values, tmp, min_t(size_t, ret, len));
>  		goto out;
>  	}
>  
>  	ret = 0;
>  	for (index = 0; index * I2C_SMBUS_BLOCK_MAX < len; index++) {
> +		u8 tmp[I2C_SMBUS_BLOCK_MAX];
> +		size_t chunk = min_t(size_t, len - index * I2C_SMBUS_BLOCK_MAX,
> +				     I2C_SMBUS_BLOCK_MAX);
> +
>  		smbus_cmd = SMBUS_ENCODE_IDX(cmd, index);
>  		smbus_cmd = SMBUS_ENCODE_RW(smbus_cmd, SMBUS_READ);
>  		buf = values + I2C_SMBUS_BLOCK_MAX * index;
> -		ret = i2c_smbus_read_block_data(client, smbus_cmd, buf);
> +		ret = i2c_smbus_read_block_data(client, smbus_cmd, tmp);
>  		if (ret < 0)
>  			goto out;
> +		memcpy(buf, tmp, min_t(size_t, ret, chunk));
>  	}

[Severity: High]
What happens in cyapa_smbus_read_block() if the device returns a short block
count where 0 < ret < len (or 0 <= ret < chunk in the indexed loop)?

Both branches copy only ret bytes into values or buf, leaving the remainder
of the caller's buffer untouched, and then jump to out:

drivers/input/mouse/cyapa_gen3.c:cyapa_smbus_read_block() {
	...
out:
	return ret > 0 ? len : ret;
}

Because cyapa_smbus_read_block() still returns the full requested len whenever
the last i2c_smbus_read_block_data() call returned a positive count, callers
that pass uninitialized stack buffers and check for a full read cannot detect
the short read:

drivers/input/mouse/cyapa_gen3.c:cyapa_gen3_get_query_data() {
	u8 query_data[QUERY_DATA_SIZE];
	int ret;

	/* query dataabda has 27 bytes */
	ret = cyapa_read_block(cyapa, CYAPA_CMD_GROUP_QUERY, query_data);
	if (ret != QUERY_DATA_SIZE)
		return (ret < 0) ? ret : -EIO;
	...
}

drivers/input/mouse/cyapa_gen3.c:cyapa_gen3_irq_handler() {
	struct cyapa_reg_data data;
	int ret;

	ret = cyapa_read_block(cyapa, CYAPA_CMD_GROUP_DATA, (u8 *)&data);
	if (ret != sizeof(data)) {
		dev_err(dev, "failed to read report data, (%d)\n", ret);
		return -EINVAL;
	}
	...
}

Wouldn't a device returning fewer bytes than requested cause
cyapa_gen3_get_query_data(), cyapa_gen3_irq_handler(),
cyapa_gen3_try_poll_handler(), and cyapa_get_state() to consume uninitialized
stack memory in query_data, data, and status (and expose uninitialized bytes
from query_data via the product_id and firmware_version sysfs attributes)?
Should cyapa_smbus_read_block() return an error such as -EIO when ret < len
in the group-read branch or ret < chunk in the indexed loop?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20261103131127.1585884-1-lui2012qwq@gmail.com?part=2

  reply	other threads:[~2026-11-03 13:22 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-11-03 13:11 [PATCH 0/2] Input: clamp SMBus block reads to the caller's buffer Chengyu Liu
2026-11-03 13:11 ` [PATCH 1/2] Input: rmi4 - clamp SMBus block reads to the requested length Chengyu Liu
2026-11-03 13:11 ` [PATCH 2/2] Input: cyapa - clamp SMBus block reads to the caller's buffer Chengyu Liu
2026-11-03 13:22   ` sashiko-bot [this message]
2026-11-03 14:10     ` cy l
2026-11-03 18:48 ` [PATCH 0/2] Input: " Dmitry Torokhov

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=sashiko-outbox-195329@kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=dmitry.torokhov@gmail.com \
    --cc=linux-input@vger.kernel.org \
    --cc=lui2012qwq@gmail.com \
    --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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.