1 /* SPDX-License-Identifier: GPL-2.0 */ 2 /* Copyright 2022 William Breathitt Gray */ 3 #ifndef _IDIO_16_H_ 4 #define _IDIO_16_H_ 5 6 #include <linux/spinlock.h> 7 #include <linux/types.h> 8 9 struct device; 10 struct regmap; 11 struct regmap_irq; 12 13 /** 14 * struct idio_16_regmap_config - Configuration for the IDIO-16 register map 15 * @parent: parent device 16 * @map: regmap for the IDIO-16 device 17 * @regmap_irqs: descriptors for individual IRQs 18 * @num_regmap_irqs: number of IRQ descriptors 19 * @irq: IRQ number for the IDIO-16 device 20 * @no_status: device has no status register 21 * @filters: device has input filters 22 */ 23 struct idio_16_regmap_config { 24 struct device *parent; 25 struct regmap *map; 26 const struct regmap_irq *regmap_irqs; 27 int num_regmap_irqs; 28 unsigned int irq; 29 bool no_status; 30 bool filters; 31 }; 32 33 /** 34 * struct idio_16 - IDIO-16 registers structure 35 * @out0_7: Read: FET Drive Outputs 0-7 36 * Write: FET Drive Outputs 0-7 37 * @in0_7: Read: Isolated Inputs 0-7 38 * Write: Clear Interrupt 39 * @irq_ctl: Read: Enable IRQ 40 * Write: Disable IRQ 41 * @filter_ctl: Read: Activate Input Filters 0-15 42 * Write: Deactivate Input Filters 0-15 43 * @out8_15: Read: FET Drive Outputs 8-15 44 * Write: FET Drive Outputs 8-15 45 * @in8_15: Read: Isolated Inputs 8-15 46 * Write: Unused 47 * @irq_status: Read: Interrupt status 48 * Write: Unused 49 */ 50 struct idio_16 { 51 u8 out0_7; 52 u8 in0_7; 53 u8 irq_ctl; 54 u8 filter_ctl; 55 u8 out8_15; 56 u8 in8_15; 57 u8 irq_status; 58 }; 59 60 #define IDIO_16_NOUT 16 61 62 /** 63 * struct idio_16_state - IDIO-16 state structure 64 * @lock: synchronization lock for accessing device state 65 * @out_state: output signals state 66 */ 67 struct idio_16_state { 68 spinlock_t lock; 69 DECLARE_BITMAP(out_state, IDIO_16_NOUT); 70 }; 71 72 /** 73 * idio_16_get_direction - get the I/O direction for a signal offset 74 * @offset: offset of signal to get direction 75 * 76 * Returns the signal direction (0=output, 1=input) for the signal at @offset. 77 */ 78 static inline int idio_16_get_direction(const unsigned long offset) 79 { 80 return (offset >= IDIO_16_NOUT) ? 1 : 0; 81 } 82 83 int idio_16_get(struct idio_16 __iomem *reg, struct idio_16_state *state, 84 unsigned long offset); 85 void idio_16_get_multiple(struct idio_16 __iomem *reg, 86 struct idio_16_state *state, 87 const unsigned long *mask, unsigned long *bits); 88 void idio_16_set(struct idio_16 __iomem *reg, struct idio_16_state *state, 89 unsigned long offset, unsigned long value); 90 void idio_16_set_multiple(struct idio_16 __iomem *reg, 91 struct idio_16_state *state, 92 const unsigned long *mask, const unsigned long *bits); 93 void idio_16_state_init(struct idio_16_state *state); 94 95 int devm_idio_16_regmap_register(struct device *dev, const struct idio_16_regmap_config *config); 96 97 #endif /* _IDIO_16_H_ */ 98