#include <util/atomic.h> // 用于 demo 4: ATOMIC_BLOCK macro.
#define LEDPIN 6
#define INTERRUPTPIN 2
volatile byte ledStatus = LOW; //此变量被中断使用,字节型 8 bit 定义为挥发性变量
volatile int bankBalance = 0; //用于 demo3 和 demo4,处理变量超过 8 bit
void setup() {
Serial.begin(9600);
pinMode(LEDPIN, OUTPUT);
pinMode(INTERRUPTPIN, INPUT_PULLUP);
digitalWrite(LEDPIN,LOW);
// demo 1 : 基本中断使用方法 - falling:拉低
attachInterrupt(digitalPinToInterrupt(INTERRUPTPIN),blink,FALLING);
// demo 2: 中断防止按钮抖动
// attachInterrupt(digitalPinToInterrupt(INTERRUPTPIN),blinkWithDebounce,FALLING);
// demo 3 , demo 4 中断使用的变量长度超过了MCU的总线宽度
// payDay 16 bits > Atmega328P 8 Bits
attachInterrupt(digitalPinToInterrupt(INTERRUPTPIN),payDay,FALLING);
}
void loop() {
digitalWrite(LEDPIN,ledStatus);
// demo 3: 使用 noInterrupts 和 interrupts
noInterrupts();// 强制关闭中断
Serial.println(bankBalance);
interrupts();// 强制开启中断
/*
// demo 4: 使用atomic block 运行时中断关闭
ATOMIC_BLOCK(ATOMIC_RESTORESTATE) {
Serial.println(bankBalance);
}
*/
}
/*
中断的函数 没有 输入也没有 输出
里面的内容越少越好,最好简化到改一个byte的内容
*/
void blink() {
ledStatus = !ledStatus; //此变量被中断使用,定义为挥发性变量
}
long debouncing_time = 15; //Debouncing Time in Milliseconds
volatile unsigned long last_micros;
void blinkWithDebounce() {
if((long)(micros() - last_micros) >= debouncing_time * 1000) {
ledStatus = !ledStatus; //此变量被中断使用,定义为挥发性变量
last_micros = micros();
}
}
void payDay() {
//中断中的赋值类型超过了1个字节
//超过了Atmega328P的总线8位比特
//在其他程序段的使用中,需要关闭中断,或者使用atomic
bankBalance=bankBalance+1000;
}