All of lore.kernel.org
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Sasha Finkelstein" <k@chaosmail.tech>
Cc: robh@kernel.org, devicetree@vger.kernel.org, conor+dt@kernel.org
Subject: Re: [PATCH v3 3/3] usb: typec: tipd: Add sn201202x support
Date: Sat, 01 Aug 2026 21:45:06 +0000	[thread overview]
Message-ID: <20260801214507.4CBB21F00AC4@smtp.kernel.org> (raw)
In-Reply-To: <20260801-tipd-ace3-v3-3-8332f2eca4fc@chaosmail.tech>

Thank you for your contribution! Sashiko AI review found 6 potential issue(s) to consider:

New issues:
- [High] sn201202x_suspend fails to wake up the device if the sleep completion times out, leaving the device in an unresponsive state during error recovery.
- [High] Passing NULL as the devname parameter to devm_request_irq causes a kernel panic during procfs directory creation.
- [Medium] Missing reinit_completion() before spmi_command_wakeup() in probe can cause premature timeout completion due to a spurious or pending interrupt.
- [Medium] The busy-wait check `val == (reg | 0x80)` incorrectly handles register addresses >= 0x80, leading to an infinite polling loop.

Pre-existing issues:
- [High] If wakeup-source is present in DT but irq is missing, tipd_suspend and tipd_resume will erroneously operate on IRQ 0.
- [High] If connect() fails and no IRQ is present, tipd_init leaks the initialized delayed work queue, leading to a Use-After-Free.
--

--- Patch [3]: [PATCH v3 3/3] usb: typec: tipd: Add sn201202x support ---
commit a0251ef6ede2e8ce60700056a8add92aa7a36382
Author: Sasha Finkelstein <k@chaosmail.tech>
Subject: usb: typec: tipd: Add sn201202x support

This patch adds support for the sn201202x (ACE3) controller, which is a tipd
variant utilizing the SPMI bus. It provides the SPMI regmap implementation
along with probe and PM routines.

> diff --git a/drivers/usb/typec/tipd/spmi.c b/drivers/usb/typec/tipd/spmi.c
> new file mode 100644
> index 0000000000000..73575a854bde1
> --- /dev/null
> +++ b/drivers/usb/typec/tipd/spmi.c
[ ... ]
> +static int regmap_sn201202x_select_reg(struct spmi_device *sdev, u8 reg)
> +{
[ ... ]
> +	while (--attempts) {
> +		err = spmi_register_read(sdev, 0, &val);
> +		if (err)
> +			return err;
> +		if (val == (reg | 0x80)) {
> +			if (!warned) {
> +				dev_warn(tps->dev,
> +					 "Got interrupt but selection not complete?\n");
> +				warned = true;
> +			}
> +			msleep(20);
> +			continue;
> +		}
> +		if (val == reg)
> +			return 0;
> +		return -EIO;
> +	}
> +
> +	return -EIO;
> +}

[Severity: Medium]
Does this logic work correctly for register addresses >= 0x80? If reg is
0x85, for example, then (reg | 0x80) evaluates to just reg. This would make
the busy condition val == (reg | 0x80) identical to the success condition 
val == reg. Since the busy condition is checked first, it will falsely match,
trigger the warning, and eventually timeout returning -EIO.

[ ... ]
> +static int sn201202x_probe(struct spmi_device *device)
> +{
[ ... ]
> +	init_completion(&sn->select_completion);
> +	init_completion(&sn->sleep_completion);
> +	init_completion(&sn->wake_completion);
> +
> +	ret = devm_request_irq(&device->dev, irq_select, sn201202x_irq,
> +			       0, NULL, &sn->select_completion);
> +	if (ret)
> +		return ret;
> +	ret = devm_request_irq(&device->dev, irq_sleep, sn201202x_irq,
> +			       0, NULL, &sn->sleep_completion);
> +	if (ret)
> +		return ret;
> +	ret = devm_request_irq(&device->dev, irq_wake, sn201202x_irq,
> +			       0, NULL, &sn->wake_completion);

[Severity: High]
Can passing NULL as the devname parameter to devm_request_irq() cause a kernel
panic during boot? The IRQ subsystem passes the devname to proc_mkdir() to 
create an entry in /proc/irq/, and calling strlen() on a NULL name will fault.

> +	if (ret)
> +		return ret;
> +
> +	spmi_device_set_drvdata(device, tps);
> +	tps->regmap = devm_regmap_init_sn201202x(device, &tps6598x_regmap_config);
> +	if (IS_ERR(tps->regmap))
> +		return PTR_ERR(tps->regmap);
> +
> +	ret = spmi_command_wakeup(device);
> +	if (ret)
> +		return ret;
> +	if (!wait_for_completion_timeout(&sn->wake_completion, msecs_to_jiffies(100)))
> +		return -ETIMEDOUT;

[Severity: Medium]
Should there be a call to reinit_completion(&sn->wake_completion) right 
before sending the wakeup command? If a pending or spurious interrupt fires 
immediately after the IRQ is registered above, wait_for_completion_timeout()
might consume the stale completion and return immediately without waiting for
the actual hardware wakeup sequence to finish.

[ ... ]
> +static int __maybe_unused sn201202x_suspend(struct device *dev)
> +{
[ ... ]
> +	err = spmi_command_sleep(sn->sdev);
> +	if (err)
> +		goto out_resume;
> +	if (!wait_for_completion_timeout(&sn->sleep_completion, msecs_to_jiffies(100))) {
> +		err = -ETIMEDOUT;
> +		goto out_resume;
> +	}
> +	return 0;
> +
> +out_resume:
> +	tipd_resume(tps);
> +	return err;
> +}

[Severity: High]
Does this error path leave the device in an unresponsive state? If the sleep 
command succeeds but wait_for_completion_timeout() times out (perhaps due to 
a lost interrupt), we jump to out_resume and call tipd_resume(). Since the
device was commanded to sleep and no spmi_command_wakeup() is issued in this
error path, the regmap reads inside tipd_resume() could fail or hang.


I also noticed a couple of pre-existing issues in the core code that might be
worth addressing:

[Severity: High]
This is a pre-existing issue, but does tipd_suspend() correctly handle cases
where the wakeup-source property is present in the device tree but the irq
property is missing?

drivers/usb/typec/tipd/core.c:tipd_suspend() {
    if (tps->wakeup) {
        disable_irq(tps->irq);
        enable_irq_wake(tps->irq);
    } else if (tps->reset) {
...

In tipd_init(), tps->wakeup can be set to true even if tps->irq is 0. If that
happens, calling disable_irq() and enable_irq_wake() here will operate on
IRQ 0, which might disable a core system interrupt like the timer.


[Severity: High]
This isn't a regression introduced by this patch, but could tipd_init() leak 
the delayed work queue if connect() fails?

drivers/usb/typec/tipd/core.c:tipd_init() {
...
    if (status & TPS_STATUS_PLUG_PRESENT) {
        ret = -EINVAL;
        ...
        ret = tps->data->connect(tps, status);
        if (ret)
            dev_err(tps->dev, "failed to register partner\n");
    }

    if (tps->irq) {
        ...
    } else {
        ...
        INIT_DELAYED_WORK(&tps->wq_poll, tps6598x_poll_work);
        queue_delayed_work(system_power_efficient_wq, &tps->wq_poll,
                   msecs_to_jiffies(POLL_INTERVAL));
    }

    if (ret)
        goto err_disconnect;
...

If tps->data->connect() fails, ret holds an error code. If the device has no
IRQ, we queue the polling work. Since ret isn't cleared, the subsequent
if (ret) check triggers a jump to err_disconnect, freeing the tps structure
without cancelling the delayed work queue. This could lead to a
use-after-free when the timer fires.

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260801-tipd-ace3-v3-0-8332f2eca4fc@chaosmail.tech?part=3

      reply	other threads:[~2026-08-01 21:45 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-08-01 21:30 [PATCH v3 0/3] usb: typec: tipd: Add sn201202x (ACE3) support Sasha Finkelstein
2026-08-01 21:30 ` [PATCH v3 1/3] dt-bindings: usb: tps6598x: Add sn201202x/ACE3 Sasha Finkelstein
2026-08-01 21:30 ` [PATCH v3 2/3] usb: typec: tipd: Factor out i2c specifics Sasha Finkelstein
2026-08-01 21:42   ` sashiko-bot
2026-08-01 21:30 ` [PATCH v3 3/3] usb: typec: tipd: Add sn201202x support Sasha Finkelstein
2026-08-01 21:45   ` 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=20260801214507.4CBB21F00AC4@smtp.kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=conor+dt@kernel.org \
    --cc=devicetree@vger.kernel.org \
    --cc=k@chaosmail.tech \
    --cc=robh@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 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.