• AVR开发 Arduino方法(二) 中断子系统


      在了解中断子系统之前,首先要了解中断的概念。你正在看书,这时电话响了,你会怎么做呢?相信大多数人会这样:先标记看到的位置,接完电话回来后继续阅读。这就是一个现实生活中中断的例子,我们把电话响了成为中断源。Arduino UNO R3的主处理器ATMega328P拥有26个中断源,如下表所示:

    向量号

    程序地址

    中断源

    中断定义

    中断服务程序名称

    1

    0x0000

    RESET

    外部电平复位,上电复位,掉电检测复位,看门狗复位

    2

    0x0002

    INT0

    外部中断请求0

    INT0_vect

    3

    0x0004

    INT1

    外部中断请求1

    INT1_vect

    4

    0x0006

    PCINT0

    引脚电平变化中断请求0

    PCINT0_vect

    5

    0x0008

    PCINT1

    引脚电平变化中断请求1

    PCINT1_vect

    6

    0x000A

    PCINT2

    引脚电平变化中断请求2

    PCINT2_vect

    7

    0x000C

    WDT

    看门狗溢出中断

    WDT_vect

    8

    0x000E

    TIMER2 COMPA

    定时/计数器2比较匹配A

    TIMER2_COMPA_vect

    9

    0x0010

    TIMER2 COMPB

    定时/计数器2比较匹配B

    TIMER2_COMPB_vect

    10

    0x0012

    TIMER2 OVF

    定时/计数器2溢出

    TIMER2_OVF_vect

    11

    0x0014

    TIMER1 CAPT

    定时/计数器1事件捕捉

    TIMER1_CAPT_vect

    12

    0x0016

    TIMER1 COMPA

    定时/计数器1比较匹配A

    TIMER1_COMPA_vect

    13

    0x0018

    TIMER1 COMPB

    定时/计数器1比较匹配B

    TIMER1_COMPB_vect

    14

    0x001A

    TIMER1 OVF

    定时/计数器1溢出

    TIMER1_OVF_vect

    15

    0x001C

    TIMER0 COMPA

    定时/计数器0比较匹配A

    TIMER0_COMPA_vect

    16

    0x001E

    TIMER0 COMPB

    定时/计数器0比较匹配B

    TIMER0_COMPB_vect

    17

    0x0020

    TIMER0 OVF

    定时/计数器0溢出

    TIMER0_OVF_vect

    18

    0x0022

    SPI STC

    SPI串行传输结束

    SPI_STC_vect

    19

    0x0024

    USART RX

    USART接收结束

    USART_RX_vect

    20

    0x0026

    USART UDRE

    USART数据寄存器空

    USART_UDRE_vect

    21

    0x0028

    USART TX

    USART,发送结束

    USART_TX_vect

    22

    0x002A

    ADC

    模数转换结束

    ADC_vect

    23

    0x002C

    EE READY

    EEPROM准备好

    EE_READY_vect

    24

    0x002E

    ANALOG COMP

    模拟比较器

    ANALOG_COMP_vect

    25

    0x0030

    TWI

    两线串行接口

    TWI_vect

    26

    0x0032

    SPM READY

    保存程序存储器内容就绪

    SPM_ready_vect

      这里以外部中断0为例了解对中断子系统的编程,沿用上一章中用于数字输入示例的电路,这个示例使得按键在按下时LED的状态取反:

     1 // Interrupt.ino
     2 const byte ledPin = 13;
     3 const byte interruptPin = 2;
     4 volatile byte state = LOW;
     5 
     6 void setup() {
     7   pinMode(ledPin, OUTPUT);
     8   pinMode(interruptPin, INPUT_PULLUP);
     9   attachInterrupt(digitalPinToInterrupt(interruptPin), blink, CHANGE);
    10 }
    11 
    12 void loop() {
    13   digitalWrite(ledPin, state);
    14 }
    15 
    16 void blink() {
    17   state = !state;
    18 }

      与外部中断相关的Arduino库函数有:

     

      attachInterrupt(digitalPinToInterrupt(pin), ISR, mode):启用指定引脚的外部中断并连接到指定中断服务程序

      pin:指定外部中断的引脚

      ISR:指定中断服务程序的名称

      modeLOW(低电平触发中断),CHANG(逻辑电平变化触发中断),RISING(上升沿触发中断)或FALLING(下降沿触发中断)

      detachInterrupt(digitalPinToInterrupt(pin)):禁用指定中断

      pin:指定取消外部中断的引脚

      interrupts():开启总中断

      noInterrupts():禁用总中断

     

      ATMega328P的外部中断由2个相关寄存器控制,外部中断控制寄存器EICRA的结构如下图所示:

     

     

     

    INT1

    INT0

     

     

     

    ISC11

    ISC10

    ISC01

    ISC00

    ISCx[1:0]x = 0, 1位用于设置外部中断的触发方式,如下表所示:

    ISCx[1:0]

    x = 0, 1

    外部中断触发方式

    00

    低电平

    01

    逻辑电平变化

    10

    下降沿

    11

    上升沿

      外部中断屏蔽寄存器EIMSK用于设置是否屏蔽外部中断,它的结构如下图所示:

     

     

     

     

     

    INT1

    INT0

    若向其中某位写入1,则该位控制的外部中断启用;写入0则禁用。

      通过直接访问寄存器改写以上程序为:

     1 // Interrupt_reg.ino
     2 volatile byte state = LOW;
     3 
     4 void setup() {
     5   DDRB |= (1 << PB5);
     6   
     7   DDRD &= ~(1 << PD2);
     8   PORTD |= (1 << PD2);
     9   EICRA &= ~(1 << ISC01) & ~(1 << ISC00);
    10   EIMSK |= (1 << INT0);
    11   sei(); // 启用总中断
    12 }
    13 
    14 void loop() {
    15   if (state == HIGH) {
    16     PORTB |= (1 << PB5);
    17   } else {
    18     PORTB &= ~(1 << PB5);
    19   }
    20 }
    21 
    22 // 外部中断0中断处理函数
    23 ISR(INT0_vect) {
    24   state = !state;
    25 }
  • 相关阅读:
    spring boot 在windows下安装为service(转)
    win7安装Anaconda+TensorFlow+配置PyCharm(转)
    IDEA中Spring boot配置热部署无效问题解决方式(转)
    WEB后台--基于Token的WEB后台登录认证机制(转)
    selenium之使用chrome浏览器测试(附chromedriver与chrome的对应关系表)(转)
    开源巨献:Google最热门60款开源项目(转)
    反射获取一个方法中的参数名(不是类型)(转)
    ELK原理与介绍(转)
    Linux下Redis的安装和部署(转)
    webpack+ES6+less开发环境搭建(转)
  • 原文地址:https://www.cnblogs.com/lets-blu/p/7513709.html
Copyright © 2020-2023  润新知