diff options
author | William Breathitt Gray <william.gray@linaro.org> | 2022-07-20 09:45:58 -0400 |
---|---|---|
committer | Bartosz Golaszewski <brgl@bgdev.pl> | 2022-07-20 17:44:32 +0200 |
commit | cc442e4db9cb851f18cd3ea0c933e016b29fafc3 (patch) | |
tree | 3f4b69b5327b011ad41baedd234f068b8128dde3 | |
parent | 2c05a0f29f41cbb1e31e94a53e7dacf0622706bb (diff) |
gpio: 104-idio-16: Implement and utilize register structures
Reduce magic numbers and improve code readability by implementing and
utilizing named register data structures.
Tested-by: Fred Eckert <Frede@cmslaser.com>
Reviewed-by: Linus Walleij <linus.walleij@linaro.org>
Cc: John Hentges <jhentges@accesio.com>
Cc: Jay Dolan <jay.dolan@accesio.com>
Signed-off-by: William Breathitt Gray <william.gray@linaro.org>
Signed-off-by: Bartosz Golaszewski <brgl@bgdev.pl>
-rw-r--r-- | drivers/gpio/gpio-104-idio-16.c | 60 |
1 files changed, 42 insertions, 18 deletions
diff --git a/drivers/gpio/gpio-104-idio-16.c b/drivers/gpio/gpio-104-idio-16.c index 45f7ad8573e1..65a5f581d981 100644 --- a/drivers/gpio/gpio-104-idio-16.c +++ b/drivers/gpio/gpio-104-idio-16.c @@ -6,7 +6,7 @@ * This driver supports the following ACCES devices: 104-IDIO-16, * 104-IDIO-16E, 104-IDO-16, 104-IDIO-8, 104-IDIO-8E, and 104-IDO-8. */ -#include <linux/bitops.h> +#include <linux/bits.h> #include <linux/device.h> #include <linux/errno.h> #include <linux/gpio/driver.h> @@ -19,6 +19,7 @@ #include <linux/module.h> #include <linux/moduleparam.h> #include <linux/spinlock.h> +#include <linux/types.h> #define IDIO_16_EXTENT 8 #define MAX_NUM_IDIO_16 max_num_isa_dev(IDIO_16_EXTENT) @@ -33,18 +34,41 @@ module_param_hw_array(irq, uint, irq, NULL, 0); MODULE_PARM_DESC(irq, "ACCES 104-IDIO-16 interrupt line numbers"); /** + * struct idio_16_reg - device registers structure + * @out0_7: Read: N/A + * Write: FET Drive Outputs 0-7 + * @in0_7: Read: Isolated Inputs 0-7 + * Write: Clear Interrupt + * @irq_ctl: Read: Enable IRQ + * Write: Disable IRQ + * @unused: N/A + * @out8_15: Read: N/A + * Write: FET Drive Outputs 8-15 + * @in8_15: Read: Isolated Inputs 8-15 + * Write: N/A + */ +struct idio_16_reg { + u8 out0_7; + u8 in0_7; + u8 irq_ctl; + u8 unused; + u8 out8_15; + u8 in8_15; +}; + +/** * struct idio_16_gpio - GPIO device private data structure * @chip: instance of the gpio_chip * @lock: synchronization lock to prevent I/O race conditions * @irq_mask: I/O bits affected by interrupts - * @base: base port address of the GPIO device + * @reg: I/O address offset for the device registers * @out_state: output bits state */ struct idio_16_gpio { struct gpio_chip chip; raw_spinlock_t lock; unsigned long irq_mask; - void __iomem *base; + struct idio_16_reg __iomem *reg; unsigned int out_state; }; @@ -79,9 +103,9 @@ static int idio_16_gpio_get(struct gpio_chip *chip, unsigned int offset) return -EINVAL; if (offset < 24) - return !!(ioread8(idio16gpio->base + 1) & mask); + return !!(ioread8(&idio16gpio->reg->in0_7) & mask); - return !!(ioread8(idio16gpio->base + 5) & (mask>>8)); + return !!(ioread8(&idio16gpio->reg->in8_15) & (mask>>8)); } static int idio_16_gpio_get_multiple(struct gpio_chip *chip, @@ -91,9 +115,9 @@ static int idio_16_gpio_get_multiple(struct gpio_chip *chip, *bits = 0; if (*mask & GENMASK(23, 16)) - *bits |= (unsigned long)ioread8(idio16gpio->base + 1) << 16; + *bits |= (unsigned long)ioread8(&idio16gpio->reg->in0_7) << 16; if (*mask & GENMASK(31, 24)) - *bits |= (unsigned long)ioread8(idio16gpio->base + 5) << 24; + *bits |= (unsigned long)ioread8(&idio16gpio->reg->in8_15) << 24; return 0; } @@ -116,9 +140,9 @@ static void idio_16_gpio_set(struct gpio_chip *chip, unsigned int offset, idio16gpio->out_state &= ~mask; if (offset > 7) - iowrite8(idio16gpio->out_state >> 8, idio16gpio->base + 4); + iowrite8(idio16gpio->out_state >> 8, &idio16gpio->reg->out8_15); else - iowrite8(idio16gpio->out_state, idio16gpio->base); + iowrite8(idio16gpio->out_state, &idio16gpio->reg->out0_7); raw_spin_unlock_irqrestore(&idio16gpio->lock, flags); } @@ -135,9 +159,9 @@ static void idio_16_gpio_set_multiple(struct gpio_chip *chip, idio16gpio->out_state |= *mask & *bits; if (*mask & 0xFF) - iowrite8(idio16gpio->out_state, idio16gpio->base); + iowrite8(idio16gpio->out_state, &idio16gpio->reg->out0_7); if ((*mask >> 8) & 0xFF) - iowrite8(idio16gpio->out_state >> 8, idio16gpio->base + 4); + iowrite8(idio16gpio->out_state >> 8, &idio16gpio->reg->out8_15); raw_spin_unlock_irqrestore(&idio16gpio->lock, flags); } @@ -158,7 +182,7 @@ static void idio_16_irq_mask(struct irq_data *data) if (!idio16gpio->irq_mask) { raw_spin_lock_irqsave(&idio16gpio->lock, flags); - iowrite8(0, idio16gpio->base + 2); + iowrite8(0, &idio16gpio->reg->irq_ctl); raw_spin_unlock_irqrestore(&idio16gpio->lock, flags); } @@ -177,7 +201,7 @@ static void idio_16_irq_unmask(struct irq_data *data) if (!prev_irq_mask) { raw_spin_lock_irqsave(&idio16gpio->lock, flags); - ioread8(idio16gpio->base + 2); + ioread8(&idio16gpio->reg->irq_ctl); raw_spin_unlock_irqrestore(&idio16gpio->lock, flags); } @@ -212,7 +236,7 @@ static irqreturn_t idio_16_irq_handler(int irq, void *dev_id) raw_spin_lock(&idio16gpio->lock); - iowrite8(0, idio16gpio->base + 1); + iowrite8(0, &idio16gpio->reg->in0_7); raw_spin_unlock(&idio16gpio->lock); @@ -232,8 +256,8 @@ static int idio_16_irq_init_hw(struct gpio_chip *gc) struct idio_16_gpio *const idio16gpio = gpiochip_get_data(gc); /* Disable IRQ by default */ - iowrite8(0, idio16gpio->base + 2); - iowrite8(0, idio16gpio->base + 1); + iowrite8(0, &idio16gpio->reg->irq_ctl); + iowrite8(0, &idio16gpio->reg->in0_7); return 0; } @@ -255,8 +279,8 @@ static int idio_16_probe(struct device *dev, unsigned int id) return -EBUSY; } - idio16gpio->base = devm_ioport_map(dev, base[id], IDIO_16_EXTENT); - if (!idio16gpio->base) + idio16gpio->reg = devm_ioport_map(dev, base[id], IDIO_16_EXTENT); + if (!idio16gpio->reg) return -ENOMEM; idio16gpio->chip.label = name; |