var_intr.c
来自「eCos操作系统源码」· C语言 代码 · 共 496 行 · 第 1/2 页
C
496 行
//==========================================================================//// var_intr.c//// PowerPC variant interrupt handlers////==========================================================================//####ECOSGPLCOPYRIGHTBEGIN####// -------------------------------------------// This file is part of eCos, the Embedded Configurable Operating System.// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.// Copyright (C) 2002, 2003, 2004 Gary Thomas//// eCos 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 or (at your option) any later version.//// eCos 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 eCos; if not, write to the Free Software Foundation, Inc.,// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.//// As a special exception, if other files instantiate templates or use macros// or inline functions from this file, or you compile this file and link it// with other works to produce a work based on this file, this file does not// by itself cause the resulting work to be covered by the GNU General Public// License. However the source code for this file must still be made available// in accordance with section (3) of the GNU General Public License.//// This exception does not invalidate any other reasons why a work based on// this file might be covered by the GNU General Public License.//// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.// at http://sources.redhat.com/ecos/ecos-license/// -------------------------------------------//####ECOSGPLCOPYRIGHTEND####//==========================================================================//#####DESCRIPTIONBEGIN####//// Author(s): jskov// Contributors: jskov, gthomas// Date: 2000-02-11// Purpose: PowerPC variant interrupt handlers// Description: This file contains code to handle interrupt related issues// on the PowerPC variant.////####DESCRIPTIONEND####////==========================================================================#include <pkgconf/hal.h>#define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS#include <cyg/hal/ppc_regs.h>#include <cyg/hal/hal_intr.h>#include <cyg/infra/cyg_type.h>extern void hal_platform_IRQ_init(void);//// Sadly, the IBM PPC40x family of devices are only related by number// and not always by functionality. In particular, the 403 has a// completely different interrupt controller than the 405. For now// at least, these differences are controlled by CDL within this file.//#if defined(CYGHWR_HAL_POWERPC_PPC4XX_403)static cyg_uint32 exier_mask[] = { 0x00000000, // Unused 0x00000000, // Unused 0x80000000, // CYGNUM_HAL_INTERRUPT_CRITICAL 2 0x08000000, // CYGNUM_HAL_INTERRUPT_SERIAL_RCV 3 0x04000000, // CYGNUM_HAL_INTERRUPT_SERIAL_XMT 4 0x02000000, // CYGNUM_HAL_INTERRUPT_JTAG_RCV 5 0x01000000, // CYGNUM_HAL_INTERRUPT_JTAG_XMT 6 0x00800000, // CYGNUM_HAL_INTERRUPT_DMA0 7 0x00400000, // CYGNUM_HAL_INTERRUPT_DMA1 8 0x00200000, // CYGNUM_HAL_INTERRUPT_DMA2 9 0x00100000, // CYGNUM_HAL_INTERRUPT_DMA3 10 0x00000010, // CYGNUM_HAL_INTERRUPT_EXT0 11 0x00000008, // CYGNUM_HAL_INTERRUPT_EXT1 12 0x00000004, // CYGNUM_HAL_INTERRUPT_EXT2 13 0x00000002, // CYGNUM_HAL_INTERRUPT_EXT3 14 0x00000001, // CYGNUM_HAL_INTERRUPT_EXT4 15};// This table inverts bit number to signal numbercyg_uint32 EXISR_TAB[] = { CYGNUM_HAL_INTERRUPT_CRITICAL, // 0x80000000 0x00000000, // 0x40000000 0x00000000, // 0x20000000 0x00000000, // 0x10000000 CYGNUM_HAL_INTERRUPT_SERIAL_RCV, // 0x08000000 CYGNUM_HAL_INTERRUPT_SERIAL_XMT, // 0x04000000 CYGNUM_HAL_INTERRUPT_JTAG_RCV, // 0x02000000 CYGNUM_HAL_INTERRUPT_JTAG_XMT, // 0x01000000 CYGNUM_HAL_INTERRUPT_DMA0, // 0x00800000 CYGNUM_HAL_INTERRUPT_DMA1, // 0x00400000 CYGNUM_HAL_INTERRUPT_DMA2, // 0x00200000 CYGNUM_HAL_INTERRUPT_DMA3, // 0x00100000 0x00000000, // 0x00080000 0x00000000, // 0x00040000 0x00000000, // 0x00020000 0x00000000, // 0x00010000 0x00000000, // 0x00008000 0x00000000, // 0x00004000 0x00000000, // 0x00002000 0x00000000, // 0x00001000 0x00000000, // 0x00000800 0x00000000, // 0x00000400 0x00000000, // 0x00000200 0x00000000, // 0x00000100 0x00000000, // 0x00000080 0x00000000, // 0x00000040 0x00000000, // 0x00000020 CYGNUM_HAL_INTERRUPT_EXT0, // 0x00000010 CYGNUM_HAL_INTERRUPT_EXT1, // 0x00000008 CYGNUM_HAL_INTERRUPT_EXT2, // 0x00000004 CYGNUM_HAL_INTERRUPT_EXT3, // 0x00000002 CYGNUM_HAL_INTERRUPT_EXT4 // 0x00000001};cyg_uint32 _hold_tcr = 0; // Shadow of hardware registerexternC voidhal_variant_IRQ_init(void){ cyg_uint32 iocr; // Ensure all interrupts masked (disabled) & cleared CYGARC_MTDCR(DCR_EXIER, 0); CYGARC_MTDCR(DCR_EXISR, 0xFFFFFFFF); // Configure all external interrupts to be level/low CYGARC_MFDCR(DCR_IOCR, iocr); iocr &= ~0xFFC00000; CYGARC_MTDCR(DCR_IOCR, iocr); // Disable timers CYGARC_MTSPR(SPR_TCR, 0); // Let the platform do any overrides hal_platform_IRQ_init();}externC void hal_ppc40x_interrupt_mask(int vector){ cyg_uint32 exier, tcr; switch (vector) { case CYGNUM_HAL_INTERRUPT_CRITICAL: case CYGNUM_HAL_INTERRUPT_SERIAL_RCV: case CYGNUM_HAL_INTERRUPT_SERIAL_XMT: case CYGNUM_HAL_INTERRUPT_JTAG_RCV: case CYGNUM_HAL_INTERRUPT_JTAG_XMT: case CYGNUM_HAL_INTERRUPT_DMA0: case CYGNUM_HAL_INTERRUPT_DMA1: case CYGNUM_HAL_INTERRUPT_DMA2: case CYGNUM_HAL_INTERRUPT_DMA3: case CYGNUM_HAL_INTERRUPT_EXT0: case CYGNUM_HAL_INTERRUPT_EXT1: case CYGNUM_HAL_INTERRUPT_EXT2: case CYGNUM_HAL_INTERRUPT_EXT3: case CYGNUM_HAL_INTERRUPT_EXT4: CYGARC_MFDCR(DCR_EXIER, exier); exier &= ~exier_mask[vector]; CYGARC_MTDCR(DCR_EXIER, exier); break; case CYGNUM_HAL_INTERRUPT_VAR_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr &= ~TCR_PIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; case CYGNUM_HAL_INTERRUPT_FIXED_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr &= ~TCR_FIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; case CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr &= ~TCR_WIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; default: break; }}externC void hal_ppc40x_interrupt_unmask(int vector){ cyg_uint32 exier, tcr; switch (vector) { case CYGNUM_HAL_INTERRUPT_CRITICAL: case CYGNUM_HAL_INTERRUPT_SERIAL_RCV: case CYGNUM_HAL_INTERRUPT_SERIAL_XMT: case CYGNUM_HAL_INTERRUPT_JTAG_RCV: case CYGNUM_HAL_INTERRUPT_JTAG_XMT: case CYGNUM_HAL_INTERRUPT_DMA0: case CYGNUM_HAL_INTERRUPT_DMA1: case CYGNUM_HAL_INTERRUPT_DMA2: case CYGNUM_HAL_INTERRUPT_DMA3: case CYGNUM_HAL_INTERRUPT_EXT0: case CYGNUM_HAL_INTERRUPT_EXT1: case CYGNUM_HAL_INTERRUPT_EXT2: case CYGNUM_HAL_INTERRUPT_EXT3: case CYGNUM_HAL_INTERRUPT_EXT4: CYGARC_MFDCR(DCR_EXIER, exier); exier |= exier_mask[vector]; CYGARC_MTDCR(DCR_EXIER, exier); break; case CYGNUM_HAL_INTERRUPT_VAR_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr |= TCR_PIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; case CYGNUM_HAL_INTERRUPT_FIXED_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr |= TCR_FIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; case CYGNUM_HAL_INTERRUPT_WATCHDOG_TIMER: CYGARC_MFSPR(SPR_TCR, tcr); tcr = _hold_tcr; tcr |= TCR_WIE; CYGARC_MTSPR(SPR_TCR, tcr); _hold_tcr = tcr; break; default: break; }}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?