⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 interrupts.c

📁 U-boot源码 ARM7启动代码
💻 C
字号:
/* * (C) Copyright 2007 Michal Simek * (C) Copyright 2004 Atmark Techno, Inc. * * Michal  SIMEK <monstr@monstr.eu> * Yasushi SHOJI <yashi@atmark-techno.com> * * See file CREDITS for list of people who contributed to this * project. * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation; either version 2 of * the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, * MA 02111-1307 USA */#include <common.h>#include <command.h>#include <asm/microblaze_intc.h>#include <asm/asm.h>#undef DEBUG_INTextern void microblaze_disable_interrupts (void);extern void microblaze_enable_interrupts (void);void enable_interrupts (void){	MSRSET(0x2);}int disable_interrupts (void){	MSRCLR(0x2);	return 0;}#ifdef CFG_INTC_0#ifdef CFG_TIMER_0extern void timer_init (void);#endif#ifdef CFG_FSL_2extern void fsl_init2 (void);#endifstatic struct irq_action vecs[CFG_INTC_0_NUM];/* mapping structure to interrupt controller */microblaze_intc_t *intc = (microblaze_intc_t *) (CFG_INTC_0_ADDR);/* default handler */void def_hdlr (void){	puts ("def_hdlr\n");}void enable_one_interrupt (int irq){	int mask;	int offset = 1;	offset <<= irq;	mask = intc->ier;	intc->ier = (mask | offset);#ifdef DEBUG_INT	printf ("Enable one interrupt irq %x - mask %x,ier %x\n", offset, mask,		intc->ier);	printf ("INTC isr %x, ier %x, iar %x, mer %x\n", intc->isr, intc->ier,		intc->iar, intc->mer);#endif}void disable_one_interrupt (int irq){	int mask;	int offset = 1;	offset <<= irq;	mask = intc->ier;	intc->ier = (mask & ~offset);#ifdef DEBUG_INT	printf ("Disable one interrupt irq %x - mask %x,ier %x\n", irq, mask,		intc->ier);	printf ("INTC isr %x, ier %x, iar %x, mer %x\n", intc->isr, intc->ier,		intc->iar, intc->mer);#endif}/* adding new handler for interrupt */void install_interrupt_handler (int irq, interrupt_handler_t * hdlr, void *arg){	struct irq_action *act;	/* irq out of range */	if ((irq < 0) || (irq > CFG_INTC_0_NUM)) {		puts ("IRQ out of range\n");		return;	}	act = &vecs[irq];	if (hdlr) {		/* enable */		act->handler = hdlr;		act->arg = arg;		act->count = 0;		enable_one_interrupt (irq);	} else {		/* disable */		act->handler = (interrupt_handler_t *) def_hdlr;		act->arg = (void *)irq;		disable_one_interrupt (irq);	}}/* initialization interrupt controller - hardware */void intc_init (void){	intc->mer = 0;	intc->ier = 0;	intc->iar = 0xFFFFFFFF;	/* XIntc_Start - hw_interrupt enable and all interrupt enable */	intc->mer = 0x3;#ifdef DEBUG_INT	printf ("INTC isr %x, ier %x, iar %x, mer %x\n", intc->isr, intc->ier,		intc->iar, intc->mer);#endif}int interrupts_init (void){	int i;	/* initialize irq list */	for (i = 0; i < CFG_INTC_0_NUM; i++) {		vecs[i].handler = (interrupt_handler_t *) def_hdlr;		vecs[i].arg = (void *)i;		vecs[i].count = 0;	}	/* initialize intc controller */	intc_init ();#ifdef CFG_TIMER_0	timer_init ();#endif#ifdef CFG_FSL_2	fsl_init2 ();#endif	enable_interrupts ();	return 0;}void interrupt_handler (void){	int irqs = (intc->isr & intc->ier);	/* find active interrupt */	int i = 1;#ifdef DEBUG_INT	int value;	printf ("INTC isr %x, ier %x, iar %x, mer %x\n", intc->isr, intc->ier,		intc->iar, intc->mer);	R14(value);	printf ("Interrupt handler on %x line, r14 %x\n", irqs, value);#endif	struct irq_action *act = vecs;	while (irqs) {		if (irqs & 1) {#ifdef DEBUG_INT			printf			    ("Jumping to interrupt handler rutine addr %x,count %x,arg %x\n",			     act->handler, act->count, act->arg);#endif			act->handler (act->arg);			act->count++;			intc->iar = i;			return;		}		irqs >>= 1;		act++;		i <<= 1;	}#ifdef DEBUG_INT	printf ("Dump INTC reg, isr %x, ier %x, iar %x, mer %x\n", intc->isr,		intc->ier, intc->iar, intc->mer);	R14(value);	printf ("Interrupt handler on %x line, r14 %x\n", irqs, value);#endif}#endif#if defined(CONFIG_CMD_IRQ)#ifdef CFG_INTC_0int do_irqinfo (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){	int i;	struct irq_action *act = vecs;	puts ("\nInterrupt-Information:\n\n"	      "Nr  Routine   Arg       Count\n"	      "-----------------------------\n");	for (i = 0; i < CFG_INTC_0_NUM; i++) {		if (act->handler != (interrupt_handler_t*) def_hdlr) {			printf ("%02d  %08lx  %08lx  %d\n", i,				(int)act->handler, (int)act->arg, act->count);		}		act++;	}	puts ("\n");	return (0);}#elseint do_irqinfo (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){	puts ("Undefined interrupt controller\n");}#endif#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -