]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
gpio: xilinx: Use better bitmap APIs where appropriate
authorAndy Shevchenko <andriy.shevchenko@linux.intel.com>
Wed, 5 Feb 2025 09:31:10 +0000 (11:31 +0200)
committerBartosz Golaszewski <bartosz.golaszewski@linaro.org>
Wed, 12 Feb 2025 09:58:14 +0000 (10:58 +0100)
There are bitmap_gather() and bitmap_scatter() that are factually
simplified version of the APIs used in the driver. Use them where
appropriate.

While at it, replace bitmap_bitremap() with find_nth_bit()
for the sake of simplification.

Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Link: https://lore.kernel.org/r/20250205093200.373709-2-andriy.shevchenko@linux.intel.com
Signed-off-by: Bartosz Golaszewski <bartosz.golaszewski@linaro.org>
drivers/gpio/gpio-xilinx.c

index 792d94c49077c361a5901c46c744594ea5c8ecee..1ff527ccf6c75553f22c325fa99558302f61be37 100644 (file)
@@ -45,8 +45,7 @@
  * struct xgpio_instance - Stores information about GPIO device
  * @gc: GPIO chip
  * @regs: register block
- * @hw_map: GPIO pin mapping on hardware side
- * @sw_map: GPIO pin mapping on software side
+ * @map: GPIO pin mapping on hardware side
  * @state: GPIO write state shadow register
  * @last_irq_read: GPIO read state register from last interrupt
  * @dir: GPIO direction shadow register
@@ -60,8 +59,7 @@
 struct xgpio_instance {
        struct gpio_chip gc;
        void __iomem *regs;
-       DECLARE_BITMAP(hw_map, 64);
-       DECLARE_BITMAP(sw_map, 64);
+       DECLARE_BITMAP(map, 64);
        DECLARE_BITMAP(state, 64);
        DECLARE_BITMAP(last_irq_read, 64);
        DECLARE_BITMAP(dir, 64);
@@ -73,16 +71,6 @@ struct xgpio_instance {
        struct clk *clk;
 };
 
-static inline int xgpio_from_bit(struct xgpio_instance *chip, int bit)
-{
-       return bitmap_bitremap(bit, chip->hw_map, chip->sw_map, 64);
-}
-
-static inline int xgpio_to_bit(struct xgpio_instance *chip, int gpio)
-{
-       return bitmap_bitremap(gpio, chip->sw_map, chip->hw_map, 64);
-}
-
 static inline u32 xgpio_get_value32(const unsigned long *map, int bit)
 {
        const size_t index = BIT_WORD(bit);
@@ -128,7 +116,8 @@ static void xgpio_write_ch(struct xgpio_instance *chip, int reg, int bit, unsign
 
 static void xgpio_read_ch_all(struct xgpio_instance *chip, int reg, unsigned long *a)
 {
-       int bit, lastbit = xgpio_to_bit(chip, chip->gc.ngpio - 1);
+       unsigned long lastbit = find_nth_bit(chip->map, 64, chip->gc.ngpio - 1);
+       int bit;
 
        for (bit = 0; bit <= lastbit ; bit += 32)
                xgpio_read_ch(chip, reg, bit, a);
@@ -136,7 +125,8 @@ static void xgpio_read_ch_all(struct xgpio_instance *chip, int reg, unsigned lon
 
 static void xgpio_write_ch_all(struct xgpio_instance *chip, int reg, unsigned long *a)
 {
-       int bit, lastbit = xgpio_to_bit(chip, chip->gc.ngpio - 1);
+       unsigned long lastbit = find_nth_bit(chip->map, 64, chip->gc.ngpio - 1);
+       int bit;
 
        for (bit = 0; bit <= lastbit ; bit += 32)
                xgpio_write_ch(chip, reg, bit, a);
@@ -156,7 +146,7 @@ static void xgpio_write_ch_all(struct xgpio_instance *chip, int reg, unsigned lo
 static int xgpio_get(struct gpio_chip *gc, unsigned int gpio)
 {
        struct xgpio_instance *chip = gpiochip_get_data(gc);
-       int bit = xgpio_to_bit(chip, gpio);
+       unsigned long bit = find_nth_bit(chip->map, 64, gpio);
        DECLARE_BITMAP(state, 64);
 
        xgpio_read_ch(chip, XGPIO_DATA_OFFSET, bit, state);
@@ -177,7 +167,7 @@ static void xgpio_set(struct gpio_chip *gc, unsigned int gpio, int val)
 {
        unsigned long flags;
        struct xgpio_instance *chip = gpiochip_get_data(gc);
-       int bit = xgpio_to_bit(chip, gpio);
+       unsigned long bit = find_nth_bit(chip->map, 64, gpio);
 
        raw_spin_lock_irqsave(&chip->gpio_lock, flags);
 
@@ -207,8 +197,8 @@ static void xgpio_set_multiple(struct gpio_chip *gc, unsigned long *mask,
        unsigned long flags;
        struct xgpio_instance *chip = gpiochip_get_data(gc);
 
-       bitmap_remap(hw_mask, mask, chip->sw_map, chip->hw_map, 64);
-       bitmap_remap(hw_bits, bits, chip->sw_map, chip->hw_map, 64);
+       bitmap_scatter(hw_mask, mask, chip->map, 64);
+       bitmap_scatter(hw_bits, bits, chip->map, 64);
 
        raw_spin_lock_irqsave(&chip->gpio_lock, flags);
 
@@ -234,7 +224,7 @@ static int xgpio_dir_in(struct gpio_chip *gc, unsigned int gpio)
 {
        unsigned long flags;
        struct xgpio_instance *chip = gpiochip_get_data(gc);
-       int bit = xgpio_to_bit(chip, gpio);
+       unsigned long bit = find_nth_bit(chip->map, 64, gpio);
 
        raw_spin_lock_irqsave(&chip->gpio_lock, flags);
 
@@ -263,7 +253,7 @@ static int xgpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val)
 {
        unsigned long flags;
        struct xgpio_instance *chip = gpiochip_get_data(gc);
-       int bit = xgpio_to_bit(chip, gpio);
+       unsigned long bit = find_nth_bit(chip->map, 64, gpio);
 
        raw_spin_lock_irqsave(&chip->gpio_lock, flags);
 
@@ -395,7 +385,7 @@ static void xgpio_irq_mask(struct irq_data *irq_data)
        unsigned long flags;
        struct xgpio_instance *chip = irq_data_get_irq_chip_data(irq_data);
        int irq_offset = irqd_to_hwirq(irq_data);
-       int bit = xgpio_to_bit(chip, irq_offset);
+       unsigned long bit = find_nth_bit(chip->map, 64, irq_offset);
        u32 mask = BIT(bit / 32), temp;
 
        raw_spin_lock_irqsave(&chip->gpio_lock, flags);
@@ -422,7 +412,7 @@ static void xgpio_irq_unmask(struct irq_data *irq_data)
        unsigned long flags;
        struct xgpio_instance *chip = irq_data_get_irq_chip_data(irq_data);
        int irq_offset = irqd_to_hwirq(irq_data);
-       int bit = xgpio_to_bit(chip, irq_offset);
+       unsigned long bit = find_nth_bit(chip->map, 64, irq_offset);
        u32 old_enable = xgpio_get_value32(chip->enable, bit);
        u32 mask = BIT(bit / 32), val;
 
@@ -462,7 +452,7 @@ static int xgpio_set_irq_type(struct irq_data *irq_data, unsigned int type)
 {
        struct xgpio_instance *chip = irq_data_get_irq_chip_data(irq_data);
        int irq_offset = irqd_to_hwirq(irq_data);
-       int bit = xgpio_to_bit(chip, irq_offset);
+       unsigned long bit = find_nth_bit(chip->map, 64, irq_offset);
 
        /*
         * The Xilinx GPIO hardware provides a single interrupt status
@@ -502,10 +492,10 @@ static void xgpio_irqhandler(struct irq_desc *desc)
        struct irq_chip *irqchip = irq_desc_get_chip(desc);
        DECLARE_BITMAP(rising, 64);
        DECLARE_BITMAP(falling, 64);
-       DECLARE_BITMAP(all, 64);
+       DECLARE_BITMAP(hw, 64);
+       DECLARE_BITMAP(sw, 64);
        int irq_offset;
        u32 status;
-       u32 bit;
 
        status = xgpio_readreg(chip->regs + XGPIO_IPISR_OFFSET);
        xgpio_writereg(chip->regs + XGPIO_IPISR_OFFSET, status);
@@ -514,29 +504,28 @@ static void xgpio_irqhandler(struct irq_desc *desc)
 
        raw_spin_lock(&chip->gpio_lock);
 
-       xgpio_read_ch_all(chip, XGPIO_DATA_OFFSET, all);
+       xgpio_read_ch_all(chip, XGPIO_DATA_OFFSET, hw);
 
        bitmap_complement(rising, chip->last_irq_read, 64);
-       bitmap_and(rising, rising, all, 64);
+       bitmap_and(rising, rising, hw, 64);
        bitmap_and(rising, rising, chip->enable, 64);
        bitmap_and(rising, rising, chip->rising_edge, 64);
 
-       bitmap_complement(falling, all, 64);
+       bitmap_complement(falling, hw, 64);
        bitmap_and(falling, falling, chip->last_irq_read, 64);
        bitmap_and(falling, falling, chip->enable, 64);
        bitmap_and(falling, falling, chip->falling_edge, 64);
 
-       bitmap_copy(chip->last_irq_read, all, 64);
-       bitmap_or(all, rising, falling, 64);
+       bitmap_copy(chip->last_irq_read, hw, 64);
+       bitmap_or(hw, rising, falling, 64);
 
        raw_spin_unlock(&chip->gpio_lock);
 
        dev_dbg(gc->parent, "IRQ rising %*pb falling %*pb\n", 64, rising, 64, falling);
 
-       for_each_set_bit(bit, all, 64) {
-               irq_offset = xgpio_from_bit(chip, bit);
+       bitmap_gather(sw, hw, chip->map, 64);
+       for_each_set_bit(irq_offset, sw, 64)
                generic_handle_domain_irq(gc->irq.domain, irq_offset);
-       }
 
        chained_irq_exit(irqchip, desc);
 }
@@ -613,17 +602,14 @@ static int xgpio_probe(struct platform_device *pdev)
        if (width[1] > 32)
                return -EINVAL;
 
-       /* Setup software pin mapping */
-       bitmap_set(chip->sw_map, 0, width[0] + width[1]);
-
        /* Setup hardware pin mapping */
-       bitmap_set(chip->hw_map,  0, width[0]);
-       bitmap_set(chip->hw_map, 32, width[1]);
+       bitmap_set(chip->map,  0, width[0]);
+       bitmap_set(chip->map, 32, width[1]);
 
        raw_spin_lock_init(&chip->gpio_lock);
 
        chip->gc.base = -1;
-       chip->gc.ngpio = bitmap_weight(chip->hw_map, 64);
+       chip->gc.ngpio = bitmap_weight(chip->map, 64);
        chip->gc.parent = dev;
        chip->gc.direction_input = xgpio_dir_in;
        chip->gc.direction_output = xgpio_dir_out;