📄 int.c
字号:
/* *---------------------------------------------------------------------- * T-Kernel * * Copyright (C) 2004 by Ken Sakamura. All rights reserved. * T-Kernel is distributed under the T-License. *---------------------------------------------------------------------- * * Version: 1.01.00 * Released by T-Engine Forum(http://www.t-engine.org) at 2004/6/28. * *---------------------------------------------------------------------- *//* * @(#)int.c (libtk/VR4131) * * Interrupt controller */#include <basic.h>#include <tk/syslib.h>#include <tk/sysdef.h>/* * Disable/enable interrupt */IMPORT UINT _disint( void );IMPORT void _enaint( UINT imask );#define _DI(imask) ( imask = _disint() )#define _EI(imask) ( _enaint(imask) )/* * Set interrupt mode * Sets the interrupt specified in intvec to the mode * specified in mode. * * mode := (IM_LEVEL || IM_EDGE) | (IM_HI || IM_LOW) * * The only intvec which can be set is GPIO interrupt. * * The hold/through select register is set as follows. * For edge trigger: hold * For level trigger through */EXPORT void SetIntMode( INTVEC intvec, UINT mode ){ _UH *typ, *hts, *als; UW imask, bit; W i; if ( (i = intvec - IV_GPIO(15)) >= 0 ) { typ = (_UH*)GIUINTTYPL; hts = (_UH*)GIUINTHTSELL; als = (_UH*)GIUINTALSELL; } else if ( (i = intvec - IV_GPIO(31)) >= 0 ) { typ = (_UH*)GIUINTTYPH; hts = (_UH*)GIUINTHTSELH; als = (_UH*)GIUINTALSELH; } else return; bit = 0x8000 >> i; _DI(imask); if ( (mode & IM_EDGE) != 0 ) { *typ |= bit; *hts |= bit; } else { *typ &= ~bit; *hts &= ~bit; } if ( (mode & IM_HI) != 0 ) { *als |= bit; } else { *als &= ~bit; } _EI(imask);}/* * Interrupt enabled * Enables the interrupt specified in intvec. * * IRQ and GPIO interrupt can be specified in intvec. * FPGA interrupt cannot be specified; a direct FPGA register * operation is required. */EXPORT void EnableInt( INTVEC intvec ){ _UH *msk; UW imask; W i; if ( (i = intvec - IV_GPIO(15)) >= 0 ) { msk = (_UH*)GIUINTENL; } else if ( (i = intvec - IV_GPIO(31)) >= 0 ) { msk = (_UH*)GIUINTENH; } else if ( (i = intvec - IV_IRQ(15)) >= 0 ) { msk = (_UH*)MSYSINT1REG; } else if ( (i = intvec - IV_IRQ(31)) >= 0 ) { msk = (_UH*)MSYSINT2REG; } else return; _DI(imask); *msk |= 0x8000 >> i; _EI(imask);}/* * Interrupt disabled * Disables the interrupt specified in intvec. * * IRQ and GPIO can be specified in intvec. * FPGA interrupt cannot be specified; a direct FPGA register * operation is required. */EXPORT void DisableInt( INTVEC intvec ){ _UH *msk; UW imask; W i; if ( (i = intvec - IV_GPIO(15)) >= 0 ) { msk = (_UH*)GIUINTENL; } else if ( (i = intvec - IV_GPIO(31)) >= 0 ) { msk = (_UH*)GIUINTENH; } else if ( (i = intvec - IV_IRQ(15)) >= 0 ) { msk = (_UH*)MSYSINT1REG; } else if ( (i = intvec - IV_IRQ(31)) >= 0 ) { msk = (_UH*)MSYSINT2REG; } else return; _DI(imask); *msk &= ~(0x8000 >> i); _EI(imask);}/* * Clear interrupt request * Clears the intvec interrupt request. * Only GPIO can be specified as intvec. * * Valid only for edge trigger. * For edge trigger, the interrupt must be cleared with an * interrupt handler. */EXPORT void ClearInt( INTVEC intvec ){ _UH *stat; W i; if ( (i = intvec - IV_GPIO(15)) >= 0 ) { stat = (_UH*)GIUINTSTATL; } else if ( (i = intvec - IV_GPIO(31)) >= 0 ) { stat = (_UH*)GIUINTSTATH; } else return; *stat = 0x8000 >> i;}/* * Check for interrupt requests * Checks for intvec interrupt requests. * If an interrupt request is found, returns TRUE (other than 0). */EXPORT BOOL CheckInt( INTVEC intvec ){ _UH *stat; W i; if ( (i = intvec - IV_FPGA(31)) >= 0 ) { return *(_UW*)INT_PEND & (0x80000000 >> i); } else if ( (i = intvec - IV_GPIO(15)) >= 0 ) { stat = (_UH*)GIUINTSTATL; } else if ( (i = intvec - IV_GPIO(31)) >= 0 ) { stat = (_UH*)GIUINTSTATH; } else if ( (i = intvec - IV_IRQ(15)) >= 0 ) { stat = (_UH*)SYSINT1REG; } else if ( (i = intvec - IV_IRQ(31)) >= 0 ) { stat = (_UH*)SYSINT2REG; } else return FALSE; return *stat & (0x8000 >> i);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -