0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <linux/init.h>
0010 #include <linux/irq.h>
0011 #include <linux/types.h>
0012
0013 #include <asm/dec/kn02.h>
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024 u32 cached_kn02_csr;
0025
0026 static int kn02_irq_base;
0027
0028 static void unmask_kn02_irq(struct irq_data *d)
0029 {
0030 volatile u32 *csr = (volatile u32 *)CKSEG1ADDR(KN02_SLOT_BASE +
0031 KN02_CSR);
0032
0033 cached_kn02_csr |= (1 << (d->irq - kn02_irq_base + 16));
0034 *csr = cached_kn02_csr;
0035 }
0036
0037 static void mask_kn02_irq(struct irq_data *d)
0038 {
0039 volatile u32 *csr = (volatile u32 *)CKSEG1ADDR(KN02_SLOT_BASE +
0040 KN02_CSR);
0041
0042 cached_kn02_csr &= ~(1 << (d->irq - kn02_irq_base + 16));
0043 *csr = cached_kn02_csr;
0044 }
0045
0046 static void ack_kn02_irq(struct irq_data *d)
0047 {
0048 mask_kn02_irq(d);
0049 iob();
0050 }
0051
0052 static struct irq_chip kn02_irq_type = {
0053 .name = "KN02-CSR",
0054 .irq_ack = ack_kn02_irq,
0055 .irq_mask = mask_kn02_irq,
0056 .irq_mask_ack = ack_kn02_irq,
0057 .irq_unmask = unmask_kn02_irq,
0058 };
0059
0060 void __init init_kn02_irqs(int base)
0061 {
0062 volatile u32 *csr = (volatile u32 *)CKSEG1ADDR(KN02_SLOT_BASE +
0063 KN02_CSR);
0064 int i;
0065
0066
0067 cached_kn02_csr &= ~KN02_CSR_IOINTEN;
0068 *csr = cached_kn02_csr;
0069 iob();
0070
0071 for (i = base; i < base + KN02_IRQ_LINES; i++)
0072 irq_set_chip_and_handler(i, &kn02_irq_type, handle_level_irq);
0073
0074 kn02_irq_base = base;
0075 }