1 // SPDX-License-Identifier: GPL-2.0-only
3 * GPIO driver for the ACCES 104-IDIO-16 family
4 * Copyright (C) 2015 William Breathitt Gray
6 * This driver supports the following ACCES devices: 104-IDIO-16,
7 * 104-IDIO-16E, 104-IDO-16, 104-IDIO-8, 104-IDIO-8E, and 104-IDO-8.
9 #include <linux/bits.h>
10 #include <linux/device.h>
11 #include <linux/errno.h>
12 #include <linux/gpio/driver.h>
14 #include <linux/ioport.h>
15 #include <linux/interrupt.h>
16 #include <linux/irqdesc.h>
17 #include <linux/isa.h>
18 #include <linux/kernel.h>
19 #include <linux/module.h>
20 #include <linux/moduleparam.h>
21 #include <linux/spinlock.h>
22 #include <linux/types.h>
24 #define IDIO_16_EXTENT 8
25 #define MAX_NUM_IDIO_16 max_num_isa_dev(IDIO_16_EXTENT)
27 static unsigned int base[MAX_NUM_IDIO_16];
28 static unsigned int num_idio_16;
29 module_param_hw_array(base, uint, ioport, &num_idio_16, 0);
30 MODULE_PARM_DESC(base, "ACCES 104-IDIO-16 base addresses");
32 static unsigned int irq[MAX_NUM_IDIO_16];
33 static unsigned int num_irq;
34 module_param_hw_array(irq, uint, irq, &num_irq, 0);
35 MODULE_PARM_DESC(irq, "ACCES 104-IDIO-16 interrupt line numbers");
38 * struct idio_16_reg - device registers structure
40 * Write: FET Drive Outputs 0-7
41 * @in0_7: Read: Isolated Inputs 0-7
42 * Write: Clear Interrupt
43 * @irq_ctl: Read: Enable IRQ
47 * Write: FET Drive Outputs 8-15
48 * @in8_15: Read: Isolated Inputs 8-15
61 * struct idio_16_gpio - GPIO device private data structure
62 * @chip: instance of the gpio_chip
63 * @lock: synchronization lock to prevent I/O race conditions
64 * @irq_mask: I/O bits affected by interrupts
65 * @reg: I/O address offset for the device registers
66 * @out_state: output bits state
69 struct gpio_chip chip;
71 unsigned long irq_mask;
72 struct idio_16_reg __iomem *reg;
73 unsigned int out_state;
76 static int idio_16_gpio_get_direction(struct gpio_chip *chip,
80 return GPIO_LINE_DIRECTION_IN;
82 return GPIO_LINE_DIRECTION_OUT;
85 static int idio_16_gpio_direction_input(struct gpio_chip *chip,
91 static int idio_16_gpio_direction_output(struct gpio_chip *chip,
92 unsigned int offset, int value)
94 chip->set(chip, offset, value);
98 static int idio_16_gpio_get(struct gpio_chip *chip, unsigned int offset)
100 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
101 const unsigned int mask = BIT(offset-16);
107 return !!(ioread8(&idio16gpio->reg->in0_7) & mask);
109 return !!(ioread8(&idio16gpio->reg->in8_15) & (mask>>8));
112 static int idio_16_gpio_get_multiple(struct gpio_chip *chip,
113 unsigned long *mask, unsigned long *bits)
115 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
118 if (*mask & GENMASK(23, 16))
119 *bits |= (unsigned long)ioread8(&idio16gpio->reg->in0_7) << 16;
120 if (*mask & GENMASK(31, 24))
121 *bits |= (unsigned long)ioread8(&idio16gpio->reg->in8_15) << 24;
126 static void idio_16_gpio_set(struct gpio_chip *chip, unsigned int offset,
129 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
130 const unsigned int mask = BIT(offset);
136 raw_spin_lock_irqsave(&idio16gpio->lock, flags);
139 idio16gpio->out_state |= mask;
141 idio16gpio->out_state &= ~mask;
144 iowrite8(idio16gpio->out_state >> 8, &idio16gpio->reg->out8_15);
146 iowrite8(idio16gpio->out_state, &idio16gpio->reg->out0_7);
148 raw_spin_unlock_irqrestore(&idio16gpio->lock, flags);
151 static void idio_16_gpio_set_multiple(struct gpio_chip *chip,
152 unsigned long *mask, unsigned long *bits)
154 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
157 raw_spin_lock_irqsave(&idio16gpio->lock, flags);
159 idio16gpio->out_state &= ~*mask;
160 idio16gpio->out_state |= *mask & *bits;
163 iowrite8(idio16gpio->out_state, &idio16gpio->reg->out0_7);
164 if ((*mask >> 8) & 0xFF)
165 iowrite8(idio16gpio->out_state >> 8, &idio16gpio->reg->out8_15);
167 raw_spin_unlock_irqrestore(&idio16gpio->lock, flags);
170 static void idio_16_irq_ack(struct irq_data *data)
174 static void idio_16_irq_mask(struct irq_data *data)
176 struct gpio_chip *chip = irq_data_get_irq_chip_data(data);
177 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
178 const unsigned long offset = irqd_to_hwirq(data);
181 idio16gpio->irq_mask &= ~BIT(offset);
182 gpiochip_disable_irq(chip, offset);
184 if (!idio16gpio->irq_mask) {
185 raw_spin_lock_irqsave(&idio16gpio->lock, flags);
187 iowrite8(0, &idio16gpio->reg->irq_ctl);
189 raw_spin_unlock_irqrestore(&idio16gpio->lock, flags);
193 static void idio_16_irq_unmask(struct irq_data *data)
195 struct gpio_chip *chip = irq_data_get_irq_chip_data(data);
196 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(chip);
197 const unsigned long offset = irqd_to_hwirq(data);
198 const unsigned long prev_irq_mask = idio16gpio->irq_mask;
201 gpiochip_enable_irq(chip, offset);
202 idio16gpio->irq_mask |= BIT(offset);
204 if (!prev_irq_mask) {
205 raw_spin_lock_irqsave(&idio16gpio->lock, flags);
207 ioread8(&idio16gpio->reg->irq_ctl);
209 raw_spin_unlock_irqrestore(&idio16gpio->lock, flags);
213 static int idio_16_irq_set_type(struct irq_data *data, unsigned int flow_type)
215 /* The only valid irq types are none and both-edges */
216 if (flow_type != IRQ_TYPE_NONE &&
217 (flow_type & IRQ_TYPE_EDGE_BOTH) != IRQ_TYPE_EDGE_BOTH)
223 static const struct irq_chip idio_16_irqchip = {
224 .name = "104-idio-16",
225 .irq_ack = idio_16_irq_ack,
226 .irq_mask = idio_16_irq_mask,
227 .irq_unmask = idio_16_irq_unmask,
228 .irq_set_type = idio_16_irq_set_type,
229 .flags = IRQCHIP_IMMUTABLE,
230 GPIOCHIP_IRQ_RESOURCE_HELPERS,
233 static irqreturn_t idio_16_irq_handler(int irq, void *dev_id)
235 struct idio_16_gpio *const idio16gpio = dev_id;
236 struct gpio_chip *const chip = &idio16gpio->chip;
239 for_each_set_bit(gpio, &idio16gpio->irq_mask, chip->ngpio)
240 generic_handle_domain_irq(chip->irq.domain, gpio);
242 raw_spin_lock(&idio16gpio->lock);
244 iowrite8(0, &idio16gpio->reg->in0_7);
246 raw_spin_unlock(&idio16gpio->lock);
251 #define IDIO_16_NGPIO 32
252 static const char *idio_16_names[IDIO_16_NGPIO] = {
253 "OUT0", "OUT1", "OUT2", "OUT3", "OUT4", "OUT5", "OUT6", "OUT7",
254 "OUT8", "OUT9", "OUT10", "OUT11", "OUT12", "OUT13", "OUT14", "OUT15",
255 "IIN0", "IIN1", "IIN2", "IIN3", "IIN4", "IIN5", "IIN6", "IIN7",
256 "IIN8", "IIN9", "IIN10", "IIN11", "IIN12", "IIN13", "IIN14", "IIN15"
259 static int idio_16_irq_init_hw(struct gpio_chip *gc)
261 struct idio_16_gpio *const idio16gpio = gpiochip_get_data(gc);
263 /* Disable IRQ by default */
264 iowrite8(0, &idio16gpio->reg->irq_ctl);
265 iowrite8(0, &idio16gpio->reg->in0_7);
270 static int idio_16_probe(struct device *dev, unsigned int id)
272 struct idio_16_gpio *idio16gpio;
273 const char *const name = dev_name(dev);
274 struct gpio_irq_chip *girq;
277 idio16gpio = devm_kzalloc(dev, sizeof(*idio16gpio), GFP_KERNEL);
281 if (!devm_request_region(dev, base[id], IDIO_16_EXTENT, name)) {
282 dev_err(dev, "Unable to lock port addresses (0x%X-0x%X)\n",
283 base[id], base[id] + IDIO_16_EXTENT);
287 idio16gpio->reg = devm_ioport_map(dev, base[id], IDIO_16_EXTENT);
288 if (!idio16gpio->reg)
291 idio16gpio->chip.label = name;
292 idio16gpio->chip.parent = dev;
293 idio16gpio->chip.owner = THIS_MODULE;
294 idio16gpio->chip.base = -1;
295 idio16gpio->chip.ngpio = IDIO_16_NGPIO;
296 idio16gpio->chip.names = idio_16_names;
297 idio16gpio->chip.get_direction = idio_16_gpio_get_direction;
298 idio16gpio->chip.direction_input = idio_16_gpio_direction_input;
299 idio16gpio->chip.direction_output = idio_16_gpio_direction_output;
300 idio16gpio->chip.get = idio_16_gpio_get;
301 idio16gpio->chip.get_multiple = idio_16_gpio_get_multiple;
302 idio16gpio->chip.set = idio_16_gpio_set;
303 idio16gpio->chip.set_multiple = idio_16_gpio_set_multiple;
304 idio16gpio->out_state = 0xFFFF;
306 girq = &idio16gpio->chip.irq;
307 gpio_irq_chip_set_chip(girq, &idio_16_irqchip);
308 /* This will let us handle the parent IRQ in the driver */
309 girq->parent_handler = NULL;
310 girq->num_parents = 0;
311 girq->parents = NULL;
312 girq->default_type = IRQ_TYPE_NONE;
313 girq->handler = handle_edge_irq;
314 girq->init_hw = idio_16_irq_init_hw;
316 raw_spin_lock_init(&idio16gpio->lock);
318 err = devm_gpiochip_add_data(dev, &idio16gpio->chip, idio16gpio);
320 dev_err(dev, "GPIO registering failed (%d)\n", err);
324 err = devm_request_irq(dev, irq[id], idio_16_irq_handler, 0, name,
327 dev_err(dev, "IRQ handler registering failed (%d)\n", err);
334 static struct isa_driver idio_16_driver = {
335 .probe = idio_16_probe,
337 .name = "104-idio-16"
341 module_isa_driver_with_irq(idio_16_driver, num_idio_16, num_irq);
343 MODULE_AUTHOR("William Breathitt Gray <vilhelm.gray@gmail.com>");
344 MODULE_DESCRIPTION("ACCES 104-IDIO-16 GPIO driver");
345 MODULE_LICENSE("GPL v2");