Linux Audio

Check our new training course

Loading...
v6.8
  1// SPDX-License-Identifier: GPL-2.0-or-later
  2/*
  3 * arch/powerpc/sysdev/ipic.c
  4 *
  5 * IPIC routines implementations.
  6 *
  7 * Copyright 2005 Freescale Semiconductor, Inc.
 
 
 
 
 
  8 */
  9#include <linux/kernel.h>
 10#include <linux/init.h>
 11#include <linux/errno.h>
 12#include <linux/reboot.h>
 13#include <linux/slab.h>
 14#include <linux/stddef.h>
 15#include <linux/sched.h>
 16#include <linux/signal.h>
 17#include <linux/syscore_ops.h>
 18#include <linux/device.h>
 19#include <linux/spinlock.h>
 20#include <linux/fsl_devices.h>
 21#include <linux/irqdomain.h>
 22#include <linux/of_address.h>
 23#include <asm/irq.h>
 24#include <asm/io.h>
 
 25#include <asm/ipic.h>
 26
 27#include "ipic.h"
 28
 29static struct ipic * primary_ipic;
 30static struct irq_chip ipic_level_irq_chip, ipic_edge_irq_chip;
 31static DEFINE_RAW_SPINLOCK(ipic_lock);
 32
 33static struct ipic_info ipic_info[] = {
 34	[1] = {
 35		.mask	= IPIC_SIMSR_H,
 36		.prio	= IPIC_SIPRR_C,
 37		.force	= IPIC_SIFCR_H,
 38		.bit	= 16,
 39		.prio_mask = 0,
 40	},
 41	[2] = {
 42		.mask	= IPIC_SIMSR_H,
 43		.prio	= IPIC_SIPRR_C,
 44		.force	= IPIC_SIFCR_H,
 45		.bit	= 17,
 46		.prio_mask = 1,
 47	},
 48	[3] = {
 49		.mask	= IPIC_SIMSR_H,
 50		.prio	= IPIC_SIPRR_C,
 51		.force	= IPIC_SIFCR_H,
 52		.bit	= 18,
 53		.prio_mask = 2,
 54	},
 55	[4] = {
 56		.mask	= IPIC_SIMSR_H,
 57		.prio	= IPIC_SIPRR_C,
 58		.force	= IPIC_SIFCR_H,
 59		.bit	= 19,
 60		.prio_mask = 3,
 61	},
 62	[5] = {
 63		.mask	= IPIC_SIMSR_H,
 64		.prio	= IPIC_SIPRR_C,
 65		.force	= IPIC_SIFCR_H,
 66		.bit	= 20,
 67		.prio_mask = 4,
 68	},
 69	[6] = {
 70		.mask	= IPIC_SIMSR_H,
 71		.prio	= IPIC_SIPRR_C,
 72		.force	= IPIC_SIFCR_H,
 73		.bit	= 21,
 74		.prio_mask = 5,
 75	},
 76	[7] = {
 77		.mask	= IPIC_SIMSR_H,
 78		.prio	= IPIC_SIPRR_C,
 79		.force	= IPIC_SIFCR_H,
 80		.bit	= 22,
 81		.prio_mask = 6,
 82	},
 83	[8] = {
 84		.mask	= IPIC_SIMSR_H,
 85		.prio	= IPIC_SIPRR_C,
 86		.force	= IPIC_SIFCR_H,
 87		.bit	= 23,
 88		.prio_mask = 7,
 89	},
 90	[9] = {
 91		.mask	= IPIC_SIMSR_H,
 92		.prio	= IPIC_SIPRR_D,
 93		.force	= IPIC_SIFCR_H,
 94		.bit	= 24,
 95		.prio_mask = 0,
 96	},
 97	[10] = {
 98		.mask	= IPIC_SIMSR_H,
 99		.prio	= IPIC_SIPRR_D,
100		.force	= IPIC_SIFCR_H,
101		.bit	= 25,
102		.prio_mask = 1,
103	},
104	[11] = {
105		.mask	= IPIC_SIMSR_H,
106		.prio	= IPIC_SIPRR_D,
107		.force	= IPIC_SIFCR_H,
108		.bit	= 26,
109		.prio_mask = 2,
110	},
111	[12] = {
112		.mask	= IPIC_SIMSR_H,
113		.prio	= IPIC_SIPRR_D,
114		.force	= IPIC_SIFCR_H,
115		.bit	= 27,
116		.prio_mask = 3,
117	},
118	[13] = {
119		.mask	= IPIC_SIMSR_H,
120		.prio	= IPIC_SIPRR_D,
121		.force	= IPIC_SIFCR_H,
122		.bit	= 28,
123		.prio_mask = 4,
124	},
125	[14] = {
126		.mask	= IPIC_SIMSR_H,
127		.prio	= IPIC_SIPRR_D,
128		.force	= IPIC_SIFCR_H,
129		.bit	= 29,
130		.prio_mask = 5,
131	},
132	[15] = {
133		.mask	= IPIC_SIMSR_H,
134		.prio	= IPIC_SIPRR_D,
135		.force	= IPIC_SIFCR_H,
136		.bit	= 30,
137		.prio_mask = 6,
138	},
139	[16] = {
140		.mask	= IPIC_SIMSR_H,
141		.prio	= IPIC_SIPRR_D,
142		.force	= IPIC_SIFCR_H,
143		.bit	= 31,
144		.prio_mask = 7,
145	},
146	[17] = {
147		.ack	= IPIC_SEPNR,
148		.mask	= IPIC_SEMSR,
149		.prio	= IPIC_SMPRR_A,
150		.force	= IPIC_SEFCR,
151		.bit	= 1,
152		.prio_mask = 5,
153	},
154	[18] = {
155		.ack	= IPIC_SEPNR,
156		.mask	= IPIC_SEMSR,
157		.prio	= IPIC_SMPRR_A,
158		.force	= IPIC_SEFCR,
159		.bit	= 2,
160		.prio_mask = 6,
161	},
162	[19] = {
163		.ack	= IPIC_SEPNR,
164		.mask	= IPIC_SEMSR,
165		.prio	= IPIC_SMPRR_A,
166		.force	= IPIC_SEFCR,
167		.bit	= 3,
168		.prio_mask = 7,
169	},
170	[20] = {
171		.ack	= IPIC_SEPNR,
172		.mask	= IPIC_SEMSR,
173		.prio	= IPIC_SMPRR_B,
174		.force	= IPIC_SEFCR,
175		.bit	= 4,
176		.prio_mask = 4,
177	},
178	[21] = {
179		.ack	= IPIC_SEPNR,
180		.mask	= IPIC_SEMSR,
181		.prio	= IPIC_SMPRR_B,
182		.force	= IPIC_SEFCR,
183		.bit	= 5,
184		.prio_mask = 5,
185	},
186	[22] = {
187		.ack	= IPIC_SEPNR,
188		.mask	= IPIC_SEMSR,
189		.prio	= IPIC_SMPRR_B,
190		.force	= IPIC_SEFCR,
191		.bit	= 6,
192		.prio_mask = 6,
193	},
194	[23] = {
195		.ack	= IPIC_SEPNR,
196		.mask	= IPIC_SEMSR,
197		.prio	= IPIC_SMPRR_B,
198		.force	= IPIC_SEFCR,
199		.bit	= 7,
200		.prio_mask = 7,
201	},
202	[32] = {
203		.mask	= IPIC_SIMSR_H,
204		.prio	= IPIC_SIPRR_A,
205		.force	= IPIC_SIFCR_H,
206		.bit	= 0,
207		.prio_mask = 0,
208	},
209	[33] = {
210		.mask	= IPIC_SIMSR_H,
211		.prio	= IPIC_SIPRR_A,
212		.force	= IPIC_SIFCR_H,
213		.bit	= 1,
214		.prio_mask = 1,
215	},
216	[34] = {
217		.mask	= IPIC_SIMSR_H,
218		.prio	= IPIC_SIPRR_A,
219		.force	= IPIC_SIFCR_H,
220		.bit	= 2,
221		.prio_mask = 2,
222	},
223	[35] = {
224		.mask	= IPIC_SIMSR_H,
225		.prio	= IPIC_SIPRR_A,
226		.force	= IPIC_SIFCR_H,
227		.bit	= 3,
228		.prio_mask = 3,
229	},
230	[36] = {
231		.mask	= IPIC_SIMSR_H,
232		.prio	= IPIC_SIPRR_A,
233		.force	= IPIC_SIFCR_H,
234		.bit	= 4,
235		.prio_mask = 4,
236	},
237	[37] = {
238		.mask	= IPIC_SIMSR_H,
239		.prio	= IPIC_SIPRR_A,
240		.force	= IPIC_SIFCR_H,
241		.bit	= 5,
242		.prio_mask = 5,
243	},
244	[38] = {
245		.mask	= IPIC_SIMSR_H,
246		.prio	= IPIC_SIPRR_A,
247		.force	= IPIC_SIFCR_H,
248		.bit	= 6,
249		.prio_mask = 6,
250	},
251	[39] = {
252		.mask	= IPIC_SIMSR_H,
253		.prio	= IPIC_SIPRR_A,
254		.force	= IPIC_SIFCR_H,
255		.bit	= 7,
256		.prio_mask = 7,
257	},
258	[40] = {
259		.mask	= IPIC_SIMSR_H,
260		.prio	= IPIC_SIPRR_B,
261		.force	= IPIC_SIFCR_H,
262		.bit	= 8,
263		.prio_mask = 0,
264	},
265	[41] = {
266		.mask	= IPIC_SIMSR_H,
267		.prio	= IPIC_SIPRR_B,
268		.force	= IPIC_SIFCR_H,
269		.bit	= 9,
270		.prio_mask = 1,
271	},
272	[42] = {
273		.mask	= IPIC_SIMSR_H,
274		.prio	= IPIC_SIPRR_B,
275		.force	= IPIC_SIFCR_H,
276		.bit	= 10,
277		.prio_mask = 2,
278	},
279	[43] = {
280		.mask	= IPIC_SIMSR_H,
281		.prio	= IPIC_SIPRR_B,
282		.force	= IPIC_SIFCR_H,
283		.bit	= 11,
284		.prio_mask = 3,
285	},
286	[44] = {
287		.mask	= IPIC_SIMSR_H,
288		.prio	= IPIC_SIPRR_B,
289		.force	= IPIC_SIFCR_H,
290		.bit	= 12,
291		.prio_mask = 4,
292	},
293	[45] = {
294		.mask	= IPIC_SIMSR_H,
295		.prio	= IPIC_SIPRR_B,
296		.force	= IPIC_SIFCR_H,
297		.bit	= 13,
298		.prio_mask = 5,
299	},
300	[46] = {
301		.mask	= IPIC_SIMSR_H,
302		.prio	= IPIC_SIPRR_B,
303		.force	= IPIC_SIFCR_H,
304		.bit	= 14,
305		.prio_mask = 6,
306	},
307	[47] = {
308		.mask	= IPIC_SIMSR_H,
309		.prio	= IPIC_SIPRR_B,
310		.force	= IPIC_SIFCR_H,
311		.bit	= 15,
312		.prio_mask = 7,
313	},
314	[48] = {
315		.ack	= IPIC_SEPNR,
316		.mask	= IPIC_SEMSR,
317		.prio	= IPIC_SMPRR_A,
318		.force	= IPIC_SEFCR,
319		.bit	= 0,
320		.prio_mask = 4,
321	},
322	[64] = {
323		.mask	= IPIC_SIMSR_L,
324		.prio	= IPIC_SMPRR_A,
325		.force	= IPIC_SIFCR_L,
326		.bit	= 0,
327		.prio_mask = 0,
328	},
329	[65] = {
330		.mask	= IPIC_SIMSR_L,
331		.prio	= IPIC_SMPRR_A,
332		.force	= IPIC_SIFCR_L,
333		.bit	= 1,
334		.prio_mask = 1,
335	},
336	[66] = {
337		.mask	= IPIC_SIMSR_L,
338		.prio	= IPIC_SMPRR_A,
339		.force	= IPIC_SIFCR_L,
340		.bit	= 2,
341		.prio_mask = 2,
342	},
343	[67] = {
344		.mask	= IPIC_SIMSR_L,
345		.prio	= IPIC_SMPRR_A,
346		.force	= IPIC_SIFCR_L,
347		.bit	= 3,
348		.prio_mask = 3,
349	},
350	[68] = {
351		.mask	= IPIC_SIMSR_L,
352		.prio	= IPIC_SMPRR_B,
353		.force	= IPIC_SIFCR_L,
354		.bit	= 4,
355		.prio_mask = 0,
356	},
357	[69] = {
358		.mask	= IPIC_SIMSR_L,
359		.prio	= IPIC_SMPRR_B,
360		.force	= IPIC_SIFCR_L,
361		.bit	= 5,
362		.prio_mask = 1,
363	},
364	[70] = {
365		.mask	= IPIC_SIMSR_L,
366		.prio	= IPIC_SMPRR_B,
367		.force	= IPIC_SIFCR_L,
368		.bit	= 6,
369		.prio_mask = 2,
370	},
371	[71] = {
372		.mask	= IPIC_SIMSR_L,
373		.prio	= IPIC_SMPRR_B,
374		.force	= IPIC_SIFCR_L,
375		.bit	= 7,
376		.prio_mask = 3,
377	},
378	[72] = {
379		.mask	= IPIC_SIMSR_L,
380		.prio	= 0,
381		.force	= IPIC_SIFCR_L,
382		.bit	= 8,
383	},
384	[73] = {
385		.mask	= IPIC_SIMSR_L,
386		.prio	= 0,
387		.force	= IPIC_SIFCR_L,
388		.bit	= 9,
389	},
390	[74] = {
391		.mask	= IPIC_SIMSR_L,
392		.prio	= 0,
393		.force	= IPIC_SIFCR_L,
394		.bit	= 10,
395	},
396	[75] = {
397		.mask	= IPIC_SIMSR_L,
398		.prio	= 0,
399		.force	= IPIC_SIFCR_L,
400		.bit	= 11,
401	},
402	[76] = {
403		.mask	= IPIC_SIMSR_L,
404		.prio	= 0,
405		.force	= IPIC_SIFCR_L,
406		.bit	= 12,
407	},
408	[77] = {
409		.mask	= IPIC_SIMSR_L,
410		.prio	= 0,
411		.force	= IPIC_SIFCR_L,
412		.bit	= 13,
413	},
414	[78] = {
415		.mask	= IPIC_SIMSR_L,
416		.prio	= 0,
417		.force	= IPIC_SIFCR_L,
418		.bit	= 14,
419	},
420	[79] = {
421		.mask	= IPIC_SIMSR_L,
422		.prio	= 0,
423		.force	= IPIC_SIFCR_L,
424		.bit	= 15,
425	},
426	[80] = {
427		.mask	= IPIC_SIMSR_L,
428		.prio	= 0,
429		.force	= IPIC_SIFCR_L,
430		.bit	= 16,
431	},
432	[81] = {
433		.mask	= IPIC_SIMSR_L,
434		.prio	= 0,
435		.force	= IPIC_SIFCR_L,
436		.bit	= 17,
437	},
438	[82] = {
439		.mask	= IPIC_SIMSR_L,
440		.prio	= 0,
441		.force	= IPIC_SIFCR_L,
442		.bit	= 18,
443	},
444	[83] = {
445		.mask	= IPIC_SIMSR_L,
446		.prio	= 0,
447		.force	= IPIC_SIFCR_L,
448		.bit	= 19,
449	},
450	[84] = {
451		.mask	= IPIC_SIMSR_L,
452		.prio	= 0,
453		.force	= IPIC_SIFCR_L,
454		.bit	= 20,
455	},
456	[85] = {
457		.mask	= IPIC_SIMSR_L,
458		.prio	= 0,
459		.force	= IPIC_SIFCR_L,
460		.bit	= 21,
461	},
462	[86] = {
463		.mask	= IPIC_SIMSR_L,
464		.prio	= 0,
465		.force	= IPIC_SIFCR_L,
466		.bit	= 22,
467	},
468	[87] = {
469		.mask	= IPIC_SIMSR_L,
470		.prio	= 0,
471		.force	= IPIC_SIFCR_L,
472		.bit	= 23,
473	},
474	[88] = {
475		.mask	= IPIC_SIMSR_L,
476		.prio	= 0,
477		.force	= IPIC_SIFCR_L,
478		.bit	= 24,
479	},
480	[89] = {
481		.mask	= IPIC_SIMSR_L,
482		.prio	= 0,
483		.force	= IPIC_SIFCR_L,
484		.bit	= 25,
485	},
486	[90] = {
487		.mask	= IPIC_SIMSR_L,
488		.prio	= 0,
489		.force	= IPIC_SIFCR_L,
490		.bit	= 26,
491	},
492	[91] = {
493		.mask	= IPIC_SIMSR_L,
494		.prio	= 0,
495		.force	= IPIC_SIFCR_L,
496		.bit	= 27,
497	},
498	[94] = {
499		.mask	= IPIC_SIMSR_L,
500		.prio	= 0,
501		.force	= IPIC_SIFCR_L,
502		.bit	= 30,
503	},
504};
505
506static inline u32 ipic_read(volatile u32 __iomem *base, unsigned int reg)
507{
508	return in_be32(base + (reg >> 2));
509}
510
511static inline void ipic_write(volatile u32 __iomem *base, unsigned int reg, u32 value)
512{
513	out_be32(base + (reg >> 2), value);
514}
515
516static inline struct ipic * ipic_from_irq(unsigned int virq)
517{
518	return primary_ipic;
519}
520
521static void ipic_unmask_irq(struct irq_data *d)
522{
523	struct ipic *ipic = ipic_from_irq(d->irq);
524	unsigned int src = irqd_to_hwirq(d);
525	unsigned long flags;
526	u32 temp;
527
528	raw_spin_lock_irqsave(&ipic_lock, flags);
529
530	temp = ipic_read(ipic->regs, ipic_info[src].mask);
531	temp |= (1 << (31 - ipic_info[src].bit));
532	ipic_write(ipic->regs, ipic_info[src].mask, temp);
533
534	raw_spin_unlock_irqrestore(&ipic_lock, flags);
535}
536
537static void ipic_mask_irq(struct irq_data *d)
538{
539	struct ipic *ipic = ipic_from_irq(d->irq);
540	unsigned int src = irqd_to_hwirq(d);
541	unsigned long flags;
542	u32 temp;
543
544	raw_spin_lock_irqsave(&ipic_lock, flags);
545
546	temp = ipic_read(ipic->regs, ipic_info[src].mask);
547	temp &= ~(1 << (31 - ipic_info[src].bit));
548	ipic_write(ipic->regs, ipic_info[src].mask, temp);
549
550	/* mb() can't guarantee that masking is finished.  But it does finish
551	 * for nearly all cases. */
552	mb();
553
554	raw_spin_unlock_irqrestore(&ipic_lock, flags);
555}
556
557static void ipic_ack_irq(struct irq_data *d)
558{
559	struct ipic *ipic = ipic_from_irq(d->irq);
560	unsigned int src = irqd_to_hwirq(d);
561	unsigned long flags;
562	u32 temp;
563
564	raw_spin_lock_irqsave(&ipic_lock, flags);
565
566	temp = 1 << (31 - ipic_info[src].bit);
567	ipic_write(ipic->regs, ipic_info[src].ack, temp);
568
569	/* mb() can't guarantee that ack is finished.  But it does finish
570	 * for nearly all cases. */
571	mb();
572
573	raw_spin_unlock_irqrestore(&ipic_lock, flags);
574}
575
576static void ipic_mask_irq_and_ack(struct irq_data *d)
577{
578	struct ipic *ipic = ipic_from_irq(d->irq);
579	unsigned int src = irqd_to_hwirq(d);
580	unsigned long flags;
581	u32 temp;
582
583	raw_spin_lock_irqsave(&ipic_lock, flags);
584
585	temp = ipic_read(ipic->regs, ipic_info[src].mask);
586	temp &= ~(1 << (31 - ipic_info[src].bit));
587	ipic_write(ipic->regs, ipic_info[src].mask, temp);
588
589	temp = 1 << (31 - ipic_info[src].bit);
590	ipic_write(ipic->regs, ipic_info[src].ack, temp);
591
592	/* mb() can't guarantee that ack is finished.  But it does finish
593	 * for nearly all cases. */
594	mb();
595
596	raw_spin_unlock_irqrestore(&ipic_lock, flags);
597}
598
599static int ipic_set_irq_type(struct irq_data *d, unsigned int flow_type)
600{
601	struct ipic *ipic = ipic_from_irq(d->irq);
602	unsigned int src = irqd_to_hwirq(d);
603	unsigned int vold, vnew, edibit;
604
605	if (flow_type == IRQ_TYPE_NONE)
606		flow_type = IRQ_TYPE_LEVEL_LOW;
607
608	/* ipic supports only low assertion and high-to-low change senses
609	 */
610	if (!(flow_type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_EDGE_FALLING))) {
611		printk(KERN_ERR "ipic: sense type 0x%x not supported\n",
612			flow_type);
613		return -EINVAL;
614	}
615	/* ipic supports only edge mode on external interrupts */
616	if ((flow_type & IRQ_TYPE_EDGE_FALLING) && !ipic_info[src].ack) {
617		printk(KERN_ERR "ipic: edge sense not supported on internal "
618				"interrupts\n");
619		return -EINVAL;
620
621	}
622
623	irqd_set_trigger_type(d, flow_type);
624	if (flow_type & IRQ_TYPE_LEVEL_LOW)  {
625		irq_set_handler_locked(d, handle_level_irq);
626		d->chip = &ipic_level_irq_chip;
627	} else {
628		irq_set_handler_locked(d, handle_edge_irq);
629		d->chip = &ipic_edge_irq_chip;
630	}
631
632	/* only EXT IRQ senses are programmable on ipic
633	 * internal IRQ senses are LEVEL_LOW
634	 */
635	if (src == IPIC_IRQ_EXT0)
636		edibit = 15;
637	else
638		if (src >= IPIC_IRQ_EXT1 && src <= IPIC_IRQ_EXT7)
639			edibit = (14 - (src - IPIC_IRQ_EXT1));
640		else
641			return (flow_type & IRQ_TYPE_LEVEL_LOW) ? 0 : -EINVAL;
642
643	vold = ipic_read(ipic->regs, IPIC_SECNR);
644	if ((flow_type & IRQ_TYPE_SENSE_MASK) == IRQ_TYPE_EDGE_FALLING) {
645		vnew = vold | (1 << edibit);
646	} else {
647		vnew = vold & ~(1 << edibit);
648	}
649	if (vold != vnew)
650		ipic_write(ipic->regs, IPIC_SECNR, vnew);
651	return IRQ_SET_MASK_OK_NOCOPY;
652}
653
654/* level interrupts and edge interrupts have different ack operations */
655static struct irq_chip ipic_level_irq_chip = {
656	.name		= "IPIC",
657	.irq_unmask	= ipic_unmask_irq,
658	.irq_mask	= ipic_mask_irq,
659	.irq_mask_ack	= ipic_mask_irq,
660	.irq_set_type	= ipic_set_irq_type,
661};
662
663static struct irq_chip ipic_edge_irq_chip = {
664	.name		= "IPIC",
665	.irq_unmask	= ipic_unmask_irq,
666	.irq_mask	= ipic_mask_irq,
667	.irq_mask_ack	= ipic_mask_irq_and_ack,
668	.irq_ack	= ipic_ack_irq,
669	.irq_set_type	= ipic_set_irq_type,
670};
671
672static int ipic_host_match(struct irq_domain *h, struct device_node *node,
673			   enum irq_domain_bus_token bus_token)
674{
675	/* Exact match, unless ipic node is NULL */
676	struct device_node *of_node = irq_domain_get_of_node(h);
677	return of_node == NULL || of_node == node;
678}
679
680static int ipic_host_map(struct irq_domain *h, unsigned int virq,
681			 irq_hw_number_t hw)
682{
683	struct ipic *ipic = h->host_data;
684
685	irq_set_chip_data(virq, ipic);
686	irq_set_chip_and_handler(virq, &ipic_level_irq_chip, handle_level_irq);
687
688	/* Set default irq type */
689	irq_set_irq_type(virq, IRQ_TYPE_NONE);
690
691	return 0;
692}
693
694static const struct irq_domain_ops ipic_host_ops = {
695	.match	= ipic_host_match,
696	.map	= ipic_host_map,
697	.xlate	= irq_domain_xlate_onetwocell,
698};
699
700struct ipic * __init ipic_init(struct device_node *node, unsigned int flags)
701{
702	struct ipic	*ipic;
703	struct resource res;
704	u32 temp = 0, ret;
705
706	ret = of_address_to_resource(node, 0, &res);
707	if (ret)
708		return NULL;
709
710	ipic = kzalloc(sizeof(*ipic), GFP_KERNEL);
711	if (ipic == NULL)
712		return NULL;
713
714	ipic->irqhost = irq_domain_add_linear(node, NR_IPIC_INTS,
715					      &ipic_host_ops, ipic);
716	if (ipic->irqhost == NULL) {
717		kfree(ipic);
718		return NULL;
719	}
720
721	ipic->regs = ioremap(res.start, resource_size(&res));
722
723	/* init hw */
724	ipic_write(ipic->regs, IPIC_SICNR, 0x0);
725
726	/* default priority scheme is grouped. If spread mode is required
727	 * configure SICFR accordingly */
728	if (flags & IPIC_SPREADMODE_GRP_A)
729		temp |= SICFR_IPSA;
730	if (flags & IPIC_SPREADMODE_GRP_B)
731		temp |= SICFR_IPSB;
732	if (flags & IPIC_SPREADMODE_GRP_C)
733		temp |= SICFR_IPSC;
734	if (flags & IPIC_SPREADMODE_GRP_D)
735		temp |= SICFR_IPSD;
736	if (flags & IPIC_SPREADMODE_MIX_A)
737		temp |= SICFR_MPSA;
738	if (flags & IPIC_SPREADMODE_MIX_B)
739		temp |= SICFR_MPSB;
740
741	ipic_write(ipic->regs, IPIC_SICFR, temp);
742
743	/* handle MCP route */
744	temp = 0;
745	if (flags & IPIC_DISABLE_MCP_OUT)
746		temp = SERCR_MCPR;
747	ipic_write(ipic->regs, IPIC_SERCR, temp);
748
749	/* handle routing of IRQ0 to MCP */
750	temp = ipic_read(ipic->regs, IPIC_SEMSR);
751
752	if (flags & IPIC_IRQ0_MCP)
753		temp |= SEMSR_SIRQ0;
754	else
755		temp &= ~SEMSR_SIRQ0;
756
757	ipic_write(ipic->regs, IPIC_SEMSR, temp);
758
759	primary_ipic = ipic;
760	irq_set_default_host(primary_ipic->irqhost);
761
762	ipic_write(ipic->regs, IPIC_SIMSR_H, 0);
763	ipic_write(ipic->regs, IPIC_SIMSR_L, 0);
764
765	printk ("IPIC (%d IRQ sources) at %p\n", NR_IPIC_INTS,
766			primary_ipic->regs);
767
768	return ipic;
769}
770
771void __init ipic_set_default_priority(void)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
772{
773	ipic_write(primary_ipic->regs, IPIC_SIPRR_A, IPIC_PRIORITY_DEFAULT);
774	ipic_write(primary_ipic->regs, IPIC_SIPRR_B, IPIC_PRIORITY_DEFAULT);
775	ipic_write(primary_ipic->regs, IPIC_SIPRR_C, IPIC_PRIORITY_DEFAULT);
776	ipic_write(primary_ipic->regs, IPIC_SIPRR_D, IPIC_PRIORITY_DEFAULT);
777	ipic_write(primary_ipic->regs, IPIC_SMPRR_A, IPIC_PRIORITY_DEFAULT);
778	ipic_write(primary_ipic->regs, IPIC_SMPRR_B, IPIC_PRIORITY_DEFAULT);
779}
780
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
781u32 ipic_get_mcp_status(void)
782{
783	return primary_ipic ? ipic_read(primary_ipic->regs, IPIC_SERSR) : 0;
784}
785
786void ipic_clear_mcp_status(u32 mask)
787{
788	ipic_write(primary_ipic->regs, IPIC_SERSR, mask);
789}
790
791/* Return an interrupt vector or 0 if no interrupt is pending. */
792unsigned int ipic_get_irq(void)
793{
794	int irq;
795
796	BUG_ON(primary_ipic == NULL);
797
798#define IPIC_SIVCR_VECTOR_MASK	0x7f
799	irq = ipic_read(primary_ipic->regs, IPIC_SIVCR) & IPIC_SIVCR_VECTOR_MASK;
800
801	if (irq == 0)    /* 0 --> no irq is pending */
802		return 0;
803
804	return irq_linear_revmap(primary_ipic->irqhost, irq);
805}
806
807#ifdef CONFIG_SUSPEND
808static struct {
809	u32 sicfr;
810	u32 siprr[2];
811	u32 simsr[2];
812	u32 sicnr;
813	u32 smprr[2];
814	u32 semsr;
815	u32 secnr;
816	u32 sermr;
817	u32 sercr;
818} ipic_saved_state;
819
820static int ipic_suspend(void)
821{
822	struct ipic *ipic = primary_ipic;
823
824	ipic_saved_state.sicfr = ipic_read(ipic->regs, IPIC_SICFR);
825	ipic_saved_state.siprr[0] = ipic_read(ipic->regs, IPIC_SIPRR_A);
826	ipic_saved_state.siprr[1] = ipic_read(ipic->regs, IPIC_SIPRR_D);
827	ipic_saved_state.simsr[0] = ipic_read(ipic->regs, IPIC_SIMSR_H);
828	ipic_saved_state.simsr[1] = ipic_read(ipic->regs, IPIC_SIMSR_L);
829	ipic_saved_state.sicnr = ipic_read(ipic->regs, IPIC_SICNR);
830	ipic_saved_state.smprr[0] = ipic_read(ipic->regs, IPIC_SMPRR_A);
831	ipic_saved_state.smprr[1] = ipic_read(ipic->regs, IPIC_SMPRR_B);
832	ipic_saved_state.semsr = ipic_read(ipic->regs, IPIC_SEMSR);
833	ipic_saved_state.secnr = ipic_read(ipic->regs, IPIC_SECNR);
834	ipic_saved_state.sermr = ipic_read(ipic->regs, IPIC_SERMR);
835	ipic_saved_state.sercr = ipic_read(ipic->regs, IPIC_SERCR);
836
837	if (fsl_deep_sleep()) {
838		/* In deep sleep, make sure there can be no
839		 * pending interrupts, as this can cause
840		 * problems on 831x.
841		 */
842		ipic_write(ipic->regs, IPIC_SIMSR_H, 0);
843		ipic_write(ipic->regs, IPIC_SIMSR_L, 0);
844		ipic_write(ipic->regs, IPIC_SEMSR, 0);
845		ipic_write(ipic->regs, IPIC_SERMR, 0);
846	}
847
848	return 0;
849}
850
851static void ipic_resume(void)
852{
853	struct ipic *ipic = primary_ipic;
854
855	ipic_write(ipic->regs, IPIC_SICFR, ipic_saved_state.sicfr);
856	ipic_write(ipic->regs, IPIC_SIPRR_A, ipic_saved_state.siprr[0]);
857	ipic_write(ipic->regs, IPIC_SIPRR_D, ipic_saved_state.siprr[1]);
858	ipic_write(ipic->regs, IPIC_SIMSR_H, ipic_saved_state.simsr[0]);
859	ipic_write(ipic->regs, IPIC_SIMSR_L, ipic_saved_state.simsr[1]);
860	ipic_write(ipic->regs, IPIC_SICNR, ipic_saved_state.sicnr);
861	ipic_write(ipic->regs, IPIC_SMPRR_A, ipic_saved_state.smprr[0]);
862	ipic_write(ipic->regs, IPIC_SMPRR_B, ipic_saved_state.smprr[1]);
863	ipic_write(ipic->regs, IPIC_SEMSR, ipic_saved_state.semsr);
864	ipic_write(ipic->regs, IPIC_SECNR, ipic_saved_state.secnr);
865	ipic_write(ipic->regs, IPIC_SERMR, ipic_saved_state.sermr);
866	ipic_write(ipic->regs, IPIC_SERCR, ipic_saved_state.sercr);
867}
868#else
869#define ipic_suspend NULL
870#define ipic_resume NULL
871#endif
872
873static struct syscore_ops ipic_syscore_ops = {
874	.suspend = ipic_suspend,
875	.resume = ipic_resume,
876};
877
878static int __init init_ipic_syscore(void)
879{
880	if (!primary_ipic || !primary_ipic->regs)
881		return -ENODEV;
882
883	printk(KERN_DEBUG "Registering ipic system core operations\n");
884	register_syscore_ops(&ipic_syscore_ops);
885
886	return 0;
887}
888
889subsys_initcall(init_ipic_syscore);
v4.10.11
 
  1/*
  2 * arch/powerpc/sysdev/ipic.c
  3 *
  4 * IPIC routines implementations.
  5 *
  6 * Copyright 2005 Freescale Semiconductor, Inc.
  7 *
  8 * This program is free software; you can redistribute  it and/or modify it
  9 * under  the terms of  the GNU General  Public License as published by the
 10 * Free Software Foundation;  either version 2 of the  License, or (at your
 11 * option) any later version.
 12 */
 13#include <linux/kernel.h>
 14#include <linux/init.h>
 15#include <linux/errno.h>
 16#include <linux/reboot.h>
 17#include <linux/slab.h>
 18#include <linux/stddef.h>
 19#include <linux/sched.h>
 20#include <linux/signal.h>
 21#include <linux/syscore_ops.h>
 22#include <linux/device.h>
 23#include <linux/spinlock.h>
 24#include <linux/fsl_devices.h>
 
 
 25#include <asm/irq.h>
 26#include <asm/io.h>
 27#include <asm/prom.h>
 28#include <asm/ipic.h>
 29
 30#include "ipic.h"
 31
 32static struct ipic * primary_ipic;
 33static struct irq_chip ipic_level_irq_chip, ipic_edge_irq_chip;
 34static DEFINE_RAW_SPINLOCK(ipic_lock);
 35
 36static struct ipic_info ipic_info[] = {
 37	[1] = {
 38		.mask	= IPIC_SIMSR_H,
 39		.prio	= IPIC_SIPRR_C,
 40		.force	= IPIC_SIFCR_H,
 41		.bit	= 16,
 42		.prio_mask = 0,
 43	},
 44	[2] = {
 45		.mask	= IPIC_SIMSR_H,
 46		.prio	= IPIC_SIPRR_C,
 47		.force	= IPIC_SIFCR_H,
 48		.bit	= 17,
 49		.prio_mask = 1,
 50	},
 51	[3] = {
 52		.mask	= IPIC_SIMSR_H,
 53		.prio	= IPIC_SIPRR_C,
 54		.force	= IPIC_SIFCR_H,
 55		.bit	= 18,
 56		.prio_mask = 2,
 57	},
 58	[4] = {
 59		.mask	= IPIC_SIMSR_H,
 60		.prio	= IPIC_SIPRR_C,
 61		.force	= IPIC_SIFCR_H,
 62		.bit	= 19,
 63		.prio_mask = 3,
 64	},
 65	[5] = {
 66		.mask	= IPIC_SIMSR_H,
 67		.prio	= IPIC_SIPRR_C,
 68		.force	= IPIC_SIFCR_H,
 69		.bit	= 20,
 70		.prio_mask = 4,
 71	},
 72	[6] = {
 73		.mask	= IPIC_SIMSR_H,
 74		.prio	= IPIC_SIPRR_C,
 75		.force	= IPIC_SIFCR_H,
 76		.bit	= 21,
 77		.prio_mask = 5,
 78	},
 79	[7] = {
 80		.mask	= IPIC_SIMSR_H,
 81		.prio	= IPIC_SIPRR_C,
 82		.force	= IPIC_SIFCR_H,
 83		.bit	= 22,
 84		.prio_mask = 6,
 85	},
 86	[8] = {
 87		.mask	= IPIC_SIMSR_H,
 88		.prio	= IPIC_SIPRR_C,
 89		.force	= IPIC_SIFCR_H,
 90		.bit	= 23,
 91		.prio_mask = 7,
 92	},
 93	[9] = {
 94		.mask	= IPIC_SIMSR_H,
 95		.prio	= IPIC_SIPRR_D,
 96		.force	= IPIC_SIFCR_H,
 97		.bit	= 24,
 98		.prio_mask = 0,
 99	},
100	[10] = {
101		.mask	= IPIC_SIMSR_H,
102		.prio	= IPIC_SIPRR_D,
103		.force	= IPIC_SIFCR_H,
104		.bit	= 25,
105		.prio_mask = 1,
106	},
107	[11] = {
108		.mask	= IPIC_SIMSR_H,
109		.prio	= IPIC_SIPRR_D,
110		.force	= IPIC_SIFCR_H,
111		.bit	= 26,
112		.prio_mask = 2,
113	},
114	[12] = {
115		.mask	= IPIC_SIMSR_H,
116		.prio	= IPIC_SIPRR_D,
117		.force	= IPIC_SIFCR_H,
118		.bit	= 27,
119		.prio_mask = 3,
120	},
121	[13] = {
122		.mask	= IPIC_SIMSR_H,
123		.prio	= IPIC_SIPRR_D,
124		.force	= IPIC_SIFCR_H,
125		.bit	= 28,
126		.prio_mask = 4,
127	},
128	[14] = {
129		.mask	= IPIC_SIMSR_H,
130		.prio	= IPIC_SIPRR_D,
131		.force	= IPIC_SIFCR_H,
132		.bit	= 29,
133		.prio_mask = 5,
134	},
135	[15] = {
136		.mask	= IPIC_SIMSR_H,
137		.prio	= IPIC_SIPRR_D,
138		.force	= IPIC_SIFCR_H,
139		.bit	= 30,
140		.prio_mask = 6,
141	},
142	[16] = {
143		.mask	= IPIC_SIMSR_H,
144		.prio	= IPIC_SIPRR_D,
145		.force	= IPIC_SIFCR_H,
146		.bit	= 31,
147		.prio_mask = 7,
148	},
149	[17] = {
150		.ack	= IPIC_SEPNR,
151		.mask	= IPIC_SEMSR,
152		.prio	= IPIC_SMPRR_A,
153		.force	= IPIC_SEFCR,
154		.bit	= 1,
155		.prio_mask = 5,
156	},
157	[18] = {
158		.ack	= IPIC_SEPNR,
159		.mask	= IPIC_SEMSR,
160		.prio	= IPIC_SMPRR_A,
161		.force	= IPIC_SEFCR,
162		.bit	= 2,
163		.prio_mask = 6,
164	},
165	[19] = {
166		.ack	= IPIC_SEPNR,
167		.mask	= IPIC_SEMSR,
168		.prio	= IPIC_SMPRR_A,
169		.force	= IPIC_SEFCR,
170		.bit	= 3,
171		.prio_mask = 7,
172	},
173	[20] = {
174		.ack	= IPIC_SEPNR,
175		.mask	= IPIC_SEMSR,
176		.prio	= IPIC_SMPRR_B,
177		.force	= IPIC_SEFCR,
178		.bit	= 4,
179		.prio_mask = 4,
180	},
181	[21] = {
182		.ack	= IPIC_SEPNR,
183		.mask	= IPIC_SEMSR,
184		.prio	= IPIC_SMPRR_B,
185		.force	= IPIC_SEFCR,
186		.bit	= 5,
187		.prio_mask = 5,
188	},
189	[22] = {
190		.ack	= IPIC_SEPNR,
191		.mask	= IPIC_SEMSR,
192		.prio	= IPIC_SMPRR_B,
193		.force	= IPIC_SEFCR,
194		.bit	= 6,
195		.prio_mask = 6,
196	},
197	[23] = {
198		.ack	= IPIC_SEPNR,
199		.mask	= IPIC_SEMSR,
200		.prio	= IPIC_SMPRR_B,
201		.force	= IPIC_SEFCR,
202		.bit	= 7,
203		.prio_mask = 7,
204	},
205	[32] = {
206		.mask	= IPIC_SIMSR_H,
207		.prio	= IPIC_SIPRR_A,
208		.force	= IPIC_SIFCR_H,
209		.bit	= 0,
210		.prio_mask = 0,
211	},
212	[33] = {
213		.mask	= IPIC_SIMSR_H,
214		.prio	= IPIC_SIPRR_A,
215		.force	= IPIC_SIFCR_H,
216		.bit	= 1,
217		.prio_mask = 1,
218	},
219	[34] = {
220		.mask	= IPIC_SIMSR_H,
221		.prio	= IPIC_SIPRR_A,
222		.force	= IPIC_SIFCR_H,
223		.bit	= 2,
224		.prio_mask = 2,
225	},
226	[35] = {
227		.mask	= IPIC_SIMSR_H,
228		.prio	= IPIC_SIPRR_A,
229		.force	= IPIC_SIFCR_H,
230		.bit	= 3,
231		.prio_mask = 3,
232	},
233	[36] = {
234		.mask	= IPIC_SIMSR_H,
235		.prio	= IPIC_SIPRR_A,
236		.force	= IPIC_SIFCR_H,
237		.bit	= 4,
238		.prio_mask = 4,
239	},
240	[37] = {
241		.mask	= IPIC_SIMSR_H,
242		.prio	= IPIC_SIPRR_A,
243		.force	= IPIC_SIFCR_H,
244		.bit	= 5,
245		.prio_mask = 5,
246	},
247	[38] = {
248		.mask	= IPIC_SIMSR_H,
249		.prio	= IPIC_SIPRR_A,
250		.force	= IPIC_SIFCR_H,
251		.bit	= 6,
252		.prio_mask = 6,
253	},
254	[39] = {
255		.mask	= IPIC_SIMSR_H,
256		.prio	= IPIC_SIPRR_A,
257		.force	= IPIC_SIFCR_H,
258		.bit	= 7,
259		.prio_mask = 7,
260	},
261	[40] = {
262		.mask	= IPIC_SIMSR_H,
263		.prio	= IPIC_SIPRR_B,
264		.force	= IPIC_SIFCR_H,
265		.bit	= 8,
266		.prio_mask = 0,
267	},
268	[41] = {
269		.mask	= IPIC_SIMSR_H,
270		.prio	= IPIC_SIPRR_B,
271		.force	= IPIC_SIFCR_H,
272		.bit	= 9,
273		.prio_mask = 1,
274	},
275	[42] = {
276		.mask	= IPIC_SIMSR_H,
277		.prio	= IPIC_SIPRR_B,
278		.force	= IPIC_SIFCR_H,
279		.bit	= 10,
280		.prio_mask = 2,
281	},
282	[43] = {
283		.mask	= IPIC_SIMSR_H,
284		.prio	= IPIC_SIPRR_B,
285		.force	= IPIC_SIFCR_H,
286		.bit	= 11,
287		.prio_mask = 3,
288	},
289	[44] = {
290		.mask	= IPIC_SIMSR_H,
291		.prio	= IPIC_SIPRR_B,
292		.force	= IPIC_SIFCR_H,
293		.bit	= 12,
294		.prio_mask = 4,
295	},
296	[45] = {
297		.mask	= IPIC_SIMSR_H,
298		.prio	= IPIC_SIPRR_B,
299		.force	= IPIC_SIFCR_H,
300		.bit	= 13,
301		.prio_mask = 5,
302	},
303	[46] = {
304		.mask	= IPIC_SIMSR_H,
305		.prio	= IPIC_SIPRR_B,
306		.force	= IPIC_SIFCR_H,
307		.bit	= 14,
308		.prio_mask = 6,
309	},
310	[47] = {
311		.mask	= IPIC_SIMSR_H,
312		.prio	= IPIC_SIPRR_B,
313		.force	= IPIC_SIFCR_H,
314		.bit	= 15,
315		.prio_mask = 7,
316	},
317	[48] = {
 
318		.mask	= IPIC_SEMSR,
319		.prio	= IPIC_SMPRR_A,
320		.force	= IPIC_SEFCR,
321		.bit	= 0,
322		.prio_mask = 4,
323	},
324	[64] = {
325		.mask	= IPIC_SIMSR_L,
326		.prio	= IPIC_SMPRR_A,
327		.force	= IPIC_SIFCR_L,
328		.bit	= 0,
329		.prio_mask = 0,
330	},
331	[65] = {
332		.mask	= IPIC_SIMSR_L,
333		.prio	= IPIC_SMPRR_A,
334		.force	= IPIC_SIFCR_L,
335		.bit	= 1,
336		.prio_mask = 1,
337	},
338	[66] = {
339		.mask	= IPIC_SIMSR_L,
340		.prio	= IPIC_SMPRR_A,
341		.force	= IPIC_SIFCR_L,
342		.bit	= 2,
343		.prio_mask = 2,
344	},
345	[67] = {
346		.mask	= IPIC_SIMSR_L,
347		.prio	= IPIC_SMPRR_A,
348		.force	= IPIC_SIFCR_L,
349		.bit	= 3,
350		.prio_mask = 3,
351	},
352	[68] = {
353		.mask	= IPIC_SIMSR_L,
354		.prio	= IPIC_SMPRR_B,
355		.force	= IPIC_SIFCR_L,
356		.bit	= 4,
357		.prio_mask = 0,
358	},
359	[69] = {
360		.mask	= IPIC_SIMSR_L,
361		.prio	= IPIC_SMPRR_B,
362		.force	= IPIC_SIFCR_L,
363		.bit	= 5,
364		.prio_mask = 1,
365	},
366	[70] = {
367		.mask	= IPIC_SIMSR_L,
368		.prio	= IPIC_SMPRR_B,
369		.force	= IPIC_SIFCR_L,
370		.bit	= 6,
371		.prio_mask = 2,
372	},
373	[71] = {
374		.mask	= IPIC_SIMSR_L,
375		.prio	= IPIC_SMPRR_B,
376		.force	= IPIC_SIFCR_L,
377		.bit	= 7,
378		.prio_mask = 3,
379	},
380	[72] = {
381		.mask	= IPIC_SIMSR_L,
382		.prio	= 0,
383		.force	= IPIC_SIFCR_L,
384		.bit	= 8,
385	},
386	[73] = {
387		.mask	= IPIC_SIMSR_L,
388		.prio	= 0,
389		.force	= IPIC_SIFCR_L,
390		.bit	= 9,
391	},
392	[74] = {
393		.mask	= IPIC_SIMSR_L,
394		.prio	= 0,
395		.force	= IPIC_SIFCR_L,
396		.bit	= 10,
397	},
398	[75] = {
399		.mask	= IPIC_SIMSR_L,
400		.prio	= 0,
401		.force	= IPIC_SIFCR_L,
402		.bit	= 11,
403	},
404	[76] = {
405		.mask	= IPIC_SIMSR_L,
406		.prio	= 0,
407		.force	= IPIC_SIFCR_L,
408		.bit	= 12,
409	},
410	[77] = {
411		.mask	= IPIC_SIMSR_L,
412		.prio	= 0,
413		.force	= IPIC_SIFCR_L,
414		.bit	= 13,
415	},
416	[78] = {
417		.mask	= IPIC_SIMSR_L,
418		.prio	= 0,
419		.force	= IPIC_SIFCR_L,
420		.bit	= 14,
421	},
422	[79] = {
423		.mask	= IPIC_SIMSR_L,
424		.prio	= 0,
425		.force	= IPIC_SIFCR_L,
426		.bit	= 15,
427	},
428	[80] = {
429		.mask	= IPIC_SIMSR_L,
430		.prio	= 0,
431		.force	= IPIC_SIFCR_L,
432		.bit	= 16,
433	},
434	[81] = {
435		.mask	= IPIC_SIMSR_L,
436		.prio	= 0,
437		.force	= IPIC_SIFCR_L,
438		.bit	= 17,
439	},
440	[82] = {
441		.mask	= IPIC_SIMSR_L,
442		.prio	= 0,
443		.force	= IPIC_SIFCR_L,
444		.bit	= 18,
445	},
446	[83] = {
447		.mask	= IPIC_SIMSR_L,
448		.prio	= 0,
449		.force	= IPIC_SIFCR_L,
450		.bit	= 19,
451	},
452	[84] = {
453		.mask	= IPIC_SIMSR_L,
454		.prio	= 0,
455		.force	= IPIC_SIFCR_L,
456		.bit	= 20,
457	},
458	[85] = {
459		.mask	= IPIC_SIMSR_L,
460		.prio	= 0,
461		.force	= IPIC_SIFCR_L,
462		.bit	= 21,
463	},
464	[86] = {
465		.mask	= IPIC_SIMSR_L,
466		.prio	= 0,
467		.force	= IPIC_SIFCR_L,
468		.bit	= 22,
469	},
470	[87] = {
471		.mask	= IPIC_SIMSR_L,
472		.prio	= 0,
473		.force	= IPIC_SIFCR_L,
474		.bit	= 23,
475	},
476	[88] = {
477		.mask	= IPIC_SIMSR_L,
478		.prio	= 0,
479		.force	= IPIC_SIFCR_L,
480		.bit	= 24,
481	},
482	[89] = {
483		.mask	= IPIC_SIMSR_L,
484		.prio	= 0,
485		.force	= IPIC_SIFCR_L,
486		.bit	= 25,
487	},
488	[90] = {
489		.mask	= IPIC_SIMSR_L,
490		.prio	= 0,
491		.force	= IPIC_SIFCR_L,
492		.bit	= 26,
493	},
494	[91] = {
495		.mask	= IPIC_SIMSR_L,
496		.prio	= 0,
497		.force	= IPIC_SIFCR_L,
498		.bit	= 27,
499	},
500	[94] = {
501		.mask	= IPIC_SIMSR_L,
502		.prio	= 0,
503		.force	= IPIC_SIFCR_L,
504		.bit	= 30,
505	},
506};
507
508static inline u32 ipic_read(volatile u32 __iomem *base, unsigned int reg)
509{
510	return in_be32(base + (reg >> 2));
511}
512
513static inline void ipic_write(volatile u32 __iomem *base, unsigned int reg, u32 value)
514{
515	out_be32(base + (reg >> 2), value);
516}
517
518static inline struct ipic * ipic_from_irq(unsigned int virq)
519{
520	return primary_ipic;
521}
522
523static void ipic_unmask_irq(struct irq_data *d)
524{
525	struct ipic *ipic = ipic_from_irq(d->irq);
526	unsigned int src = irqd_to_hwirq(d);
527	unsigned long flags;
528	u32 temp;
529
530	raw_spin_lock_irqsave(&ipic_lock, flags);
531
532	temp = ipic_read(ipic->regs, ipic_info[src].mask);
533	temp |= (1 << (31 - ipic_info[src].bit));
534	ipic_write(ipic->regs, ipic_info[src].mask, temp);
535
536	raw_spin_unlock_irqrestore(&ipic_lock, flags);
537}
538
539static void ipic_mask_irq(struct irq_data *d)
540{
541	struct ipic *ipic = ipic_from_irq(d->irq);
542	unsigned int src = irqd_to_hwirq(d);
543	unsigned long flags;
544	u32 temp;
545
546	raw_spin_lock_irqsave(&ipic_lock, flags);
547
548	temp = ipic_read(ipic->regs, ipic_info[src].mask);
549	temp &= ~(1 << (31 - ipic_info[src].bit));
550	ipic_write(ipic->regs, ipic_info[src].mask, temp);
551
552	/* mb() can't guarantee that masking is finished.  But it does finish
553	 * for nearly all cases. */
554	mb();
555
556	raw_spin_unlock_irqrestore(&ipic_lock, flags);
557}
558
559static void ipic_ack_irq(struct irq_data *d)
560{
561	struct ipic *ipic = ipic_from_irq(d->irq);
562	unsigned int src = irqd_to_hwirq(d);
563	unsigned long flags;
564	u32 temp;
565
566	raw_spin_lock_irqsave(&ipic_lock, flags);
567
568	temp = 1 << (31 - ipic_info[src].bit);
569	ipic_write(ipic->regs, ipic_info[src].ack, temp);
570
571	/* mb() can't guarantee that ack is finished.  But it does finish
572	 * for nearly all cases. */
573	mb();
574
575	raw_spin_unlock_irqrestore(&ipic_lock, flags);
576}
577
578static void ipic_mask_irq_and_ack(struct irq_data *d)
579{
580	struct ipic *ipic = ipic_from_irq(d->irq);
581	unsigned int src = irqd_to_hwirq(d);
582	unsigned long flags;
583	u32 temp;
584
585	raw_spin_lock_irqsave(&ipic_lock, flags);
586
587	temp = ipic_read(ipic->regs, ipic_info[src].mask);
588	temp &= ~(1 << (31 - ipic_info[src].bit));
589	ipic_write(ipic->regs, ipic_info[src].mask, temp);
590
591	temp = 1 << (31 - ipic_info[src].bit);
592	ipic_write(ipic->regs, ipic_info[src].ack, temp);
593
594	/* mb() can't guarantee that ack is finished.  But it does finish
595	 * for nearly all cases. */
596	mb();
597
598	raw_spin_unlock_irqrestore(&ipic_lock, flags);
599}
600
601static int ipic_set_irq_type(struct irq_data *d, unsigned int flow_type)
602{
603	struct ipic *ipic = ipic_from_irq(d->irq);
604	unsigned int src = irqd_to_hwirq(d);
605	unsigned int vold, vnew, edibit;
606
607	if (flow_type == IRQ_TYPE_NONE)
608		flow_type = IRQ_TYPE_LEVEL_LOW;
609
610	/* ipic supports only low assertion and high-to-low change senses
611	 */
612	if (!(flow_type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_EDGE_FALLING))) {
613		printk(KERN_ERR "ipic: sense type 0x%x not supported\n",
614			flow_type);
615		return -EINVAL;
616	}
617	/* ipic supports only edge mode on external interrupts */
618	if ((flow_type & IRQ_TYPE_EDGE_FALLING) && !ipic_info[src].ack) {
619		printk(KERN_ERR "ipic: edge sense not supported on internal "
620				"interrupts\n");
621		return -EINVAL;
622
623	}
624
625	irqd_set_trigger_type(d, flow_type);
626	if (flow_type & IRQ_TYPE_LEVEL_LOW)  {
627		irq_set_handler_locked(d, handle_level_irq);
628		d->chip = &ipic_level_irq_chip;
629	} else {
630		irq_set_handler_locked(d, handle_edge_irq);
631		d->chip = &ipic_edge_irq_chip;
632	}
633
634	/* only EXT IRQ senses are programmable on ipic
635	 * internal IRQ senses are LEVEL_LOW
636	 */
637	if (src == IPIC_IRQ_EXT0)
638		edibit = 15;
639	else
640		if (src >= IPIC_IRQ_EXT1 && src <= IPIC_IRQ_EXT7)
641			edibit = (14 - (src - IPIC_IRQ_EXT1));
642		else
643			return (flow_type & IRQ_TYPE_LEVEL_LOW) ? 0 : -EINVAL;
644
645	vold = ipic_read(ipic->regs, IPIC_SECNR);
646	if ((flow_type & IRQ_TYPE_SENSE_MASK) == IRQ_TYPE_EDGE_FALLING) {
647		vnew = vold | (1 << edibit);
648	} else {
649		vnew = vold & ~(1 << edibit);
650	}
651	if (vold != vnew)
652		ipic_write(ipic->regs, IPIC_SECNR, vnew);
653	return IRQ_SET_MASK_OK_NOCOPY;
654}
655
656/* level interrupts and edge interrupts have different ack operations */
657static struct irq_chip ipic_level_irq_chip = {
658	.name		= "IPIC",
659	.irq_unmask	= ipic_unmask_irq,
660	.irq_mask	= ipic_mask_irq,
661	.irq_mask_ack	= ipic_mask_irq,
662	.irq_set_type	= ipic_set_irq_type,
663};
664
665static struct irq_chip ipic_edge_irq_chip = {
666	.name		= "IPIC",
667	.irq_unmask	= ipic_unmask_irq,
668	.irq_mask	= ipic_mask_irq,
669	.irq_mask_ack	= ipic_mask_irq_and_ack,
670	.irq_ack	= ipic_ack_irq,
671	.irq_set_type	= ipic_set_irq_type,
672};
673
674static int ipic_host_match(struct irq_domain *h, struct device_node *node,
675			   enum irq_domain_bus_token bus_token)
676{
677	/* Exact match, unless ipic node is NULL */
678	struct device_node *of_node = irq_domain_get_of_node(h);
679	return of_node == NULL || of_node == node;
680}
681
682static int ipic_host_map(struct irq_domain *h, unsigned int virq,
683			 irq_hw_number_t hw)
684{
685	struct ipic *ipic = h->host_data;
686
687	irq_set_chip_data(virq, ipic);
688	irq_set_chip_and_handler(virq, &ipic_level_irq_chip, handle_level_irq);
689
690	/* Set default irq type */
691	irq_set_irq_type(virq, IRQ_TYPE_NONE);
692
693	return 0;
694}
695
696static const struct irq_domain_ops ipic_host_ops = {
697	.match	= ipic_host_match,
698	.map	= ipic_host_map,
699	.xlate	= irq_domain_xlate_onetwocell,
700};
701
702struct ipic * __init ipic_init(struct device_node *node, unsigned int flags)
703{
704	struct ipic	*ipic;
705	struct resource res;
706	u32 temp = 0, ret;
707
708	ret = of_address_to_resource(node, 0, &res);
709	if (ret)
710		return NULL;
711
712	ipic = kzalloc(sizeof(*ipic), GFP_KERNEL);
713	if (ipic == NULL)
714		return NULL;
715
716	ipic->irqhost = irq_domain_add_linear(node, NR_IPIC_INTS,
717					      &ipic_host_ops, ipic);
718	if (ipic->irqhost == NULL) {
719		kfree(ipic);
720		return NULL;
721	}
722
723	ipic->regs = ioremap(res.start, resource_size(&res));
724
725	/* init hw */
726	ipic_write(ipic->regs, IPIC_SICNR, 0x0);
727
728	/* default priority scheme is grouped. If spread mode is required
729	 * configure SICFR accordingly */
730	if (flags & IPIC_SPREADMODE_GRP_A)
731		temp |= SICFR_IPSA;
732	if (flags & IPIC_SPREADMODE_GRP_B)
733		temp |= SICFR_IPSB;
734	if (flags & IPIC_SPREADMODE_GRP_C)
735		temp |= SICFR_IPSC;
736	if (flags & IPIC_SPREADMODE_GRP_D)
737		temp |= SICFR_IPSD;
738	if (flags & IPIC_SPREADMODE_MIX_A)
739		temp |= SICFR_MPSA;
740	if (flags & IPIC_SPREADMODE_MIX_B)
741		temp |= SICFR_MPSB;
742
743	ipic_write(ipic->regs, IPIC_SICFR, temp);
744
745	/* handle MCP route */
746	temp = 0;
747	if (flags & IPIC_DISABLE_MCP_OUT)
748		temp = SERCR_MCPR;
749	ipic_write(ipic->regs, IPIC_SERCR, temp);
750
751	/* handle routing of IRQ0 to MCP */
752	temp = ipic_read(ipic->regs, IPIC_SEMSR);
753
754	if (flags & IPIC_IRQ0_MCP)
755		temp |= SEMSR_SIRQ0;
756	else
757		temp &= ~SEMSR_SIRQ0;
758
759	ipic_write(ipic->regs, IPIC_SEMSR, temp);
760
761	primary_ipic = ipic;
762	irq_set_default_host(primary_ipic->irqhost);
763
764	ipic_write(ipic->regs, IPIC_SIMSR_H, 0);
765	ipic_write(ipic->regs, IPIC_SIMSR_L, 0);
766
767	printk ("IPIC (%d IRQ sources) at %p\n", NR_IPIC_INTS,
768			primary_ipic->regs);
769
770	return ipic;
771}
772
773int ipic_set_priority(unsigned int virq, unsigned int priority)
774{
775	struct ipic *ipic = ipic_from_irq(virq);
776	unsigned int src = virq_to_hw(virq);
777	u32 temp;
778
779	if (priority > 7)
780		return -EINVAL;
781	if (src > 127)
782		return -EINVAL;
783	if (ipic_info[src].prio == 0)
784		return -EINVAL;
785
786	temp = ipic_read(ipic->regs, ipic_info[src].prio);
787
788	if (priority < 4) {
789		temp &= ~(0x7 << (20 + (3 - priority) * 3));
790		temp |= ipic_info[src].prio_mask << (20 + (3 - priority) * 3);
791	} else {
792		temp &= ~(0x7 << (4 + (7 - priority) * 3));
793		temp |= ipic_info[src].prio_mask << (4 + (7 - priority) * 3);
794	}
795
796	ipic_write(ipic->regs, ipic_info[src].prio, temp);
797
798	return 0;
799}
800
801void ipic_set_highest_priority(unsigned int virq)
802{
803	struct ipic *ipic = ipic_from_irq(virq);
804	unsigned int src = virq_to_hw(virq);
805	u32 temp;
806
807	temp = ipic_read(ipic->regs, IPIC_SICFR);
808
809	/* clear and set HPI */
810	temp &= 0x7f000000;
811	temp |= (src & 0x7f) << 24;
812
813	ipic_write(ipic->regs, IPIC_SICFR, temp);
814}
815
816void ipic_set_default_priority(void)
817{
818	ipic_write(primary_ipic->regs, IPIC_SIPRR_A, IPIC_PRIORITY_DEFAULT);
819	ipic_write(primary_ipic->regs, IPIC_SIPRR_B, IPIC_PRIORITY_DEFAULT);
820	ipic_write(primary_ipic->regs, IPIC_SIPRR_C, IPIC_PRIORITY_DEFAULT);
821	ipic_write(primary_ipic->regs, IPIC_SIPRR_D, IPIC_PRIORITY_DEFAULT);
822	ipic_write(primary_ipic->regs, IPIC_SMPRR_A, IPIC_PRIORITY_DEFAULT);
823	ipic_write(primary_ipic->regs, IPIC_SMPRR_B, IPIC_PRIORITY_DEFAULT);
824}
825
826void ipic_enable_mcp(enum ipic_mcp_irq mcp_irq)
827{
828	struct ipic *ipic = primary_ipic;
829	u32 temp;
830
831	temp = ipic_read(ipic->regs, IPIC_SERMR);
832	temp |= (1 << (31 - mcp_irq));
833	ipic_write(ipic->regs, IPIC_SERMR, temp);
834}
835
836void ipic_disable_mcp(enum ipic_mcp_irq mcp_irq)
837{
838	struct ipic *ipic = primary_ipic;
839	u32 temp;
840
841	temp = ipic_read(ipic->regs, IPIC_SERMR);
842	temp &= (1 << (31 - mcp_irq));
843	ipic_write(ipic->regs, IPIC_SERMR, temp);
844}
845
846u32 ipic_get_mcp_status(void)
847{
848	return ipic_read(primary_ipic->regs, IPIC_SERMR);
849}
850
851void ipic_clear_mcp_status(u32 mask)
852{
853	ipic_write(primary_ipic->regs, IPIC_SERMR, mask);
854}
855
856/* Return an interrupt vector or 0 if no interrupt is pending. */
857unsigned int ipic_get_irq(void)
858{
859	int irq;
860
861	BUG_ON(primary_ipic == NULL);
862
863#define IPIC_SIVCR_VECTOR_MASK	0x7f
864	irq = ipic_read(primary_ipic->regs, IPIC_SIVCR) & IPIC_SIVCR_VECTOR_MASK;
865
866	if (irq == 0)    /* 0 --> no irq is pending */
867		return 0;
868
869	return irq_linear_revmap(primary_ipic->irqhost, irq);
870}
871
872#ifdef CONFIG_SUSPEND
873static struct {
874	u32 sicfr;
875	u32 siprr[2];
876	u32 simsr[2];
877	u32 sicnr;
878	u32 smprr[2];
879	u32 semsr;
880	u32 secnr;
881	u32 sermr;
882	u32 sercr;
883} ipic_saved_state;
884
885static int ipic_suspend(void)
886{
887	struct ipic *ipic = primary_ipic;
888
889	ipic_saved_state.sicfr = ipic_read(ipic->regs, IPIC_SICFR);
890	ipic_saved_state.siprr[0] = ipic_read(ipic->regs, IPIC_SIPRR_A);
891	ipic_saved_state.siprr[1] = ipic_read(ipic->regs, IPIC_SIPRR_D);
892	ipic_saved_state.simsr[0] = ipic_read(ipic->regs, IPIC_SIMSR_H);
893	ipic_saved_state.simsr[1] = ipic_read(ipic->regs, IPIC_SIMSR_L);
894	ipic_saved_state.sicnr = ipic_read(ipic->regs, IPIC_SICNR);
895	ipic_saved_state.smprr[0] = ipic_read(ipic->regs, IPIC_SMPRR_A);
896	ipic_saved_state.smprr[1] = ipic_read(ipic->regs, IPIC_SMPRR_B);
897	ipic_saved_state.semsr = ipic_read(ipic->regs, IPIC_SEMSR);
898	ipic_saved_state.secnr = ipic_read(ipic->regs, IPIC_SECNR);
899	ipic_saved_state.sermr = ipic_read(ipic->regs, IPIC_SERMR);
900	ipic_saved_state.sercr = ipic_read(ipic->regs, IPIC_SERCR);
901
902	if (fsl_deep_sleep()) {
903		/* In deep sleep, make sure there can be no
904		 * pending interrupts, as this can cause
905		 * problems on 831x.
906		 */
907		ipic_write(ipic->regs, IPIC_SIMSR_H, 0);
908		ipic_write(ipic->regs, IPIC_SIMSR_L, 0);
909		ipic_write(ipic->regs, IPIC_SEMSR, 0);
910		ipic_write(ipic->regs, IPIC_SERMR, 0);
911	}
912
913	return 0;
914}
915
916static void ipic_resume(void)
917{
918	struct ipic *ipic = primary_ipic;
919
920	ipic_write(ipic->regs, IPIC_SICFR, ipic_saved_state.sicfr);
921	ipic_write(ipic->regs, IPIC_SIPRR_A, ipic_saved_state.siprr[0]);
922	ipic_write(ipic->regs, IPIC_SIPRR_D, ipic_saved_state.siprr[1]);
923	ipic_write(ipic->regs, IPIC_SIMSR_H, ipic_saved_state.simsr[0]);
924	ipic_write(ipic->regs, IPIC_SIMSR_L, ipic_saved_state.simsr[1]);
925	ipic_write(ipic->regs, IPIC_SICNR, ipic_saved_state.sicnr);
926	ipic_write(ipic->regs, IPIC_SMPRR_A, ipic_saved_state.smprr[0]);
927	ipic_write(ipic->regs, IPIC_SMPRR_B, ipic_saved_state.smprr[1]);
928	ipic_write(ipic->regs, IPIC_SEMSR, ipic_saved_state.semsr);
929	ipic_write(ipic->regs, IPIC_SECNR, ipic_saved_state.secnr);
930	ipic_write(ipic->regs, IPIC_SERMR, ipic_saved_state.sermr);
931	ipic_write(ipic->regs, IPIC_SERCR, ipic_saved_state.sercr);
932}
933#else
934#define ipic_suspend NULL
935#define ipic_resume NULL
936#endif
937
938static struct syscore_ops ipic_syscore_ops = {
939	.suspend = ipic_suspend,
940	.resume = ipic_resume,
941};
942
943static int __init init_ipic_syscore(void)
944{
945	if (!primary_ipic || !primary_ipic->regs)
946		return -ENODEV;
947
948	printk(KERN_DEBUG "Registering ipic system core operations\n");
949	register_syscore_ops(&ipic_syscore_ops);
950
951	return 0;
952}
953
954subsys_initcall(init_ipic_syscore);