File Index
Files and directories
Sign in
FILE

gpio-sa1100.c

File preview with syntax highlighting.

linux-6.19.14/drivers/gpio/gpio-sa1100.c C
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * linux/arch/arm/mach-sa1100/gpio.c
  4 *
  5 * Generic SA-1100 GPIO handling
  6 */
  7#include <linux/gpio/driver.h>
  8#include <linux/init.h>
  9#include <linux/module.h>
 10#include <linux/io.h>
 11#include <linux/syscore_ops.h>
 12#include <soc/sa1100/pwer.h>
 13#include <mach/hardware.h>
 14#include <mach/irqs.h>
 15#include <mach/generic.h>
 16
 17struct sa1100_gpio_chip {
 18	struct gpio_chip chip;
 19	void __iomem *membase;
 20	int irqbase;
 21	u32 irqmask;
 22	u32 irqrising;
 23	u32 irqfalling;
 24	u32 irqwake;
 25};
 26
 27#define sa1100_gpio_chip(x) container_of(x, struct sa1100_gpio_chip, chip)
 28
 29enum {
 30	R_GPLR = 0x00,
 31	R_GPDR = 0x04,
 32	R_GPSR = 0x08,
 33	R_GPCR = 0x0c,
 34	R_GRER = 0x10,
 35	R_GFER = 0x14,
 36	R_GEDR = 0x18,
 37	R_GAFR = 0x1c,
 38};
 39
 40static int sa1100_gpio_get(struct gpio_chip *chip, unsigned offset)
 41{
 42	return readl_relaxed(sa1100_gpio_chip(chip)->membase + R_GPLR) &
 43		BIT(offset);
 44}
 45
 46static int sa1100_gpio_set(struct gpio_chip *chip, unsigned int offset,
 47			   int value)
 48{
 49	int reg = value ? R_GPSR : R_GPCR;
 50
 51	writel_relaxed(BIT(offset), sa1100_gpio_chip(chip)->membase + reg);
 52
 53	return 0;
 54}
 55
 56static int sa1100_get_direction(struct gpio_chip *chip, unsigned offset)
 57{
 58	void __iomem *gpdr = sa1100_gpio_chip(chip)->membase + R_GPDR;
 59
 60	if (readl_relaxed(gpdr) & BIT(offset))
 61		return GPIO_LINE_DIRECTION_OUT;
 62
 63	return GPIO_LINE_DIRECTION_IN;
 64}
 65
 66static int sa1100_direction_input(struct gpio_chip *chip, unsigned offset)
 67{
 68	void __iomem *gpdr = sa1100_gpio_chip(chip)->membase + R_GPDR;
 69	unsigned long flags;
 70
 71	local_irq_save(flags);
 72	writel_relaxed(readl_relaxed(gpdr) & ~BIT(offset), gpdr);
 73	local_irq_restore(flags);
 74
 75	return 0;
 76}
 77
 78static int sa1100_direction_output(struct gpio_chip *chip, unsigned offset, int value)
 79{
 80	void __iomem *gpdr = sa1100_gpio_chip(chip)->membase + R_GPDR;
 81	unsigned long flags;
 82
 83	local_irq_save(flags);
 84	sa1100_gpio_set(chip, offset, value);
 85	writel_relaxed(readl_relaxed(gpdr) | BIT(offset), gpdr);
 86	local_irq_restore(flags);
 87
 88	return 0;
 89}
 90
 91static int sa1100_to_irq(struct gpio_chip *chip, unsigned offset)
 92{
 93	return sa1100_gpio_chip(chip)->irqbase + offset;
 94}
 95
 96static struct sa1100_gpio_chip sa1100_gpio_chip = {
 97	.chip = {
 98		.label			= "gpio",
 99		.get_direction		= sa1100_get_direction,
100		.direction_input	= sa1100_direction_input,
101		.direction_output	= sa1100_direction_output,
102		.set			= sa1100_gpio_set,
103		.get			= sa1100_gpio_get,
104		.to_irq			= sa1100_to_irq,
105		.base			= 0,
106		.ngpio			= GPIO_MAX + 1,
107	},
108	.membase = (void *)&GPLR,
109	.irqbase = IRQ_GPIO0,
110};
111
112/*
113 * SA1100 GPIO edge detection for IRQs:
114 * IRQs are generated on Falling-Edge, Rising-Edge, or both.
115 * Use this instead of directly setting GRER/GFER.
116 */
117static void sa1100_update_edge_regs(struct sa1100_gpio_chip *sgc)
118{
119	void *base = sgc->membase;
120	u32 grer, gfer;
121
122	grer = sgc->irqrising & sgc->irqmask;
123	gfer = sgc->irqfalling & sgc->irqmask;
124
125	writel_relaxed(grer, base + R_GRER);
126	writel_relaxed(gfer, base + R_GFER);
127}
128
129static int sa1100_gpio_type(struct irq_data *d, unsigned int type)
130{
131	struct sa1100_gpio_chip *sgc = irq_data_get_irq_chip_data(d);
132	unsigned int mask = BIT(d->hwirq);
133
134	if (type == IRQ_TYPE_PROBE) {
135		if ((sgc->irqrising | sgc->irqfalling) & mask)
136			return 0;
137		type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING;
138	}
139
140	if (type & IRQ_TYPE_EDGE_RISING)
141		sgc->irqrising |= mask;
142	else
143		sgc->irqrising &= ~mask;
144	if (type & IRQ_TYPE_EDGE_FALLING)
145		sgc->irqfalling |= mask;
146	else
147		sgc->irqfalling &= ~mask;
148
149	sa1100_update_edge_regs(sgc);
150
151	return 0;
152}
153
154/*
155 * GPIO IRQs must be acknowledged.
156 */
157static void sa1100_gpio_ack(struct irq_data *d)
158{
159	struct sa1100_gpio_chip *sgc = irq_data_get_irq_chip_data(d);
160
161	writel_relaxed(BIT(d->hwirq), sgc->membase + R_GEDR);
162}
163
164static void sa1100_gpio_mask(struct irq_data *d)
165{
166	struct sa1100_gpio_chip *sgc = irq_data_get_irq_chip_data(d);
167	unsigned int mask = BIT(d->hwirq);
168
169	sgc->irqmask &= ~mask;
170
171	sa1100_update_edge_regs(sgc);
172}
173
174static void sa1100_gpio_unmask(struct irq_data *d)
175{
176	struct sa1100_gpio_chip *sgc = irq_data_get_irq_chip_data(d);
177	unsigned int mask = BIT(d->hwirq);
178
179	sgc->irqmask |= mask;
180
181	sa1100_update_edge_regs(sgc);
182}
183
184static int sa1100_gpio_wake(struct irq_data *d, unsigned int on)
185{
186	struct sa1100_gpio_chip *sgc = irq_data_get_irq_chip_data(d);
187	int ret = sa11x0_gpio_set_wake(d->hwirq, on);
188	if (!ret) {
189		if (on)
190			sgc->irqwake |= BIT(d->hwirq);
191		else
192			sgc->irqwake &= ~BIT(d->hwirq);
193	}
194	return ret;
195}
196
197/*
198 * This is for GPIO IRQs
199 */
200static struct irq_chip sa1100_gpio_irq_chip = {
201	.name		= "GPIO",
202	.irq_ack	= sa1100_gpio_ack,
203	.irq_mask	= sa1100_gpio_mask,
204	.irq_unmask	= sa1100_gpio_unmask,
205	.irq_set_type	= sa1100_gpio_type,
206	.irq_set_wake	= sa1100_gpio_wake,
207};
208
209static int sa1100_gpio_irqdomain_map(struct irq_domain *d,
210		unsigned int irq, irq_hw_number_t hwirq)
211{
212	struct sa1100_gpio_chip *sgc = d->host_data;
213
214	irq_set_chip_data(irq, sgc);
215	irq_set_chip_and_handler(irq, &sa1100_gpio_irq_chip, handle_edge_irq);
216	irq_set_probe(irq);
217
218	return 0;
219}
220
221static const struct irq_domain_ops sa1100_gpio_irqdomain_ops = {
222	.map = sa1100_gpio_irqdomain_map,
223	.xlate = irq_domain_xlate_onetwocell,
224};
225
226static struct irq_domain *sa1100_gpio_irqdomain;
227
228/*
229 * IRQ 0-11 (GPIO) handler.  We enter here with the
230 * irq_controller_lock held, and IRQs disabled.  Decode the IRQ
231 * and call the handler.
232 */
233static void sa1100_gpio_handler(struct irq_desc *desc)
234{
235	struct sa1100_gpio_chip *sgc = irq_desc_get_handler_data(desc);
236	unsigned int irq, mask;
237	void __iomem *gedr = sgc->membase + R_GEDR;
238
239	mask = readl_relaxed(gedr);
240	do {
241		/*
242		 * clear down all currently active IRQ sources.
243		 * We will be processing them all.
244		 */
245		writel_relaxed(mask, gedr);
246
247		irq = sgc->irqbase;
248		do {
249			if (mask & 1)
250				generic_handle_irq(irq);
251			mask >>= 1;
252			irq++;
253		} while (mask);
254
255		mask = readl_relaxed(gedr);
256	} while (mask);
257}
258
259static int sa1100_gpio_suspend(void *data)
260{
261	struct sa1100_gpio_chip *sgc = &sa1100_gpio_chip;
262
263	/*
264	 * Set the appropriate edges for wakeup.
265	 */
266	writel_relaxed(sgc->irqwake & sgc->irqrising, sgc->membase + R_GRER);
267	writel_relaxed(sgc->irqwake & sgc->irqfalling, sgc->membase + R_GFER);
268
269	/*
270	 * Clear any pending GPIO interrupts.
271	 */
272	writel_relaxed(readl_relaxed(sgc->membase + R_GEDR),
273		       sgc->membase + R_GEDR);
274
275	return 0;
276}
277
278static void sa1100_gpio_resume(void *data)
279{
280	sa1100_update_edge_regs(&sa1100_gpio_chip);
281}
282
283static const struct syscore_ops sa1100_gpio_syscore_ops = {
284	.suspend	= sa1100_gpio_suspend,
285	.resume		= sa1100_gpio_resume,
286};
287
288static struct syscore sa1100_gpio_syscore = {
289	.ops = &sa1100_gpio_syscore_ops,
290};
291
292static int __init sa1100_gpio_init_devicefs(void)
293{
294	register_syscore(&sa1100_gpio_syscore);
295	return 0;
296}
297
298device_initcall(sa1100_gpio_init_devicefs);
299
300static const int sa1100_gpio_irqs[] __initconst = {
301	/* Install handlers for GPIO 0-10 edge detect interrupts */
302	IRQ_GPIO0_SC,
303	IRQ_GPIO1_SC,
304	IRQ_GPIO2_SC,
305	IRQ_GPIO3_SC,
306	IRQ_GPIO4_SC,
307	IRQ_GPIO5_SC,
308	IRQ_GPIO6_SC,
309	IRQ_GPIO7_SC,
310	IRQ_GPIO8_SC,
311	IRQ_GPIO9_SC,
312	IRQ_GPIO10_SC,
313	/* Install handler for GPIO 11-27 edge detect interrupts */
314	IRQ_GPIO11_27,
315};
316
317void __init sa1100_init_gpio(void)
318{
319	struct sa1100_gpio_chip *sgc = &sa1100_gpio_chip;
320	int i;
321
322	/* clear all GPIO edge detects */
323	writel_relaxed(0, sgc->membase + R_GFER);
324	writel_relaxed(0, sgc->membase + R_GRER);
325	writel_relaxed(-1, sgc->membase + R_GEDR);
326
327	gpiochip_add_data(&sa1100_gpio_chip.chip, NULL);
328
329	sa1100_gpio_irqdomain = irq_domain_create_simple(NULL,
330			28, IRQ_GPIO0,
331			&sa1100_gpio_irqdomain_ops, sgc);
332
333	for (i = 0; i < ARRAY_SIZE(sa1100_gpio_irqs); i++)
334		irq_set_chained_handler_and_data(sa1100_gpio_irqs[i],
335						 sa1100_gpio_handler, sgc);
336}
~/ Read-only file preview.