Linux Audio

Check our new training course

Embedded Linux training

Mar 10-20, 2025, special US time zones
Register
Loading...
Note: File does not exist in v3.1.
  1/*
  2 * IRQ vector handles
  3 *
  4 * Copyright (C) 1995, 1996, 1997, 2003 by Ralf Baechle
  5 *
  6 * This file is subject to the terms and conditions of the GNU General Public
  7 * License.  See the file "COPYING" in the main directory of this archive
  8 * for more details.
  9 */
 10
 11#include <linux/kernel.h>
 12#include <linux/init.h>
 13#include <linux/irq.h>
 14#include <linux/interrupt.h>
 15#include <linux/ptrace.h>
 16#include <linux/time.h>
 17
 18#include <asm/irq_cpu.h>
 19
 20#include <msp_int.h>
 21
 22/* SLP bases systems */
 23extern void msp_slp_irq_init(void);
 24extern void msp_slp_irq_dispatch(void);
 25
 26/* CIC based systems */
 27extern void msp_cic_irq_init(void);
 28extern void msp_cic_irq_dispatch(void);
 29
 30/* VSMP support init */
 31extern void msp_vsmp_int_init(void);
 32
 33/* vectored interrupt implementation */
 34
 35/* SW0/1 interrupts are used for SMP/SMTC */
 36static inline void mac0_int_dispatch(void) { do_IRQ(MSP_INT_MAC0); }
 37static inline void mac1_int_dispatch(void) { do_IRQ(MSP_INT_MAC1); }
 38static inline void mac2_int_dispatch(void) { do_IRQ(MSP_INT_SAR); }
 39static inline void usb_int_dispatch(void)  { do_IRQ(MSP_INT_USB);  }
 40static inline void sec_int_dispatch(void)  { do_IRQ(MSP_INT_SEC);  }
 41
 42/*
 43 * The PMC-Sierra MSP interrupts are arranged in a 3 level cascaded
 44 * hierarchical system.	 The first level are the direct MIPS interrupts
 45 * and are assigned the interrupt range 0-7.  The second level is the SLM
 46 * interrupt controller and is assigned the range 8-39.	 The third level
 47 * comprises the Peripherial block, the PCI block, the PCI MSI block and
 48 * the SLP.  The PCI interrupts and the SLP errors are handled by the
 49 * relevant subsystems so the core interrupt code needs only concern
 50 * itself with the Peripheral block.  These are assigned interrupts in
 51 * the range 40-71.
 52 */
 53
 54asmlinkage void plat_irq_dispatch(struct pt_regs *regs)
 55{
 56	u32 pending;
 57
 58	pending = read_c0_status() & read_c0_cause();
 59
 60	/*
 61	 * jump to the correct interrupt routine
 62	 * These are arranged in priority order and the timer
 63	 * comes first!
 64	 */
 65
 66#ifdef CONFIG_IRQ_MSP_CIC	/* break out the CIC stuff for now */
 67	if (pending & C_IRQ4)	/* do the peripherals first, that's the timer */
 68		msp_cic_irq_dispatch();
 69
 70	else if (pending & C_IRQ0)
 71		do_IRQ(MSP_INT_MAC0);
 72
 73	else if (pending & C_IRQ1)
 74		do_IRQ(MSP_INT_MAC1);
 75
 76	else if (pending & C_IRQ2)
 77		do_IRQ(MSP_INT_USB);
 78
 79	else if (pending & C_IRQ3)
 80		do_IRQ(MSP_INT_SAR);
 81
 82	else if (pending & C_IRQ5)
 83		do_IRQ(MSP_INT_SEC);
 84
 85#else
 86	if (pending & C_IRQ5)
 87		do_IRQ(MSP_INT_TIMER);
 88
 89	else if (pending & C_IRQ0)
 90		do_IRQ(MSP_INT_MAC0);
 91
 92	else if (pending & C_IRQ1)
 93		do_IRQ(MSP_INT_MAC1);
 94
 95	else if (pending & C_IRQ3)
 96		do_IRQ(MSP_INT_VE);
 97
 98	else if (pending & C_IRQ4)
 99		msp_slp_irq_dispatch();
100#endif
101
102	else if (pending & C_SW0)	/* do software after hardware */
103		do_IRQ(MSP_INT_SW0);
104
105	else if (pending & C_SW1)
106		do_IRQ(MSP_INT_SW1);
107}
108
109static struct irqaction cic_cascade_msp = {
110	.handler = no_action,
111	.name	 = "MSP CIC cascade",
112	.flags	 = IRQF_NO_THREAD,
113};
114
115static struct irqaction per_cascade_msp = {
116	.handler = no_action,
117	.name	 = "MSP PER cascade",
118	.flags	 = IRQF_NO_THREAD,
119};
120
121void __init arch_init_irq(void)
122{
123	/* assume we'll be using vectored interrupt mode except in UP mode*/
124#ifdef CONFIG_MIPS_MT
125	BUG_ON(!cpu_has_vint);
126#endif
127	/* initialize the 1st-level CPU based interrupt controller */
128	mips_cpu_irq_init();
129
130#ifdef CONFIG_IRQ_MSP_CIC
131	msp_cic_irq_init();
132#ifdef CONFIG_MIPS_MT
133	set_vi_handler(MSP_INT_CIC, msp_cic_irq_dispatch);
134	set_vi_handler(MSP_INT_MAC0, mac0_int_dispatch);
135	set_vi_handler(MSP_INT_MAC1, mac1_int_dispatch);
136	set_vi_handler(MSP_INT_SAR, mac2_int_dispatch);
137	set_vi_handler(MSP_INT_USB, usb_int_dispatch);
138	set_vi_handler(MSP_INT_SEC, sec_int_dispatch);
139#ifdef CONFIG_MIPS_MT_SMP
140	msp_vsmp_int_init();
141#elif defined CONFIG_MIPS_MT_SMTC
142	/*Set hwmask for all platform devices */
143	irq_hwmask[MSP_INT_MAC0] = C_IRQ0;
144	irq_hwmask[MSP_INT_MAC1] = C_IRQ1;
145	irq_hwmask[MSP_INT_USB] = C_IRQ2;
146	irq_hwmask[MSP_INT_SAR] = C_IRQ3;
147	irq_hwmask[MSP_INT_SEC] = C_IRQ5;
148
149#endif	/* CONFIG_MIPS_MT_SMP */
150#endif	/* CONFIG_MIPS_MT */
151	/* setup the cascaded interrupts */
152	setup_irq(MSP_INT_CIC, &cic_cascade_msp);
153	setup_irq(MSP_INT_PER, &per_cascade_msp);
154
155#else
156	/* setup the 2nd-level SLP register based interrupt controller */
157	/* VSMP /SMTC support support is not enabled for SLP */
158	msp_slp_irq_init();
159
160	/* setup the cascaded SLP/PER interrupts */
161	setup_irq(MSP_INT_SLP, &cic_cascade_msp);
162	setup_irq(MSP_INT_PER, &per_cascade_msp);
163#endif
164}