STM32G474 DAC+DMA輸出正弦波


STM32G474CET6 DAC+DMA輸出正弦波

 

        通過DAC輸出正弦波可以直接在while循環中設置DAC的輸出值,函數是HAL_DAC_SetValue(&hdac1,DAC1_CHANNEL_1,DAC_ALIGN_12B_R,2000)。但這種方式會導致CPU的負載率太高,刷新頻率也不夠快。所以,我需要用DMA來幫助CPU把數據快速的寫入DAC的值寄存器中。CubeMX中的具體配置步驟如下

第一步,配置總線時鍾,按下圖配置即可,我們用的一般都是陶瓷晶振。注意是HSE作為時鍾輸入源,系統時鍾選擇PLLCLK。

 

  

        第二步,配置JTAG口,下載和調試程序使用

 

 

        第三步,配置TIM6,這個是作為DAC輸出更新的觸發源,DAC就是按這個TIM6的時間間隔更新輸出。其他定時器也可以作為觸發源的,具體哪些看對應芯片手冊。分頻系數為0就是不分配,總線時鍾168M,計數值1680-1就是10us更新一次。觸發事件要選擇update,這個一定要選,不然DAC沒有觸發源,不會工作的。

 

         第四步,配置DAC,DAC的配置要選擇連接到外部的pin,這樣信號就是在pin腳輸出了。Trigger觸發源要選擇TIM6 trigger,如果配置的是其他TIM就對應更改,DAC配置這兩個就可以了,其他默認即可。

 

 

        第五步,配置DMA,DMA是英文Direct memory access的縮寫,就是內存的直接訪問,這樣的話就不需要CPU來寫入了,並且它的速率遠高於通過CPU操作的方式。模式選擇circular,這樣只需啟動一次DMA傳輸即可。數據寬度需要特別注意,外設是選擇Word而不是halfword,被這個坑了很久。

 

 

問題解決后看到官方手冊的如下描述,訪問AHB總線的外設不支持byte/half-word傳輸,這個一定要注意,被坑了很久。

 

 

        配置好之后用CubeMX工具生產代碼,主要要選擇對應的編譯器,我用的是KEIL v5。只需要在主函數中加兩條指令和一個sin波形數組就可以了。如下是sin波形生產數據,這里只是舉例,大家可以有自己的數組。

 

 

        在初始化這里添加如下函數,第一個函數是啟動TIM,這樣TIM就會按設定好的時間去觸發DAC。當DAC被觸發后就會發送DMA請求,DMA收到請求后就會把一個數據傳入DAC寄存器,然后等待下一次的請求。流程就是TIM—>DAC—>DMA,DMA把數據傳入DAC后,DAC就會釋放DMA請求,等帶下一次TIM的觸發信號。當整個數組傳輸完成后,又會開始下一輪的傳輸,因為DMA的模式是circular。

        第二個函數就是啟動DAC和DMA,最后一個參數是12bit的右對齊。這個就是這么簡單,改變定時器的定時時間也就是改變正弦波的周期,可以根據需要自己調節。正弦波的周期就是  定時時間間隔*數組長度。我試了下TIM6的頻率為12Mhz的時候信號輸出正常,頻率再高的時候DAC輸出不變化了,這個12Mhz的更新頻率比直接在while循環中賦值的方式至少快了一個數量級。

 

 

        接示波器效果如下,唯一遇到是就是DMA配置的坑,其他一次成功。

 


免責聲明!

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



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