使用寄存器點亮LED——編程實戰


stm32的編程和stc89c51還是存在着很多思想上的不同的,在51單片機中,我們點亮LED燈,只用給對應IO高低電平就可以了,而stm32中,就一個簡單的GPIO,我們也需要配置好幾個寄存器,而且,就算配置好GPIO寄存器,我們還必須有一步不能缺少的操作,那就是開啟對應GPIO的時鍾。在stm32的編程中,開啟對應時鍾是必不可少的一個操作,而且,開啟時鍾的操作必須在配置相應寄存器之前,以GPIO為例,如果我們先配置GPIO的寄存器,不開啟時鍾或者先配置GPIO寄存器,最后再開啟時鍾,都不能正常驅動芯片工作。時鍾就像人的脈搏一樣,人必須有脈搏才能工作,同樣,stm32也必須先給時鍾,再配置寄存器達到相應的功能。

那么我是怎么知道要這樣配置的呢?

第一,現在的教程比較成熟,能夠知道這些內容;第二,在開發板的學習教程中,他也是通過ST的官方demo知道的,具體在

F4固件庫\STM32F4xx_DSP_StdPeriph_Lib_V1.5.1\STM32F4xx_DSP_StdPeriph_Lib_V1.5.1\Project\STM32F4xx_StdPeriph_Examples\

這個目錄下,有基於ST的參考代碼,別人告訴我們要先開啟時鍾;第三,為什么要先開啟對應外設時鍾才能工作,51單片機就不需要啊。這個也是可以理解的,為了低功耗嘛,時鍾相當於一把鑰匙控制這個電路的開關,沒用時鍾這把鑰匙,你什么操作也是白搭,對應時鍾控制對應外設,這也無可厚非。

 

那么我們怎么查看具體外設到底要開啟什么時鍾呢?

查看《STM32F4xx中文參考手冊1》2.3節,STM32F4xx 寄存器邊界地址 ,可以看到對應外設的時鍾。

可以看到我們的GPIOH是掛載在AHB1總線上,所以要先開啟AHB1總線上的GPIOH時鍾。

那么又在哪里查看這個呢?還是中文參考資料中,6.3.12 RCC AHB1 外設時鍾使能寄存器 (RCC_AHB1ENR)

通過這里我們我們可以看到:

參考手冊上說明,這個寄存器的第七位控制我們的GPIOH,置1,使能。

同樣,配置GPIO寄存器時,也應該參考對應手冊:

在知道這些流程之后,開始編寫程序:

/*
    使用寄存器的方法點亮LED燈
  */
#include "./stm32f4xx.h"  


/**
  *   主函數
  */
int main(void)
{    
    /*開啟 GPIOH 時鍾,使用外設時都要先開啟它的時鍾*/
    RCC_AHB1ENR |= (1<<7);    //很明朗了,第七位要置1,使能時鍾
    
    /* LED 端口初始化 */
    //根據上面的寄存器描述依次配置,這個技能是只要你去看,就會的東西
    /*GPIOH MODER10清空*/
    GPIOH_MODER  &= ~( 0x03<< (2*12));    
    /*PH10 MODER10 = 01b 輸出模式*/
    GPIOH_MODER |= (1<<2*12);
    
    /*GPIOH OTYPER10清空*/
    GPIOH_OTYPER &= ~(1<<1*12);
    /*PH10 OTYPER10 = 0b 推挽模式*/
    GPIOH_OTYPER |= (0<<1*12);
    
    /*GPIOH OSPEEDR10清空*/
    GPIOH_OSPEEDR &= ~(0x03<<2*12);
    /*PH10 OSPEEDR10 = 0b 速率2MHz*/
    GPIOH_OSPEEDR |= (0<<2*12);
    
    /*GPIOH PUPDR10清空*/
    GPIOH_PUPDR &= ~(0x03<<2*12);
    /*PH10 PUPDR10 = 01b 上拉模式*/
    GPIOH_PUPDR |= (1<<2*12);
    
    /*PH10 BSRR寄存器的 BR10置1,使引腳輸出低電平*/
    GPIOH_BSRR |= (1<<16<<12);
    
    /*PH10 BSRR寄存器的 BS10置1,使引腳輸出高電平*/
    //GPIOH_BSRR |= (1<<10);

    while(1);

}

// 函數為空,目的是為了騙過編譯器不報錯
void SystemInit(void)//這個函數必須自己寫一個加上,因為啟動文件的關系,到后面會詳細說這個問題
{    
}






/*********************************************END OF FILE**********************/

這個是我們自己用寄存器實現的例子,我的開發板有三個燈,分別接GPIOH10,11,12,所以更改了幾次代碼,這樣也發現寄存器編程的一個問題,修改代碼有點麻煩,而且還是有點冗余,雖然我們可以通過宏或者函數封裝,但是,那樣封裝之后,他就是庫函數版本了, 到后面,我們都會采用庫函數的方式來學習,項目開發中肯定也是庫函數首選。但是,我們經過自己配置寄存器這個步驟,知道了庫函數底層其實也就是封裝了配置好的寄存器而已,知道原理之后,我們還是應該才贏開發效率更高的庫函數來進行應用。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM