FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT

Subject:FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT

Date:   9-Nov-2011

By:       [email protected]

 

1. 按键电路原理图

FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第1张图片

 

2.中断控制器控制框图

FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第2张图片

 

3.按键端口寄存器设置

static void Key_Port_Init(void)

        //GPF0,2,3,4设置为外部中断口

       rGPFCON &=~((3<<0)|(3<<4)|(3<<6)|(3<<8)) ;

       rGPFCON |= ((2<<0)|(2<<4)|(2<<6)|(2<<8)) ;           //Set GPF0,2,3,4 as EINT0,2,3,4

      FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第3张图片

 

       //设置EINT0,2为下降沿触发

       rEXTINT0 &= ~(7<<0|7<<8);    

       rEXTINT0 |= (2<<0|2<<8); //EINT0,2 Falling edge triggered

      FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第4张图片

}

 

4.中断控制器寄存器设置

static void INT_Port_Init(void){

              //中断响应方式设置

              rINTMOD     &= ~(1<<0|1<<2);        //IRQ mode

            

             //中断响应优先级设置

              rPRIORITY   &= ~(1<<0);                //Prority does not rotate

           

            FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第5张图片

}

5.代码分析 KEY.c

#include "2440addr.h"

#include "2440lib.h"

#include "def.h"

#include "option.h"

#include "UART.h"

      

//按键端口寄存器设置

static void Key_Port_Init(void){

       rGPFCON &=~((3<<0)|(3<<4)|(3<<6)|(3<<8)) ;

       rGPFCON |= ((2<<0)|(2<<4)|(2<<6)|(2<<8)) ;           //Set GPF0,2,3,4 as EINT0,2,3,4

       rEXTINT0 &= ~(7<<0|7<<8);    

       rEXTINT0 |= (2<<0|2<<8); //EINT0,2 Falling edge triggered

}

 

//按键3/4扫描(轮询方式),如果按键未按下则返回NULL

static U8 Key_Scan( void ){

       if( !(rGPFDAT&(1<< 3)) ){          //按键3被按下

              FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第6张图片

               return 3 ;

       }

       else{

               if( (!rGPFDAT&(1<<4)) )    //按键4被按下    

                       return 4 ;

                else

                      return NULL;                //按键3/4均未被按下,返回NULL

       }

}

 

//按键中断处理程序

static void __irq Key_ISR(void){

       U32 r;   

        //进入临界区,屏蔽所有中断

       //void EnterCritical(U32 *pSave){

       //     __asm

       //     {

                      //读取当前CPSR并存入r0

                      //根据ATPCS汇编与C的参数传递规则,r0传递&r

        //            mrs  r1, CPSR       

        //            str   r1, [r0]

        //            orr   r1, r1, #NOINT

        //            msr  CPSR_cxsf, r1      

       //     }

       //}

       EnterCritical(&r);

 

       //判断中断源并执行相应操作

       if(rINTPND==BIT_EINT0)         //按键0按下

       {

               //清除中断信号

               //__inline void ClearPending(U32 bit)

              //{

              //     rSRCPND = bit;

              FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第7张图片

              //     rINTPND = bit;

              FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第8张图片

               //}

               ClearPending(BIT_EINT0);   //清除外部中断0信号  

               UART0_Printf( "Interrupt occured,Key1 is pressed!\n") ;    //输出按键按下信息

       }

       else

       {

               if(rINTPND==BIT_EINT2)  //按键2按下

               {

                      ClearPending(BIT_EINT2);   //清除外部中断2信号

                      UART0_Printf( "Interrupt occured,Key2 is pressed!\n") ; //输出按键按下信息

               }

       }

 

        //离开临界区

        //void ExitCritical(U32 *pSave){

       //     __asm

       //     {

        //            ldr   r1, [r0]           //读取原有保存的CPSR

        //            msr  CPSR_cxsf, r1 //恢复中断前的CPSR

       //     }

       //}

       ExitCritical(&r);

}

 

void Key_Scan_Test(void){

       U8 key;

       Key_Port_Init();     //按键端口初始化

       INT_Port_Init();    //中断控制器寄存器设置

 

        //#define pISR_EINT0          (*(unsigned *)(_ISR_STARTADDRESS+0x20))

       pISR_EINT0 = pISR_EINT2 = (U32)Key_ISR;   //指定中断处理程序地址    

      

        //使能外部中断0/2

        //#define  EnableIrq(bit)         rINTMSK &= ~(bit)

       EnableIrq(BIT_EINT0|BIT_EINT2);   

 

       while(UART0_GetKey() != ESC_KEY)

       {

               if((key = Key_Scan()) != NULL )         //按键3/4被按下

               {

                      UART0_Printf( "Key%d is pressed!\n", key ) ;

              

                      while((!(rGPFDAT & (1<<3)) )|(!(rGPFDAT & (1<<4)) ));       //wait released

              

                      UART0_Printf( "Key%d is released!\n", key ) ;

                }

         }

 

        //屏蔽外部中断0/2

        //#define  DisableIrq(bit)        rINTMSK |= (bit)

        DisableIrq(BIT_EINT0|BIT_EINT2);  

}

 

6.  测试程序及结果

#include "UART.h"

#include "KEY.h"

 

int Main(void)

{

       UART0_Port_Init(115200);    //UART0端口初始化

       Key_Scan_Test();                 //按键扫描

       while(1){

               ;                   

       }

       return 0;

}

 

FL2440无操作系统应用程序编写测试007——KEY_INTERRUPT_第9张图片    

 

 

你可能感兴趣的:(c,汇编,测试,null,代码分析)