第二章 GPIO操作實(shí)驗
本章主要內容為通過(guò)使用RT-Thread中的PIN設備接口函數對開(kāi)發(fā)板上板載的LED燈進(jìn)行操作。主要實(shí)現功能為點(diǎn)亮LED燈讓其規律閃爍。
1.1 硬件介紹
在IOT開(kāi)發(fā)板上已經(jīng)為我們集成焊接了一個(gè)三色的RGB燈,具體位置如下圖所示:
RGB燈圖示
在官方給的原理圖資料中我們也可以找到LED模塊的電路圖。如電路圖所示,我們可以發(fā)現3個(gè)LED燈外接了一個(gè)3V的直流電源接口,后面的引腳接入到了單片機的引腳,所以我只需要將單片機的引腳輸出改為低電平輸出即可點(diǎn)亮LED燈。
LED燈電路原理圖
LED燈單片機引腳圖
1.2 軟件設計
1.2.1 單色燈點(diǎn)亮測試
a) 功能實(shí)現思路分析
從電路原理圖中我們可以發(fā)現,LED_G對應了單片機的39號引腳(GPIO PE8)。若不想查看原理圖,也可以查看官方給出的IO引腳分配表。分配表中也給出了LED_G對應的GPIO引腳為PE8。
所以我們只需要利用RT-Thread為我們提供的通用GPIO驅動(dòng)來(lái)將PE8設置為低電平輸出即可點(diǎn)亮LED燈。
我們需要使用的API函數主要有以下兩個(gè),功能分別為設置引腳模式與設置引腳電平。在stuido創(chuàng )建的工程下,有一個(gè)drivers的目錄,此目錄是RT-Thread為用戶(hù)封裝好的一些常用驅動(dòng)庫。此章節需要使用的為gpio驅動(dòng)庫。關(guān)于驅動(dòng)庫的使用方式以及介紹我們可以前往RT-Thread官方文檔中進(jìn)行查看,此部分內容為設備和驅動(dòng)下的PIN設備。
在基于傳統HAL庫開(kāi)發(fā)中,我們總的開(kāi)發(fā)流程可總結為以下步驟:1.對GPIO口進(jìn)行配置;2.GPIO口初始化;3.設置GPIO口工作模式;4.設置GPIO口引腳電平狀態(tài)。使用RT-Thread進(jìn)行開(kāi)發(fā)也可總結為以下幾個(gè)步驟:1.定義引腳編號映射;2.設置引腳工作模式;3.設置引腳電平狀態(tài)?;诖肆鞒涛覀兛梢詫浖M(jìn)行設計??偭鞒虉D如圖所示:
軟件設計流程圖
在RT-Thread中獲取引腳編號的方式有三種,一種是利用API函數的方式、一種是利用宏定義的方式還有一種是查看驅動(dòng)文件來(lái)獲取引腳編號。此歷程采用查看驅動(dòng)文件來(lái)獲取引腳編號,其他方式的使用場(chǎng)景請自行前往官方文檔查看。
查看驅動(dòng)文件來(lái)獲取引腳編號具體實(shí)現步驟如下:
1. 打開(kāi)drivers目錄下的drv_gpio.c文件。打開(kāi)過(guò)后我們可以看到已經(jīng)給我們定義了非常多的相關(guān)宏定義以及結構體
2. 找到static const struct pin_index pins[] 結構體,此結構體中為我們設置了單片機與操作系統引腳編號的映射關(guān)系。
3. 找尋自己需要的端口號。以__STM32_PIN(72, E, 8) 為例,E為GPIO口名稱(chēng),即GPIOE。8為引腳號,即PE8。則72就是對應的引腳編號。所以PE8端口在RT-Thread中對應的引腳編號為72。我們在使用過(guò)程中只需要定義一個(gè)宏定義值為72即可對應單片機的PE8端口。
在我們得到了引腳編號后,即可進(jìn)行代碼編寫(xiě),調用想用的API函數進(jìn)行GPIO口的工作模式設定以及電平工作狀態(tài)設定。
b) 設置引腳模式
引腳在使用前需要先設置好其工作模式是輸入模式還是輸出模式,需要調用的API函數接口如下:
voidrt_pin_mode(rt_base_tpin,rt_base_tmode);
具體參數詳解如下表:
參數
描述
pin
引腳編號
mode
引腳工作模式
引腳編號即為我們在上一步中在驅動(dòng)文件中查詢(xún)到的引腳編號,比如PE8為72,我們只需要傳入72即可。引腳的工作模式目前RT-Thread支持的宏定義為5中宏定義。具體解釋如下表所示:
參數
描述
define PIN_MODE_OUTPUT 0x00
/*輸出*/
define PIN_MODE_INPUT 0x01
/*輸入*/
define PIN_MODE_INPUT_PULLUP 0x02
/*上拉輸入*/
define PIN_MODE_INPUT_PULLDOWN 0x03
/*下拉輸入*/
define PIN_MODE_OUTPUT_OD 0x04
/*開(kāi)漏輸出*/
所以參數mode我們只需要傳入定義好的宏定義即可。
c) 設置引腳電平
上一步我們設置完了引腳的工作模式為輸出模式,這一步我們需要對引腳的電平進(jìn)行設置,從9.1節中我們可以得到只需要將GPIO引腳設置為低電平即可點(diǎn)亮LED燈。所以我們只需要利用API函數將其設置成為低電平即可完成此功能。
需要使用的API函數接口如下:
voidrt_pin_write(rt_base_tpin,rt_base_tvalue);
參數講解如下:
參數
描述
pin
引腳編號
value
電平邏輯值,可取 2 種宏定義值之一:PIN_LOW 低電平,PIN_HIGH 高電平
d) 具體代碼實(shí)現
在上一小節中,我們已經(jīng)將從硬件到使用API函數接口去實(shí)現功能做了完整的分析。下面我們將開(kāi)始著(zhù)手編寫(xiě)代碼,進(jìn)行實(shí)際操作。
具體實(shí)現步驟如下:
1. 打開(kāi)我們新建的工程,新建一個(gè)led的源文件。
2. 在源文件中導入需要的頭文件include,include;定義led線(xiàn)程句柄、定義相關(guān)宏定義的值;
3. 編寫(xiě)led線(xiàn)程入口函數,入口函數里實(shí)現在上一小節中梳理的引腳設置模式。
4. 編譯、下載運行。
/*導入頭文件*/includeinclude/*定義線(xiàn)程句柄與GPIO引腳宏定義*/staticrt_thread_tLEDG_Thread = RT_NULL;defineLEDG 72defineTHREAD_PRIORITY 25defineTHREAD_STACK_SIZE 512defineTHREAD_TIMESLICE 5/*編寫(xiě)入口函數*/staticvoidLEDG_Thread_Entry(void*parmas){/*設置引腳模式*/rt_pin_mode(LEDG, PIN_MODE_OUTPUT);/*設置引腳電平狀態(tài)*/rt_pin_write(LEDG, PIN_LOW);
rt_kprintf("ledg on.n");
}intled_G(void){/*創(chuàng )建線(xiàn)程*/LEDG_Thread=rt_thread_create("led_thread",LEDG_Thread_Entry,RT_NULL,THREAD_STACK_SIZE,THREAD_PRIORITY,THREAD_TIMESLICE);if(LEDG_Thread == RT_NULL)
{
rt_kprintf("create led thread failed.n");return-1;
}/*啟動(dòng)線(xiàn)程*/rt_thread_startup(LEDG_Thread);return0;
}/* 導出到 msh 命令列表中 */MSH_CMD_EXPORT(led_G, led_G);
5. 打開(kāi)終端命令行執行led_G命令,查看結果。我們可以發(fā)現在終端控制臺中會(huì )打印一段話(huà)ledg on.且在開(kāi)發(fā)板上會(huì )發(fā)現LED燈部分綠色的燈亮起。如下圖所示:
實(shí)驗結果圖
1.2.2 呼吸燈應用
a) 功能實(shí)現思路分析
我們在上一小節中對開(kāi)發(fā)板中單色RGB燈進(jìn)行了點(diǎn)亮操作,從電路圖中我們可以發(fā)現還有另外兩只RGB燈可供使用。在此小節我們將實(shí)現三色燈交替閃爍的功能。
對于電路原理圖以及單片機引腳接口都可以在原理圖中以及引腳分配表中查詢(xún)到,LED_B對應了PE9,LED_G對應了PE8,LED_R對應了PE7。在代碼實(shí)現部分我們的步驟也分為以下三步:1.定義引腳編號映射;2.設置引腳工作模式;3.設置引腳電平狀態(tài)。在設置引腳電平狀態(tài)時(shí)我們需要對另外兩個(gè)RGB燈進(jìn)行關(guān)閉,確保在一個(gè)時(shí)間段能開(kāi)啟一個(gè)RGB燈,依次循環(huán)即可實(shí)現呼吸燈的效果。具體流程圖如下所示:
軟件流程圖
b) 具體代碼實(shí)現
我們需要使用的API接口函數和查看單片機引腳編號的方法已經(jīng)在上小節中做了介紹,這里就不在贅述了。我們編寫(xiě)功能代碼時(shí),按照流程圖的思路進(jìn)行編寫(xiě)即可。
1. 新建一個(gè)源文件,文件名自行更改。
2. 導入相關(guān)的頭文件。
3. 創(chuàng )建RGB線(xiàn)程,并編寫(xiě)線(xiàn)程入口函數,入口函數中實(shí)現我們需要的功能。
4. 編譯、下載、運行。
具體代碼實(shí)現如下:
/*導入頭文件*/includeinclude/*定義線(xiàn)程句柄與GPIO引腳宏定義*/staticrt_thread_tRGB_Thread = RT_NULL;defineLEDB 73defineLEDG 72defineLEDR 71defineTHREAD_PRIORITY 25defineTHREAD_STACK_SIZE 512defineTHREAD_TIMESLICE 5/*編寫(xiě)入口函數*/staticvoidRGB_Thread_Entry(void*parmas){/*設置引腳模式*/rt_pin_mode(LEDB, PIN_MODE_OUTPUT);
rt_pin_mode(LEDG, PIN_MODE_OUTPUT);
rt_pin_mode(LEDR, PIN_MODE_OUTPUT);/*設置引腳電平狀態(tài)1.先打開(kāi)LEDB 其他關(guān)閉 然后延遲500ms打開(kāi)LEDG其他關(guān)閉延遲500ms,打開(kāi)LEDR其他關(guān)閉*/while(1)
{
rt_pin_write(LEDB, PIN_LOW);
rt_pin_write(LEDG, PIN_HIGH);
rt_pin_write(LEDR, PIN_HIGH);
rt_thread_mdelay(500);
rt_kprintf("LEDB on.n");
rt_pin_write(LEDB, PIN_HIGH);
rt_pin_write(LEDG, PIN_LOW);
rt_pin_write(LEDR, PIN_HIGH);
rt_thread_mdelay(500);
rt_kprintf("LEDG on.n");
rt_pin_write(LEDB, PIN_HIGH);
rt_pin_write(LEDG, PIN_HIGH);
rt_pin_write(LEDR, PIN_LOW);
rt_thread_mdelay(500);
rt_kprintf("LEDR on.n");
}
}intRGB_Demo(void){
RGB_Thread = rt_thread_create("RGB-Thread",RGB_Thread_Entry,RT_NULL,THREAD_STACK_SIZE,THREAD_PRIORITY,THREAD_TIMESLICE);if(RGB_Thread == RT_NULL)
{
rt_kprintf("create rgb thread failedn");return-1;
}
rt_thread_startup(RGB_Thread);return0;
}
MSH_CMD_EXPORT(RGB_Demo,RGB_Demo);
我們把代碼編譯、下載到開(kāi)發(fā)板中,打開(kāi)終端命令行,輸入RGB_Demo命令執行此線(xiàn)程代碼??梢园l(fā)現實(shí)驗結果如下。
1. RGB燈部分紅、藍、綠交替閃爍。
2. 在終端命令行中循環(huán)打印led燈日志。