All of lore.kernel.org
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Markus Probst" <markus.probst@posteo.de>
Cc: lee@kernel.org, ojeda@kernel.org, linux-pci@vger.kernel.org,
	linux-leds@vger.kernel.org
Subject: Re: [PATCH v24 3/4] rust: leds: add multicolor classdev abstractions
Date: Wed, 02 Sep 2026 23:15:44 +0000	[thread overview]
Message-ID: <20260902231544.8B2C71F000E9@smtp.kernel.org> (raw)
In-Reply-To: <20260903-rust_leds-v24-3-8d9e4c04db69@posteo.de>

Thank you for your contribution! Sashiko AI review found 4 potential issue(s) to consider:
- [High] Plain non-atomic reads of `intensity` and `brightness` from `UnsafeCell` in `MultiColorSubLed` cause a data race and Undefined Behavior with concurrent C subsystem modifications.
- [High] Calling `led_mc_calc_color_components` outside of the driver's locking creates a data race and TOCTOU vulnerability.
- [High] Casting concurrent pointers to `&mut usize` in `blink_set_callback` creates an aliasing violation (Undefined Behavior).
- [Low] The commit message description is not capitalized, violating the LED subsystem guidelines.
--

commit 0c1eb1680fe4ed1aa0ee60e6b95decec69575365
Author: Markus Probst <markus.probst@posteo.de>

rust: leds: add multicolor classdev abstractions

This commit introduces the necessary Rust abstractions to support multicolor
LED class devices. It provides wrappers around the C structures mc_subled
and led_classdev_mc, alongside integration with the LED device builder.

> rust: leds: add multicolor classdev abstractions
>
> Implement the abstractions needed for multicolor led class devices,

[Severity: Low]
This isn't a bug, but the LED subsystem guidelines require capitalizing the
description after the subsystem prefix. Should the subject be capitalized as
"Add multicolor classdev abstractions", and similarly the body text?

> diff --git a/rust/kernel/led/multicolor.rs b/rust/kernel/led/multicolor.rs
> new file mode 100644
> --- /dev/null
> +++ b/rust/kernel/led/multicolor.rs
[ ... ]
> +impl MultiColorSubLed {
[ ... ]
> +    pub const fn intensity(&self) -> u32 {
> +        // SAFETY:
> +        // - self.intensity.get() is a valid pointer to u32.
> +        // - We don't have exclusive or immutable access to self.intensity,
> +        //   but the alignment should prevent "load tearing".
> +        unsafe { *self.intensity.get() }
> +    }

[Severity: High]
Does this plain read cause Undefined Behavior under Rust's concurrency rules?

If a trigger from timer or interrupt context calls intensity() concurrently
while sysfs (via multi_intensity_store) modifies the memory under the
led_access mutex, this creates a data race.

Since plain non-atomic reads of concurrently mutated memory are considered
Undefined Behavior in Rust, should this use an atomic read or read_volatile
instead?

> +
> +    /// The brightness of the sub led.
> +    #[inline]
> +    pub const fn brightness(&self) -> u32 {
> +        // SAFETY:
> +        // - self.brightness.get() is a valid pointer to u32.
> +        // - We don't have exclusive or immutable access to self.brightness,
> +        //   but the alignment should prevent "load tearing".
> +        unsafe { *self.brightness.get() }
> +    }

[Severity: High]
Does this have the same data race and Undefined Behavior issue as the
intensity() read above?

[ ... ]
> +    unsafe extern "C" fn brightness_set_callback(
> +        led_cdev: *mut bindings::led_classdev,
> +        brightness: u32,
> +    ) {
[ ... ]
> +        // SAFETY: classdev.classdev.get() is guaranteed to be a pointer to a valid
> +        // led_classdev_mc.
> +        unsafe { bindings::led_mc_calc_color_components(classdev.classdev.get(), brightness) };
> +
> +        let _ = classdev.ops.brightness_set(parent, classdev, brightness);
> +    }

[Severity: High]
Can calling bindings::led_mc_calc_color_components() before the driver 
acquires its lock cause data corruption of the hardware state?

Concurrent calls to brightness_set_callback, for example from sysfs and a
hardware trigger, will execute bindings::led_mc_calc_color_components()
outside any locks, racing to overwrite the subled_info array. 

The driver's lock in classdev.ops.brightness_set is acquired too late to
prevent this corruption. Should C drivers invoke
bindings::led_mc_calc_color_components() while holding their own lock
instead?

[ ... ]
> +    unsafe extern "C" fn brightness_set_blocking_callback(
> +        led_cdev: *mut bindings::led_classdev,
> +        brightness: u32,
> +    ) -> i32 {
> +        from_result(|| {
[ ... ]
> +            // SAFETY: classdev.classdev.get() is guaranteed to be a pointer to a valid
> +            // led_classdev_mc.
> +            unsafe { bindings::led_mc_calc_color_components(classdev.classdev.get(), brightness) };
> +
> +            classdev.ops.brightness_set(parent, classdev, brightness)?;
> +            Ok(0)
> +        })
> +    }

[Severity: High]
Does this have the same data race vulnerability as brightness_set_callback()
above?

[ ... ]
> +    unsafe extern "C" fn blink_set_callback(
> +        led_cdev: *mut bindings::led_classdev,
> +        delay_on: *mut usize,
> +        delay_off: *mut usize,
> +    ) -> i32 {
> +        from_result(|| {
[ ... ]
> +            classdev.ops.blink_set(
> +                parent,
> +                classdev,
> +                // SAFETY: The function's contract guarantees that delay_on points to a usize
> +                // and is exclusive for the period of this function.
> +                unsafe { &mut *delay_on },
> +                // SAFETY: The function's contract guarantees that delay_off points to a usize
> +                // and is exclusive for the period of this function.
> +                unsafe { &mut *delay_off },
> +            )?;
> +            Ok(0)
> +        })
> +    }

[Severity: High]
Does casting these pointers to exclusive mutable references violate Rust's
aliasing rules and cause Undefined Behavior?

The C subsystem calls blink_set with pointers to led_cdev->blink_delay_on
and blink_delay_off. Concurrently, sysfs handlers like delay_on_store write
to these fields without taking a lock. 
    
Casting these shared, concurrently accessed pointers to exclusive mutable
references falsely asserts exclusive access.

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260903-rust_leds-v24-0-8d9e4c04db69@posteo.de?part=3

  reply	other threads:[~2026-09-02 23:15 UTC|newest]

Thread overview: 13+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-09-02 23:01 [PATCH v24 0/4] rust: leds: add led classdev abstractions Markus Probst
2026-09-02 23:01 ` [PATCH v24 1/4] rust: leds: add basic " Markus Probst
2026-09-02 23:17   ` sashiko-bot
2026-09-04 13:03   ` Gary Guo
2026-09-04 13:15     ` Markus Probst
2026-09-04 13:32       ` Gary Guo
2026-09-04 14:04         ` Markus Probst
2026-09-02 23:01 ` [PATCH v24 2/4] rust: leds: add Mode trait Markus Probst
2026-09-02 23:08   ` sashiko-bot
2026-09-02 23:01 ` [PATCH v24 3/4] rust: leds: add multicolor classdev abstractions Markus Probst
2026-09-02 23:15   ` sashiko-bot [this message]
2026-09-02 23:01 ` [PATCH v24 4/4] MAINTAINERS: rust: leds: Add rust abstraction entry Markus Probst
2026-09-02 23:35 ` [PATCH v24 0/4] rust: leds: add led classdev abstractions Markus Probst

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=20260902231544.8B2C71F000E9@smtp.kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=lee@kernel.org \
    --cc=linux-leds@vger.kernel.org \
    --cc=linux-pci@vger.kernel.org \
    --cc=markus.probst@posteo.de \
    --cc=ojeda@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.