[PATCH 10/21] leds: class: Initialise trigger_lock before exposing sysfs attributes

From: Lee Jones

Date: Wed Oct 21 2026 - 08:50:48 EST


led_classdev_register_ext() calls device_create_with_groups(), which
creates the LED trigger sysfs attributes and emits the KOBJ_ADD uevent,
before initialising led_cdev->trigger_lock with init_rwsem().

Because trigger_read() and trigger_may_offload_to_hw_show() acquire
led_cdev->trigger_lock without holding led_cdev->led_access, a
concurrent sysfs read during registration can call down_read() on an
uninitialised rw_semaphore.

Initialise led_cdev->trigger_lock before calling
device_create_with_groups().

Fixes: 14b5d6dd40b3 ("leds: Fix race between LED device uevent and actual attributes creation")
Closes: https://sashiko.dev/#/bug/linux-376c7db5-ddc1-4faa-9f5b-43d2d3b7cb0d
Cc: stable@xxxxxxxxxxxxxxx
Signed-off-by: Lee Jones <lee@xxxxxxxxxx>
---
drivers/leds/led-class.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/leds/led-class.c b/drivers/leds/led-class.c
index 00be3cb96c00..2a3040fa3c4b 100644
--- a/drivers/leds/led-class.c
+++ b/drivers/leds/led-class.c
@@ -532,6 +532,9 @@ int led_classdev_register_ext(struct device *parent,
if (led_cdev->color >= LED_COLOR_ID_MAX)
dev_warn(parent, "LED %s color identifier out of range\n", final_name);

+#ifdef CONFIG_LEDS_TRIGGERS
+ init_rwsem(&led_cdev->trigger_lock);
+#endif
mutex_init(&led_cdev->led_access);
mutex_lock(&led_cdev->led_access);
led_cdev->dev = device_create_with_groups(&leds_class, parent, 0,
@@ -554,9 +557,6 @@ int led_classdev_register_ext(struct device *parent,
}

led_cdev->work_flags = 0;
-#ifdef CONFIG_LEDS_TRIGGERS
- init_rwsem(&led_cdev->trigger_lock);
-#endif
#ifdef CONFIG_LEDS_BRIGHTNESS_HW_CHANGED
led_cdev->brightness_hw_changed = -1;
#endif
--
2.56.0.218.g1ec904b173-goog