[PATCH v3 1/5] gpiolib: don't overwrite the entire flags field in gpiod_get_direction()

From: Bartosz Golaszewski

Date: Tue Nov 10 2026 - 08:52:12 EST


gpiod_get_direction() snapshots desc->flags with READ_ONCE(), updates
FLAG_IS_OUT in the local copy and writes the whole word back with
WRITE_ONCE(). Any bit that a concurrent user sets or clears atomically in
between - for instance: FLAG_USED_AS_IRQ from gpiochip_lock_as_irq() - is
silently lost.

Update FLAG_IS_OUT with a single atomic assign_bit() directly on
desc->flags. The earlier READ_ONCE() snapshot is only used for the
open-drain check and stays.

Cc: stable@xxxxxxxxxxxxxxx
Fixes: 2559f2e09211 ("gpio: reinforce desc->flags handling")
Signed-off-by: Bartosz Golaszewski <bartosz.golaszewski@xxxxxxxxxxxxxxxx>
---
drivers/gpio/gpiolib.c | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/gpio/gpiolib.c b/drivers/gpio/gpiolib.c
index 9282d9874e1109b7f030a3e83598ad016c2bf629..1285a993a1ceeff719142ad019451d2e9af6a520 100644
--- a/drivers/gpio/gpiolib.c
+++ b/drivers/gpio/gpiolib.c
@@ -486,8 +486,7 @@ int gpiod_get_direction(struct gpio_desc *desc)
if (ret > 0)
ret = 1;

- assign_bit(GPIOD_FLAG_IS_OUT, &flags, !ret);
- WRITE_ONCE(desc->flags, flags);
+ assign_bit(GPIOD_FLAG_IS_OUT, &desc->flags, !ret);

return ret;
}

--
2.47.3