在Arduino中使用digitalWrite来设置引脚的高低电平其实并不只是做了改变引脚寄存器数据这一件事,所以它的效率并不高,在需要高频输出的场景下就会出现瓶颈。
最近我在写大型LED矩阵屏驱动板的时候就遇到了这样的情况,一轮loop的速度太慢以至于watch dog以为程序死循环了而导致重启。后来我查来查去发现可以通过直接改变寄存器的数据来改变引脚的输出电平,而且官方头文件里其实也有对应的宏可以进行相关操作,但我怎么试都没成功,最后在一个官方demo里发现了一个函数,效率也同样不错,所以抄出来记录一下
void ICACHE_RAM_ATTR __digitalWrite(uint8_t pin, uint8_t val) {
if(pin < 16){
if(val) GPOS = (1 << pin);
else GPOC = (1 << pin);
} else if(pin == 16){
if(val) GP16O |= 1;
else GP16O &= ~1;
}
}
只要调用`__digitalWrite(gpio引脚,0或1)` 就可以了。
==========更新===========
把这个函数写成宏可以更进一步提高效率
//pin最好为常数,以便编译器优化掉判断
#define __digitalWrite(pin,val)\
if(pin < 16){\
if(val) GPOS = (1 << pin);\
else GPOC = (1 << pin);\
} else if(pin == 16){\
if(val) GP16O |= 1;\
else GP16O &= ~1;\
}