ESP3 + ESP-IDF | 串口1 - 简单的串口回环测试
文章目錄
- 一、前言
- 二、VSCODE + ESP-IDF
- 2.1、快速創建項目
- 2.2、選擇串口通道,ESP芯片型號
- 三、代碼
- 3.1、頭文件
- 3.2、全局變量
- 3.3、app_main( )函數
- 3.4、實驗代碼
- 四、相關API
- 4.1、uart_param_config( )
- 4.2、uart_set_pin( )
- 4.3、uart_driver_install( )
- 4.4、uart_write_bytes( )
- 4.5、uart_read_bytes( )
一、前言
測試串口外設最省事的方法是串口回環測試,因為串口回環測試不需要外部串口工具。本實驗使用GPIO23作為UART1_TX,GPIO18作為UART1_RX,然后在電路上只需用一根杜邦線將GPIO23與GPIO18連接起來即可。
ESP-IDF打印的信息:
從Monitor反饋的logo可以看到,串口1接收到字符串“hello,world”,然后通過函數strlen( )獲取收到的字符串的長度(長度是11)。
串口0(UART0)一般被用于下載與監控程序,所以最好不要用于開發功能。
二、VSCODE + ESP-IDF
2.1、快速創建項目
按照第一章節的方式創建一個sample_project的模版。ESP32 + ESP-IDF |GPIO 01 - 驅動外部兩個LED燈,以每300ms的時間間隔閃爍
2.2、選擇串口通道,ESP芯片型號
還是按照第一章節的方式來選擇串口通道與ESP芯片信號
三、代碼
官方文檔:https://docs.espressif.com/projects/esp-idf/zh_CN/latest/esp32/api-reference/peripherals/uart.html
3.1、頭文件
使用ESP32的串口外設時,需要包含頭文件“driver/uart.h”.
3.2、全局變量
- 數組msg_test[] :其實就是一個字符串,這個數組將被uart1發送出去,然后被uart1接收回來(回環測試)。
- 數組buffer[UART1_RX_BUF_SIZE]:用于暫時存儲uart1接收回來的字符串。
- 結構體uart1_config:用于初始化uart1的功能(波特率,數據位的個數等)。
3.3、app_main( )函數
3.4、實驗代碼
#include <stdio.h> #include <string.h> #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "driver/gpio.h" #include "driver/uart.h" #include "esp_log.h" #include "esp_err.h"#define UART1_TX_BUF_SIZE 256 /* 256個字節 */ #define UART1_RX_BUF_SIZE 256 /* 256個字節 */static const char *TAG = "UART section0"; static uint8_t s_led_state = 0;static char msg_test[] = "hello,world"; /* 測試使用的字符串 */ static char buffer[UART1_RX_BUF_SIZE]; /* 暫時存儲從串口接收到的字符串 *//* 串口1的配置 */ const uart_config_t uart1_config = {.baud_rate = 115200, /* 通訊波特率 */.data_bits = UART_DATA_8_BITS, /* 每一個數據是8位 */.parity = UART_PARITY_DISABLE, /* 關閉奇偶校驗 */.stop_bits = UART_STOP_BITS_1, /* 停止位是1位 */.flow_ctrl = UART_HW_FLOWCTRL_DISABLE, /* 軟件控流 */.source_clk = UART_SCLK_APB, /* APB時鐘 */ };void app_main(void) {ESP_LOGI(TAG, "Example configured to uart communication");/* 復位GPIO的狀態 */gpio_reset_pin(26);/* 設置GPIO26為輸出模式 */gpio_set_direction(26,GPIO_MODE_OUTPUT);/* 設置串口1的參數 */ESP_ERROR_CHECK(uart_param_config(UART_NUM_1,&uart1_config));/* 設置串口的gpio口,esp32支持gpio口動態設置,這一次先使用默認的串口gpio */ESP_ERROR_CHECK(uart_set_pin(UART_NUM_1,GPIO_NUM_23,GPIO_NUM_18,UART_PIN_NO_CHANGE,UART_PIN_NO_CHANGE));/* 啟動串口1 */ESP_ERROR_CHECK(uart_driver_install(UART_NUM_1, /* 串口1 */UART1_TX_BUF_SIZE, /* 發送FIFO的大小 */UART1_RX_BUF_SIZE, /* 接受FIFO的大小 */0, /* 不使用queue */NULL, /* 因為不使用queue,所以NULL */0) /* 不分配中斷標志 */ ); while(1){uart_write_bytes(UART_NUM_1,msg_test,strlen(msg_test)); /* 將字符串“hello,world"放入串口1的TX_FIFO */s_led_state = !s_led_state; /* 將電平取反 */vTaskDelay(500 / portTICK_PERIOD_MS); /* 延時300ms */gpio_set_level(26,s_led_state); /* gpio輸出電平 */int len = uart_read_bytes(UART_NUM_1,buffer,(UART1_RX_BUF_SIZE - 1), 20 / portTICK_PERIOD_MS); /* 從串口1的RX_FIFO獲取字符串 *//* 如果讀到包的話 */if(len){buffer[len] = '\0'; /* 在結尾加入字符'\0', */ESP_LOGI(TAG,"Recv str -> %s , and the length is:%d",buffer,strlen(buffer)); /* 打印logo */ESP_LOGI(TAG,"The size of buffer is %d,and ready to clear this buffer.",sizeof(buffer)); /* 打印logo */memset(buffer,0,sizeof(buffer)); /* 清空內存,等待下一次的串口保文。 */}} }四、相關API
4.1、uart_param_config( )
- uart_num : 很簡單,就是uart的端口號。這一次實驗使用uart1,對應的宏是UART_NUM_1。
- uart_config
從上圖可以看到,結構體uart_config_t里的成員變量基本都是枚舉類型,除了成員變量baud_rate與成員變量use_ref_tick。
4.2、uart_set_pin( )
有意思的是,esp32支持通過軟件來設置uart的硬件引腳,真的非常方便!!
4.3、uart_driver_install( )
剛開始沒有注意到筆記:Rx_buffer_size應該大于UART_FIFO_LEN。Tx_buffer_size應該為零或者大于UART_FIFO_LEN。導致程序編譯不成功!!!
從上圖可以看到,Rx_buffer_size應該大于128字節,Tx_buffer_size應該為零或者大于128字節。
4.4、uart_write_bytes( )
如果tx_buffer_size設置為0,那么uart_write_bytes將會“阻塞”程序(就是程序會卡在這個函數,直到所有數據都發送出去)。不管怎樣,在我看來都不應該將tx_buffer_size設置為0而影響整個程序的實時性,畢竟ESP-IDF框架是基于freertos實時系統。
4.5、uart_read_bytes( )
函數很簡單,值得注意的是uart_read_bytes( )接收完字符串后,最好在字符串的最后加入字符‘\0’,這是一個很好的C代碼習慣(可以避免strlen等C標準庫的一些bug)。詳細可以閱讀《C和指針》這本書。
還有另外一個好習慣就是使用memset( )函數清除整個buffer內存,避免影響下一次字符串讀取與判斷。
總結
以上是生活随笔為你收集整理的ESP3 + ESP-IDF | 串口1 - 简单的串口回环测试的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Liunx配置网络到nginx环境搭建步
- 下一篇: linux 内核 核心代码,8分钟掌握L