ARM⑥——中断机制

一、中断

alt

2、中断处理过程

alt

3、中断实现

  1. 查看原理图

    K3--->SIM_DET --->XEINT10/KP_COL2/ALV_DBG6/GPX1_2

  2. 芯片手册

    GPX1_2 0x11000c20 [11:8] 0xF = WAKEUP_INT1[2] //引脚设置中断

    EXT_INT41_CON 0x11000e04 [10:8] 0x2 = Triggers Falling edge //中断下降沿

    EXT_INT41_MASK 0x11000f04 [2] 0x0 = Enables Interrupt //使能中断

    EXT_INT41_PEND 0x11000f44 [2] 0x1 = Interrupt Occurs //清除中断

​ EINT[10] 26(port) 58(id)

​ ICCICR_CPU0 0x10480000 [0] 1使能

​ ICCPMR_CPU0 0x10480004 [7:0] 屏蔽优先级,0xff 为所有都可访问

​ ICCIAR_CPU0 0x1048000C [9:0] 获取中断ID

​ ICCEOIR_CPU0 0x10480010 [9:0] 要结束的id

​ ICDDCR 0x10490000 [0] 1 = 分发使能

​ ICDISER1_CPU0 0x10490104 [26] 1 = Enables interrupt. port=26 使能中断

​ ICDICPR1_CPU0 0x10490284 [26] 1 = port = 26 清除中断标志

​ ICDIPTR14_CPU0 0x10490838 [23:16] 0x1 port = 26 发送到CPU0

​ 编程:

#define GPX1CON        (*(volatile unsigned int *)0x11000C20)
#define EXT_INT41CON   (*(volatile unsigned int *)0x11000E04)
#define EXT_INT41_MASK (*(volatile unsigned int *)0x11000F04)
#define EXT_INT41_PEND (*(volatile unsigned int *)0x11000F44)

#define ICCICR_CPU0    (*(volatile unsigned int *)0x10480000)
#define ICCPMR_CPU0    (*(volatile unsigned int *)0x10480004)
#define ICCIAR_CPU0    (*(volatile unsigned int *)0x1048000C)
#define ICCEOIR_CPU0   (*(volatile unsigned int *)0x10480010)
#define ICDDCR         (*(volatile unsigned int *)0x10490000)
#define ICDISER1_CPU0  (*(volatile unsigned int *)0x10490104)
#define ICDICPR1_CPU0  (*(volatile unsigned int *)0x10490284)
#define ICDIPTR14_CPU0 (*(volatile unsigned int *)0x10490838)

void interrupt_init()  //中断初始化
{
    //1. GPIO
    GPX1CON = GPX1CON|(0xf<<4); //设置中断引脚
    EXT_INT41CON = (EXT_INT41CON&(~(0x7<<4)))|(0x2<<4); //设置下降沿触发中断
    EXT_INT41_MASK = EXT_INT41_MASK&~(0x1<<1); //设置中断使能

    //GIC
    ICDISER1_CPU0 = ICDISER1_CPU0|(1<<25); //port=25设置中断使能
    ICDIPTR14_CPU0 = (ICDIPTR14_CPU0&(~(0xff<<8)))|(0x1<<8);//port=25中断分发给cpu0
    ICDDCR = ICDDCR|(0x1<<0); //分发使能
    ICCICR_CPU0 = ICCICR_CPU0|(0x1<<0); //接口使能
    ICCPMR_CPU0 = ICCPMR_CPU0|(0xff<<0); //设置优先级屏蔽
}

void do_irq()  //中断处理函数
{
    int irq_num = ICCIAR_CPU0 & 0x3ff; //获取中断ID
    switch (irq_num) {
        case 57:  //k2
            uart_putc('2');   
            ICDICPR1_CPU0 = ICDICPR1_CPU0|(1<<25); //port=25清中断标志
            EXT_INT41_PEND = EXT_INT41_PEND|(1<<1); //GPIO清中断标志
            break;
        default:
        	uart_putc('d'); 
        	break; 
    }
    ICCEOIR_CPU0 = (ICCEOIR_CPU0&(~(0x3ff<<0)))|irq_num; //结束中断
}