Arduino 代码机制
生活随笔
收集整理的這篇文章主要介紹了
Arduino 代码机制
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
?? ? 新建一個Arduino程序??墒墙ㄍ昃陀魫灹?#xff0c;因為只看到了setup和loop函數,卻沒有基本的c函數。
void setup() {// put your setup code here, to run once: }void loop() {// put your main code here, to run repeatedly: } ? ?? ? 于是好奇心就來了,當然對于開源代碼來說這個沒有什么秘密。查一下源代碼就知道了。
? ?? ? 從配置文件來看,核心代碼在cores\arduino下。進入代碼目錄可以看到這里各個文件都是按照功能來命名的,所以很好辨認。很容易就能找到main.cpp,我們打開來看看具體內容:
int main(void) {init();#if defined(USBCON)USBDevice.attach(); #endifsetup();for (;;) {loop();if (serialEventRun) serialEventRun();}return 0; }
? ?? ? 看到我們熟悉的main函數了吧,同時看到main函數里在初始化時調用了setup函數,在for循環里調用了loop函數,所以這下大家明白了為什么在arduino中寫代碼的時候只看到setup和loop函數了吧,setup函數和loop函數已經預調用了。
? ?? ? 接下來再打開一個最簡單的例子Blink。
int led = 13;// the setup routine runs once when you press reset: void setup() { // initialize the digital pin as an output.pinMode(led, OUTPUT); }// the loop routine runs over and over again forever: void loop() {digitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(1000); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(1000); // wait for a second }
? ?? ? 這個代碼原理很簡單,把引腳13設置成輸出,然后使用for循環,在13腳交替輸出高低電平;這個邏輯很好理解。但是這其中又有疑問了;寫過avr c代碼的同學肯定都知道,一般對某個端口或者引腳操作都是使用DDRX,PORTX,PINX來操作的,為什么這里可以直接用數字來操作呢?
? ?? ? 接下來繼續分析一下pinMode這個函數,這個函數在cores\arduino\Wiring_digital.c文件里。
void pinMode(uint8_t pin, uint8_t mode) {uint8_t bit = digitalPinToBitMask(pin);uint8_t port = digitalPinToPort(pin);volatile uint8_t *reg, *out;if (port == NOT_A_PIN) return;// JWS: can I let the optimizer do this?reg = portModeRegister(port);out = portOutputRegister(port);………… }
? ?? ? 我只貼出了主要功能函數,其它部分代碼感興趣的可以自己去研究。這里可以看出主要函數是digitalPinToBitMask,digitalPinToPort,portModeRegister,portOutputRegister這幾個。本著打破砂鍋問到底的精神,我們繼續搜索這幾個函數的實現,這下可以看到是4個宏。
#define digitalPinToPort(P) ( pgm_read_byte( digital_pin_to_port_PGM + (P) ) ) #define digitalPinToBitMask(P) ( pgm_read_byte( digital_pin_to_bit_mask_PGM + (P) ) ) #define portInputRegister(P) ( (volatile uint8_t *)( pgm_read_word( port_to_input_PGM + (P))) ) #define portModeRegister(P) ( (volatile uint8_t *)( pgm_read_word( port_to_mode_PGM + (P))) )
?????? 本文的關鍵,不是pgm_read_byte這個函數,而是pgm_read_byte這個函數里面的參數:digital_pin_to_port_PGM,digital_pin_to_bit_mask_PGM,pgm_read_word( port_to_input_PGM,pgm_read_word( port_to_mode_PGM??纯催@四個參數的定義在哪里。
? ?? ? 對于芯片的定時器,pwm等基礎功能arduino都是按照這種方式實現的。就不再多說了。有了這些相信各位同學對arduino的使用會更加得心應手。
void setup() {// put your setup code here, to run once: }void loop() {// put your main code here, to run repeatedly: } ? ?? ? 于是好奇心就來了,當然對于開源代碼來說這個沒有什么秘密。查一下源代碼就知道了。
? ?? ? 從配置文件來看,核心代碼在cores\arduino下。進入代碼目錄可以看到這里各個文件都是按照功能來命名的,所以很好辨認。很容易就能找到main.cpp,我們打開來看看具體內容:
int main(void) {init();#if defined(USBCON)USBDevice.attach(); #endifsetup();for (;;) {loop();if (serialEventRun) serialEventRun();}return 0; }
? ?? ? 看到我們熟悉的main函數了吧,同時看到main函數里在初始化時調用了setup函數,在for循環里調用了loop函數,所以這下大家明白了為什么在arduino中寫代碼的時候只看到setup和loop函數了吧,setup函數和loop函數已經預調用了。
? ?? ? 接下來再打開一個最簡單的例子Blink。
int led = 13;// the setup routine runs once when you press reset: void setup() { // initialize the digital pin as an output.pinMode(led, OUTPUT); }// the loop routine runs over and over again forever: void loop() {digitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(1000); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(1000); // wait for a second }
? ?? ? 這個代碼原理很簡單,把引腳13設置成輸出,然后使用for循環,在13腳交替輸出高低電平;這個邏輯很好理解。但是這其中又有疑問了;寫過avr c代碼的同學肯定都知道,一般對某個端口或者引腳操作都是使用DDRX,PORTX,PINX來操作的,為什么這里可以直接用數字來操作呢?
? ?? ? 接下來繼續分析一下pinMode這個函數,這個函數在cores\arduino\Wiring_digital.c文件里。
void pinMode(uint8_t pin, uint8_t mode) {uint8_t bit = digitalPinToBitMask(pin);uint8_t port = digitalPinToPort(pin);volatile uint8_t *reg, *out;if (port == NOT_A_PIN) return;// JWS: can I let the optimizer do this?reg = portModeRegister(port);out = portOutputRegister(port);………… }
? ?? ? 我只貼出了主要功能函數,其它部分代碼感興趣的可以自己去研究。這里可以看出主要函數是digitalPinToBitMask,digitalPinToPort,portModeRegister,portOutputRegister這幾個。本著打破砂鍋問到底的精神,我們繼續搜索這幾個函數的實現,這下可以看到是4個宏。
#define digitalPinToPort(P) ( pgm_read_byte( digital_pin_to_port_PGM + (P) ) ) #define digitalPinToBitMask(P) ( pgm_read_byte( digital_pin_to_bit_mask_PGM + (P) ) ) #define portInputRegister(P) ( (volatile uint8_t *)( pgm_read_word( port_to_input_PGM + (P))) ) #define portModeRegister(P) ( (volatile uint8_t *)( pgm_read_word( port_to_mode_PGM + (P))) )
? ?? ? 對于pgm_read_byte這個函數說明如下:
?????? 讀取指令pgm_read_xxx宏定義其實就是一段包括了flash讀取指令的內聯匯編代碼。函數原型為:
?????? 本文的關鍵,不是pgm_read_byte這個函數,而是pgm_read_byte這個函數里面的參數:digital_pin_to_port_PGM,digital_pin_to_bit_mask_PGM,pgm_read_word( port_to_input_PGM,pgm_read_word( port_to_mode_PGM??纯催@四個參數的定義在哪里。
? ?? ? ?? 經過搜索發現在?? hardware\arduino\variants\leonardo\ Pins_arduino.h里,是不是很眼熟呀,是的,就是講配置文件的時候講過這個文件作用。
? ?? ? 對于芯片的定時器,pwm等基礎功能arduino都是按照這種方式實現的。就不再多說了。有了這些相信各位同學對arduino的使用會更加得心應手。
總結
以上是生活随笔為你收集整理的Arduino 代码机制的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: canvas 动画库 CreateJs
- 下一篇: #undef 标识符