diff options
author | Julia Cartwright <julia@ni.com> | 2017-03-21 18:43:04 -0400 |
---|---|---|
committer | Lee Jones <lee.jones@linaro.org> | 2017-04-27 04:25:05 -0400 |
commit | 93ad4471912029f7519c23da56538a5d54552124 (patch) | |
tree | 223275410925aac3cb19f4fedb8c94127a3afc58 | |
parent | 0c227c51b98c03c6e7fb4f342f930cf576292064 (diff) |
mfd: asic3: Make use of raw_spinlock variants
The asic3 mfd driver currently implements an irq_chip for handling
interrupts; due to how irq_chip handling is done, it's necessary for the
irq_chip methods to be invoked from hardirq context, even on a a
real-time kernel. Because the spinlock_t type becomes a "sleeping"
spinlock w/ RT kernels, it is not suitable to be used with irq_chips.
A quick audit of the operations under the lock reveal that they do only
minimal, bounded work, and are therefore safe to do under a raw spinlock.
Signed-off-by: Julia Cartwright <julia@ni.com>
Signed-off-by: Lee Jones <lee.jones@linaro.org>
-rw-r--r-- | drivers/mfd/asic3.c | 56 |
1 files changed, 28 insertions, 28 deletions
diff --git a/drivers/mfd/asic3.c b/drivers/mfd/asic3.c index 0413c8159551..cf2e25ab2940 100644 --- a/drivers/mfd/asic3.c +++ b/drivers/mfd/asic3.c | |||
@@ -78,7 +78,7 @@ struct asic3 { | |||
78 | unsigned int bus_shift; | 78 | unsigned int bus_shift; |
79 | unsigned int irq_nr; | 79 | unsigned int irq_nr; |
80 | unsigned int irq_base; | 80 | unsigned int irq_base; |
81 | spinlock_t lock; | 81 | raw_spinlock_t lock; |
82 | u16 irq_bothedge[4]; | 82 | u16 irq_bothedge[4]; |
83 | struct gpio_chip gpio; | 83 | struct gpio_chip gpio; |
84 | struct device *dev; | 84 | struct device *dev; |
@@ -108,14 +108,14 @@ static void asic3_set_register(struct asic3 *asic, u32 reg, u32 bits, bool set) | |||
108 | unsigned long flags; | 108 | unsigned long flags; |
109 | u32 val; | 109 | u32 val; |
110 | 110 | ||
111 | spin_lock_irqsave(&asic->lock, flags); | 111 | raw_spin_lock_irqsave(&asic->lock, flags); |
112 | val = asic3_read_register(asic, reg); | 112 | val = asic3_read_register(asic, reg); |
113 | if (set) | 113 | if (set) |
114 | val |= bits; | 114 | val |= bits; |
115 | else | 115 | else |
116 | val &= ~bits; | 116 | val &= ~bits; |
117 | asic3_write_register(asic, reg, val); | 117 | asic3_write_register(asic, reg, val); |
118 | spin_unlock_irqrestore(&asic->lock, flags); | 118 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
119 | } | 119 | } |
120 | 120 | ||
121 | /* IRQs */ | 121 | /* IRQs */ |
@@ -129,13 +129,13 @@ static void asic3_irq_flip_edge(struct asic3 *asic, | |||
129 | u16 edge; | 129 | u16 edge; |
130 | unsigned long flags; | 130 | unsigned long flags; |
131 | 131 | ||
132 | spin_lock_irqsave(&asic->lock, flags); | 132 | raw_spin_lock_irqsave(&asic->lock, flags); |
133 | edge = asic3_read_register(asic, | 133 | edge = asic3_read_register(asic, |
134 | base + ASIC3_GPIO_EDGE_TRIGGER); | 134 | base + ASIC3_GPIO_EDGE_TRIGGER); |
135 | edge ^= bit; | 135 | edge ^= bit; |
136 | asic3_write_register(asic, | 136 | asic3_write_register(asic, |
137 | base + ASIC3_GPIO_EDGE_TRIGGER, edge); | 137 | base + ASIC3_GPIO_EDGE_TRIGGER, edge); |
138 | spin_unlock_irqrestore(&asic->lock, flags); | 138 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
139 | } | 139 | } |
140 | 140 | ||
141 | static void asic3_irq_demux(struct irq_desc *desc) | 141 | static void asic3_irq_demux(struct irq_desc *desc) |
@@ -151,10 +151,10 @@ static void asic3_irq_demux(struct irq_desc *desc) | |||
151 | u32 status; | 151 | u32 status; |
152 | int bank; | 152 | int bank; |
153 | 153 | ||
154 | spin_lock_irqsave(&asic->lock, flags); | 154 | raw_spin_lock_irqsave(&asic->lock, flags); |
155 | status = asic3_read_register(asic, | 155 | status = asic3_read_register(asic, |
156 | ASIC3_OFFSET(INTR, P_INT_STAT)); | 156 | ASIC3_OFFSET(INTR, P_INT_STAT)); |
157 | spin_unlock_irqrestore(&asic->lock, flags); | 157 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
158 | 158 | ||
159 | /* Check all ten register bits */ | 159 | /* Check all ten register bits */ |
160 | if ((status & 0x3ff) == 0) | 160 | if ((status & 0x3ff) == 0) |
@@ -167,7 +167,7 @@ static void asic3_irq_demux(struct irq_desc *desc) | |||
167 | 167 | ||
168 | base = ASIC3_GPIO_A_BASE | 168 | base = ASIC3_GPIO_A_BASE |
169 | + bank * ASIC3_GPIO_BASE_INCR; | 169 | + bank * ASIC3_GPIO_BASE_INCR; |
170 | spin_lock_irqsave(&asic->lock, flags); | 170 | raw_spin_lock_irqsave(&asic->lock, flags); |
171 | istat = asic3_read_register(asic, | 171 | istat = asic3_read_register(asic, |
172 | base + | 172 | base + |
173 | ASIC3_GPIO_INT_STATUS); | 173 | ASIC3_GPIO_INT_STATUS); |
@@ -175,7 +175,7 @@ static void asic3_irq_demux(struct irq_desc *desc) | |||
175 | asic3_write_register(asic, | 175 | asic3_write_register(asic, |
176 | base + | 176 | base + |
177 | ASIC3_GPIO_INT_STATUS, 0); | 177 | ASIC3_GPIO_INT_STATUS, 0); |
178 | spin_unlock_irqrestore(&asic->lock, flags); | 178 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
179 | 179 | ||
180 | for (i = 0; i < ASIC3_GPIOS_PER_BANK; i++) { | 180 | for (i = 0; i < ASIC3_GPIOS_PER_BANK; i++) { |
181 | int bit = (1 << i); | 181 | int bit = (1 << i); |
@@ -230,11 +230,11 @@ static void asic3_mask_gpio_irq(struct irq_data *data) | |||
230 | bank = asic3_irq_to_bank(asic, data->irq); | 230 | bank = asic3_irq_to_bank(asic, data->irq); |
231 | index = asic3_irq_to_index(asic, data->irq); | 231 | index = asic3_irq_to_index(asic, data->irq); |
232 | 232 | ||
233 | spin_lock_irqsave(&asic->lock, flags); | 233 | raw_spin_lock_irqsave(&asic->lock, flags); |
234 | val = asic3_read_register(asic, bank + ASIC3_GPIO_MASK); | 234 | val = asic3_read_register(asic, bank + ASIC3_GPIO_MASK); |
235 | val |= 1 << index; | 235 | val |= 1 << index; |
236 | asic3_write_register(asic, bank + ASIC3_GPIO_MASK, val); | 236 | asic3_write_register(asic, bank + ASIC3_GPIO_MASK, val); |
237 | spin_unlock_irqrestore(&asic->lock, flags); | 237 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
238 | } | 238 | } |
239 | 239 | ||
240 | static void asic3_mask_irq(struct irq_data *data) | 240 | static void asic3_mask_irq(struct irq_data *data) |
@@ -243,7 +243,7 @@ static void asic3_mask_irq(struct irq_data *data) | |||
243 | int regval; | 243 | int regval; |
244 | unsigned long flags; | 244 | unsigned long flags; |
245 | 245 | ||
246 | spin_lock_irqsave(&asic->lock, flags); | 246 | raw_spin_lock_irqsave(&asic->lock, flags); |
247 | regval = asic3_read_register(asic, | 247 | regval = asic3_read_register(asic, |
248 | ASIC3_INTR_BASE + | 248 | ASIC3_INTR_BASE + |
249 | ASIC3_INTR_INT_MASK); | 249 | ASIC3_INTR_INT_MASK); |
@@ -255,7 +255,7 @@ static void asic3_mask_irq(struct irq_data *data) | |||
255 | ASIC3_INTR_BASE + | 255 | ASIC3_INTR_BASE + |
256 | ASIC3_INTR_INT_MASK, | 256 | ASIC3_INTR_INT_MASK, |
257 | regval); | 257 | regval); |
258 | spin_unlock_irqrestore(&asic->lock, flags); | 258 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
259 | } | 259 | } |
260 | 260 | ||
261 | static void asic3_unmask_gpio_irq(struct irq_data *data) | 261 | static void asic3_unmask_gpio_irq(struct irq_data *data) |
@@ -267,11 +267,11 @@ static void asic3_unmask_gpio_irq(struct irq_data *data) | |||
267 | bank = asic3_irq_to_bank(asic, data->irq); | 267 | bank = asic3_irq_to_bank(asic, data->irq); |
268 | index = asic3_irq_to_index(asic, data->irq); | 268 | index = asic3_irq_to_index(asic, data->irq); |
269 | 269 | ||
270 | spin_lock_irqsave(&asic->lock, flags); | 270 | raw_spin_lock_irqsave(&asic->lock, flags); |
271 | val = asic3_read_register(asic, bank + ASIC3_GPIO_MASK); | 271 | val = asic3_read_register(asic, bank + ASIC3_GPIO_MASK); |
272 | val &= ~(1 << index); | 272 | val &= ~(1 << index); |
273 | asic3_write_register(asic, bank + ASIC3_GPIO_MASK, val); | 273 | asic3_write_register(asic, bank + ASIC3_GPIO_MASK, val); |
274 | spin_unlock_irqrestore(&asic->lock, flags); | 274 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
275 | } | 275 | } |
276 | 276 | ||
277 | static void asic3_unmask_irq(struct irq_data *data) | 277 | static void asic3_unmask_irq(struct irq_data *data) |
@@ -280,7 +280,7 @@ static void asic3_unmask_irq(struct irq_data *data) | |||
280 | int regval; | 280 | int regval; |
281 | unsigned long flags; | 281 | unsigned long flags; |
282 | 282 | ||
283 | spin_lock_irqsave(&asic->lock, flags); | 283 | raw_spin_lock_irqsave(&asic->lock, flags); |
284 | regval = asic3_read_register(asic, | 284 | regval = asic3_read_register(asic, |
285 | ASIC3_INTR_BASE + | 285 | ASIC3_INTR_BASE + |
286 | ASIC3_INTR_INT_MASK); | 286 | ASIC3_INTR_INT_MASK); |
@@ -292,7 +292,7 @@ static void asic3_unmask_irq(struct irq_data *data) | |||
292 | ASIC3_INTR_BASE + | 292 | ASIC3_INTR_BASE + |
293 | ASIC3_INTR_INT_MASK, | 293 | ASIC3_INTR_INT_MASK, |
294 | regval); | 294 | regval); |
295 | spin_unlock_irqrestore(&asic->lock, flags); | 295 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
296 | } | 296 | } |
297 | 297 | ||
298 | static int asic3_gpio_irq_type(struct irq_data *data, unsigned int type) | 298 | static int asic3_gpio_irq_type(struct irq_data *data, unsigned int type) |
@@ -306,7 +306,7 @@ static int asic3_gpio_irq_type(struct irq_data *data, unsigned int type) | |||
306 | index = asic3_irq_to_index(asic, data->irq); | 306 | index = asic3_irq_to_index(asic, data->irq); |
307 | bit = 1<<index; | 307 | bit = 1<<index; |
308 | 308 | ||
309 | spin_lock_irqsave(&asic->lock, flags); | 309 | raw_spin_lock_irqsave(&asic->lock, flags); |
310 | level = asic3_read_register(asic, | 310 | level = asic3_read_register(asic, |
311 | bank + ASIC3_GPIO_LEVEL_TRIGGER); | 311 | bank + ASIC3_GPIO_LEVEL_TRIGGER); |
312 | edge = asic3_read_register(asic, | 312 | edge = asic3_read_register(asic, |
@@ -348,7 +348,7 @@ static int asic3_gpio_irq_type(struct irq_data *data, unsigned int type) | |||
348 | edge); | 348 | edge); |
349 | asic3_write_register(asic, bank + ASIC3_GPIO_TRIGGER_TYPE, | 349 | asic3_write_register(asic, bank + ASIC3_GPIO_TRIGGER_TYPE, |
350 | trigger); | 350 | trigger); |
351 | spin_unlock_irqrestore(&asic->lock, flags); | 351 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
352 | return 0; | 352 | return 0; |
353 | } | 353 | } |
354 | 354 | ||
@@ -455,7 +455,7 @@ static int asic3_gpio_direction(struct gpio_chip *chip, | |||
455 | return -EINVAL; | 455 | return -EINVAL; |
456 | } | 456 | } |
457 | 457 | ||
458 | spin_lock_irqsave(&asic->lock, flags); | 458 | raw_spin_lock_irqsave(&asic->lock, flags); |
459 | 459 | ||
460 | out_reg = asic3_read_register(asic, gpio_base + ASIC3_GPIO_DIRECTION); | 460 | out_reg = asic3_read_register(asic, gpio_base + ASIC3_GPIO_DIRECTION); |
461 | 461 | ||
@@ -467,7 +467,7 @@ static int asic3_gpio_direction(struct gpio_chip *chip, | |||
467 | 467 | ||
468 | asic3_write_register(asic, gpio_base + ASIC3_GPIO_DIRECTION, out_reg); | 468 | asic3_write_register(asic, gpio_base + ASIC3_GPIO_DIRECTION, out_reg); |
469 | 469 | ||
470 | spin_unlock_irqrestore(&asic->lock, flags); | 470 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
471 | 471 | ||
472 | return 0; | 472 | return 0; |
473 | 473 | ||
@@ -524,7 +524,7 @@ static void asic3_gpio_set(struct gpio_chip *chip, | |||
524 | 524 | ||
525 | mask = ASIC3_GPIO_TO_MASK(offset); | 525 | mask = ASIC3_GPIO_TO_MASK(offset); |
526 | 526 | ||
527 | spin_lock_irqsave(&asic->lock, flags); | 527 | raw_spin_lock_irqsave(&asic->lock, flags); |
528 | 528 | ||
529 | out_reg = asic3_read_register(asic, gpio_base + ASIC3_GPIO_OUT); | 529 | out_reg = asic3_read_register(asic, gpio_base + ASIC3_GPIO_OUT); |
530 | 530 | ||
@@ -535,7 +535,7 @@ static void asic3_gpio_set(struct gpio_chip *chip, | |||
535 | 535 | ||
536 | asic3_write_register(asic, gpio_base + ASIC3_GPIO_OUT, out_reg); | 536 | asic3_write_register(asic, gpio_base + ASIC3_GPIO_OUT, out_reg); |
537 | 537 | ||
538 | spin_unlock_irqrestore(&asic->lock, flags); | 538 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
539 | } | 539 | } |
540 | 540 | ||
541 | static int asic3_gpio_to_irq(struct gpio_chip *chip, unsigned offset) | 541 | static int asic3_gpio_to_irq(struct gpio_chip *chip, unsigned offset) |
@@ -611,13 +611,13 @@ static void asic3_clk_enable(struct asic3 *asic, struct asic3_clk *clk) | |||
611 | unsigned long flags; | 611 | unsigned long flags; |
612 | u32 cdex; | 612 | u32 cdex; |
613 | 613 | ||
614 | spin_lock_irqsave(&asic->lock, flags); | 614 | raw_spin_lock_irqsave(&asic->lock, flags); |
615 | if (clk->enabled++ == 0) { | 615 | if (clk->enabled++ == 0) { |
616 | cdex = asic3_read_register(asic, ASIC3_OFFSET(CLOCK, CDEX)); | 616 | cdex = asic3_read_register(asic, ASIC3_OFFSET(CLOCK, CDEX)); |
617 | cdex |= clk->cdex; | 617 | cdex |= clk->cdex; |
618 | asic3_write_register(asic, ASIC3_OFFSET(CLOCK, CDEX), cdex); | 618 | asic3_write_register(asic, ASIC3_OFFSET(CLOCK, CDEX), cdex); |
619 | } | 619 | } |
620 | spin_unlock_irqrestore(&asic->lock, flags); | 620 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
621 | } | 621 | } |
622 | 622 | ||
623 | static void asic3_clk_disable(struct asic3 *asic, struct asic3_clk *clk) | 623 | static void asic3_clk_disable(struct asic3 *asic, struct asic3_clk *clk) |
@@ -627,13 +627,13 @@ static void asic3_clk_disable(struct asic3 *asic, struct asic3_clk *clk) | |||
627 | 627 | ||
628 | WARN_ON(clk->enabled == 0); | 628 | WARN_ON(clk->enabled == 0); |
629 | 629 | ||
630 | spin_lock_irqsave(&asic->lock, flags); | 630 | raw_spin_lock_irqsave(&asic->lock, flags); |
631 | if (--clk->enabled == 0) { | 631 | if (--clk->enabled == 0) { |
632 | cdex = asic3_read_register(asic, ASIC3_OFFSET(CLOCK, CDEX)); | 632 | cdex = asic3_read_register(asic, ASIC3_OFFSET(CLOCK, CDEX)); |
633 | cdex &= ~clk->cdex; | 633 | cdex &= ~clk->cdex; |
634 | asic3_write_register(asic, ASIC3_OFFSET(CLOCK, CDEX), cdex); | 634 | asic3_write_register(asic, ASIC3_OFFSET(CLOCK, CDEX), cdex); |
635 | } | 635 | } |
636 | spin_unlock_irqrestore(&asic->lock, flags); | 636 | raw_spin_unlock_irqrestore(&asic->lock, flags); |
637 | } | 637 | } |
638 | 638 | ||
639 | /* MFD cells (SPI, PWM, LED, DS1WM, MMC) */ | 639 | /* MFD cells (SPI, PWM, LED, DS1WM, MMC) */ |
@@ -963,7 +963,7 @@ static int __init asic3_probe(struct platform_device *pdev) | |||
963 | if (!asic) | 963 | if (!asic) |
964 | return -ENOMEM; | 964 | return -ENOMEM; |
965 | 965 | ||
966 | spin_lock_init(&asic->lock); | 966 | raw_spin_lock_init(&asic->lock); |
967 | platform_set_drvdata(pdev, asic); | 967 | platform_set_drvdata(pdev, asic); |
968 | asic->dev = &pdev->dev; | 968 | asic->dev = &pdev->dev; |
969 | 969 | ||