OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [rc203soc/] [sw/] [uClinux/] [arch/] [or32/] [kernel/] [irq.c] - Blame information for rev 1777

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1624 jcastillo
#include <linux/types.h>
2
#include <linux/sched.h>
3
#include <linux/kernel_stat.h>
4
#include <linux/errno.h>
5
 
6
#include <asm/system.h>
7
#include <asm/irq.h>
8
#include <asm/traps.h>
9
#include <asm/page.h>
10
#include <asm/machdep.h>
11
 
12
/* table for system interrupt handlers */
13
static irq_handler_t irq_list[SYS_IRQS];
14
 
15
static const char *default_names[SYS_IRQS] = {
16
        "int0", "int1", "int2", "int3", "int4", "int5", "int6", "int7"
17
        "int8", "int9", "int10", "int11", "int12", "int13", "int14", "int15"
18
        "int16", "int17", "int18", "int19", "int20", "int21", "int22", "int23"
19
        "int24", "int25", "int26", "int27", "int28", "int29", "int30", "int31"
20
};
21
 
22
int pic_enable_irq(unsigned int irq)
23
{
24
        /* Enable in the IMR */
25
        mtspr(SPR_PICMR, mfspr(SPR_PICMR) | (0x00000001L << irq));
26
 
27
        return 0;
28
}
29
 
30
int pic_disable_irq(unsigned int irq)
31
{
32
        /* Disable in the IMR */
33
        mtspr(SPR_PICMR, mfspr(SPR_PICMR) & ~(0x00000001L << irq));
34
 
35
        return 0;
36
}
37
 
38
int pic_init(void)
39
{
40
        /* turn off all interrupts */
41
        mtspr(SPR_PICMR, 0);
42
        return 0;
43
}
44
 
45
int pic_do_irq(struct pt_regs *fp)
46
{
47
        int irq;
48
        int mask;
49
 
50
        unsigned long pend = mfspr(SPR_PICSR) & 0xfffffffc;
51
 
52
        if (pend & 0x0000ffff) {
53
                if (pend & 0x000000ff) {
54
                        if (pend & 0x0000000f) {
55
                                mask = 0x00000001;
56
                                irq = 0;
57
                        } else {
58
                                mask = 0x00000010;
59
                                irq = 4;
60
                        }
61
                } else {
62
                        if (pend & 0x00000f00) {
63
                                mask = 0x00000100;
64
                                irq = 8;
65
                        } else {
66
                                mask = 0x00001000;
67
                                irq = 12;
68
                        }
69
                }
70
        } else if(pend & 0xffff0000) {
71
                if (pend & 0x00ff0000) {
72
                        if (pend & 0x000f0000) {
73
                                mask = 0x00010000;
74
                                irq = 16;
75
                        } else {
76
                                mask = 0x00100000;
77
                                irq = 20;
78
                        }
79
                } else {
80
                        if (pend & 0x0f000000) {
81
                                mask = 0x01000000;
82
                                irq = 24;
83
                        } else {
84
                                mask = 0x10000000;
85
                                irq = 28;
86
                        }
87
                }
88
        } else {
89
                return -1;
90
        }
91
 
92
        while (! (mask & pend)) {
93
                mask <<=1;
94
                irq++;
95
        }
96
 
97
        mtspr(SPR_PICSR, mfspr(SPR_PICSR) & ~mask);
98
        return irq;
99
}
100
 
101
void init_IRQ(void)
102
{
103
        int i;
104
 
105
        for (i = 0; i < SYS_IRQS; i++) {
106
                irq_list[i].handler = NULL;
107
                irq_list[i].flags   = IRQ_FLG_STD;
108
                irq_list[i].dev_id  = NULL;
109
                irq_list[i].devname = default_names[i];
110
        }
111
 
112
        pic_init();
113
}
114
 
115
asmlinkage void handle_IRQ(struct pt_regs *regs)
116
{
117
        int irq;
118
 
119
        while((irq = pic_do_irq(regs)) >= 0) {
120
 
121
                if (irq_list[irq].handler)
122
                        irq_list[irq].handler(irq, irq_list[irq].dev_id, regs);
123
                else
124
                        panic("No interrupt handler for autovector %d\n", irq);
125
        }
126
}
127
 
128
int request_irq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *),
129
                unsigned long flags, const char *devname, void *dev_id)
130
{
131
        if (irq >= SYS_IRQS) {
132
                printk("%s: Incorrect IRQ %d from %s\n", __FUNCTION__, irq, devname);
133
                return -ENXIO;
134
        }
135
 
136
        if (!(irq_list[irq].flags & IRQ_FLG_STD)) {
137
                if (irq_list[irq].flags & IRQ_FLG_LOCK) {
138
                        printk("%s: IRQ %d from %s is not replaceable\n",
139
                               __FUNCTION__, irq, irq_list[irq].devname);
140
                        return -EBUSY;
141
                }
142
                if (flags & IRQ_FLG_REPLACE) {
143
                        printk("%s: %s can't replace IRQ %d from %s\n",
144
                               __FUNCTION__, devname, irq, irq_list[irq].devname);
145
                        return -EBUSY;
146
                }
147
        }
148
        irq_list[irq].handler = handler;
149
        irq_list[irq].flags   = flags;
150
        irq_list[irq].dev_id  = dev_id;
151
        irq_list[irq].devname = devname;
152
 
153
  pic_enable_irq(irq);
154
 
155
        return 0;
156
}
157
 
158
void free_irq(unsigned int irq, void *dev_id)
159
{
160
        if (irq >= SYS_IRQS) {
161
                printk("%s: Incorrect IRQ %d\n", __FUNCTION__, irq);
162
                return;
163
        }
164
 
165
  pic_disable_irq(irq);
166
 
167
        irq_list[irq].handler = NULL;
168
        irq_list[irq].flags   = IRQ_FLG_STD;
169
        irq_list[irq].dev_id  = NULL;
170
        irq_list[irq].devname = default_names[irq];
171
}
172
 
173
unsigned long probe_irq_on (void)
174
{
175
        return 0;
176
}
177
 
178
int probe_irq_off (unsigned long irqs)
179
{
180
        return 0;
181
}
182
 
183
void enable_irq(unsigned int irq)
184
{
185
        if (irq >= SYS_IRQS) {
186
                printk("%s: Incorrect IRQ %d\n", __FUNCTION__, irq);
187
                return;
188
        }
189
        pic_enable_irq(irq);
190
}
191
 
192
void disable_irq(unsigned int irq)
193
{
194
        if (irq >= SYS_IRQS) {
195
                printk("%s: Incorrect IRQ %d\n", __FUNCTION__, irq);
196
                return;
197
        }
198
        pic_disable_irq(irq);
199
}
200
 
201
int get_irq_list(char *buf)
202
{
203
        int i, len = 0;
204
 
205
        /* autovector interrupts */
206
        for (i = 0; i < SYS_IRQS; i++) {
207
                if (irq_list[i].handler) {
208
                        if (irq_list[i].flags & IRQ_FLG_LOCK)
209
                                len += sprintf(buf+len, "L ");
210
                        else
211
                                len += sprintf(buf+len, "  ");
212
                        if (irq_list[i].flags & IRQ_FLG_PRI_HI)
213
                                len += sprintf(buf+len, "H ");
214
                        else
215
                                len += sprintf(buf+len, "L ");
216
                        len += sprintf(buf+len, "%s\n", irq_list[i].devname);
217
                }
218
        }
219
 
220
        return len;
221
}
222
 
223
void dump(struct pt_regs *fp)
224
{
225
        unsigned long   *sp;
226
        unsigned char   *tp;
227
        int             i;
228
 
229
        printk("\nCURRENT PROCESS:\n\n");
230
        printk("COMM=%s PID=%d\n", current->comm, current->pid);
231
        if (current->mm) {
232
                printk("TEXT=%08x-%08x DATA=%08x-%08x BSS=%08x-%08x\n",
233
                        (int) current->mm->start_code,
234
                        (int) current->mm->end_code,
235
                        (int) current->mm->start_data,
236
                        (int) current->mm->end_data,
237
                        (int) current->mm->end_data,
238
                        (int) current->mm->brk);
239
                printk("USER-STACK=%08x  KERNEL-STACK=%08x\n\n",
240
                        (int) current->mm->start_stack,
241
                        (int) current->kernel_stack_page);
242
        }
243
        printk("PC: %08lx  Status: %08lx\n",
244
               fp->pc, fp->sr);
245
        printk("R0 : %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx\n",
246
                0L,             fp->sp,      fp->gprs[0], fp->gprs[1],
247
                fp->gprs[2], fp->gprs[3], fp->gprs[4], fp->gprs[5]);
248
        printk("R8 : %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx\n",
249
                fp->gprs[6], fp->gprs[7], fp->gprs[8], fp->gprs[9],
250
                fp->gprs[10], fp->gprs[11], fp->gprs[12], fp->gprs[13]);
251
        printk("R16: %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx\n",
252
                fp->gprs[14], fp->gprs[15], fp->gprs[16], fp->gprs[17],
253
                fp->gprs[18], fp->gprs[19], fp->gprs[20], fp->gprs[21]);
254
        printk("R24: %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx  %08lx\n",
255
                fp->gprs[22], fp->gprs[23], fp->gprs[24], fp->gprs[25],
256
                fp->gprs[26], fp->gprs[27], fp->gprs[28], fp->gprs[29]);
257
 
258
        printk("\nUSP: %08lx   TRAPFRAME: %08x\n",
259
                fp->sp, (unsigned int) fp);
260
 
261
        printk("\nCODE:");
262
        tp = ((unsigned char *) fp->pc) - 0x20;
263
        for (sp = (unsigned long *) tp, i = 0; (i < 0x40);  i += 4) {
264
                if ((i % 0x10) == 0)
265
                        printk("\n%08x: ", (int) (tp + i));
266
                printk("%08x ", (int) *sp++);
267
        }
268
        printk("\n");
269
 
270
        printk("\nKERNEL STACK:");
271
        tp = ((unsigned char *) fp) - 0x40;
272
        for (sp = (unsigned long *) tp, i = 0; (i < 0xc0); i += 4) {
273
                if ((i % 0x10) == 0)
274
                        printk("\n%08x: ", (int) (tp + i));
275
                printk("%08x ", (int) *sp++);
276
        }
277
        printk("\n");
278
        if (STACK_MAGIC != *(unsigned long *)current->kernel_stack_page)
279
                printk("(Possibly corrupted stack page??)\n");
280
        printk("\n");
281
 
282
        printk("\nUSER STACK:");
283
        tp = (unsigned char *) (fp->sp - 0x10);
284
        for (sp = (unsigned long *) tp, i = 0; (i < 0x80); i += 4) {
285
                if ((i % 0x10) == 0)
286
                        printk("\n%08x: ", (int) (tp + i));
287
                printk("%08x ", (int) *sp++);
288
        }
289
        printk("\n\n");
290
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.