[PATCHv2 7/8] gpio: ppc44x: fix undefined behavior in GPIO_MASK2 macro
Rosen Penev <[email protected]> Mon, 3 Aug 2026 15:35:38 -0700
| Newsgroups | org.ozlabs.lists.linuxppc-dev,org.kernel.vger.linux-gpio,org.kernel.vger.linux-kernel |
|---|---|
| Message-ID | <[email protected]> |
Shifting a 32-bit unsigned integer by 32 or more places is undefined behavior in C. GPIO_MASK2 computes its shift amount as (gpio) * 2, and for pins 16-31 in the OSRH/TSRH bank this yields shifts of 32-62. While this happens to work on PowerPC because slw masks the shift count to the low 5 bits, compilers performing value-range propagation may assume the else branch is unreachable and optimize it away, or may evaluate the shift as zero on other architectures via COMPILE_TEST. Mask gpio to the 16-pin bank index so the shift stays within [0, 30]. The registers are banked (OSRL/TSRL for gpio 0-15, OSRH/TSRH for gpio 16-31) with an identical 2-bit-per-pin layout from MSB to LSB, so masking to the within-bank index preserves the intended behavior. Assisted-by: opencode:big-pickle Signed-off-by: Rosen Penev <[email protected]> --- drivers/gpio/gpio-ppc44x.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpio/gpio-ppc44x.c b/drivers/gpio/gpio-ppc44x.c index fd543fbb959a..9fdc84e922f4 100644 --- a/drivers/gpio/gpio-ppc44x.c +++ b/drivers/gpio/gpio-ppc44x.c @@ -19,7 +19,7 @@ #include <linux/platform_device.h> #define GPIO_MASK(gpio) (0x80000000 >> (gpio)) -#define GPIO_MASK2(gpio) (0xc0000000 >> ((gpio) * 2)) +#define GPIO_MASK2(gpio) (0xc0000000 >> (((gpio) % 16) * 2)) /* Physical GPIO register layout */ struct ppc44x_gpio { -- 2.55.0