|
我並沒有什麼方法,只是對於一件事情很長時間很熱心地去考慮罷了。 - 牛頓 |
距離前一篇《
作業系統之前的程式 for stm32f4discovery (13) - 打造 c++ 標準程式庫》有 8 個月了, 這期間我轉移目標, 改為研究編譯器, 在略有小成之後, 我又回到了 stm32f407, 補足我之前沒有搞懂的部份, 也因為購買了《
Saleae Logic16 (16通道 100MHz 邏輯分析儀)》才能繼續下去。
其實我自己也為了編譯器設定不少計劃, 大概只完成 30%, 不過編譯器似乎還不夠吸引我, 我又回到和作業系統相關的主題。
終於完成這個了, 設定一個精準的 timer 是很重要的行為, 但為什麼到這麼後面才介紹, 因為需要很多東西。
- 邏輯分析儀
- 搞懂 stm32f4 clock source tree
- 設定 systick
|
fig 1 用 la 測量 pd12, pd13 |
我在《
作業系統之前的程式 for stm32f4discovery (6) - systick》完成 3, 而最近買了《
Saleae Logic16 (16通道 100MHz 邏輯分析儀)》, 只剩下最難的 2, 而在讀了《精通STM32F4(寄存器版)》、《精通STM32F4(库函数版)》之後, 我終於略懂 stm32f407 clock source tree, 還真不是普通的難。
總之在呼叫 my_timer.c L672 SystemInit() 之後:
sysclk (cpu 時脈): 168 MHz
AHB: 168 MHz
APB1: 42MHz
APB2: 84MHz
main PLL: 168 MHz
再來只要知道那個週邊掛在哪個 bus, 就知道要怎麼設定其 clock。ref:
作業系統之前的程式 for stm32f4discovery (3) - usart 最上面的幾張圖。
systick 是 sysclk/8 = 21MHz, 這表示 systick 1/21000000 s 會減小一個計數值, 如果把計數值設定為 21000, 在 21000/21000000 s 之後就會計數完畢, 也就是 1ms, 這樣就完成了1ms 的設定。my_timer.c L7 的 -1 是怎麼回事, 手冊說的, 計數值要減一。
systick 只要設定 3 個暫存器就可以完成我們需要的功能 (ref:
DDI0337E_cortex_m3_r1p1_trm.pdf ):
- control
- reload
- current value
ref: my_timer.c 712, 713, 740
my_timer.c L708 而 control bit[2] 的 clksource, 在我的測試下, 不管是 0 或 1 都沒影響, 真是奇怪, 0 應該是使用 implementation defined external reference clock (168Mhz/8 = 21Mhz), 而 1 應該是用 168Mhz 當作 clksource。
程式邏輯是這樣: 點亮綠色 led, 1ms 後, 熄燈, 1ms 後, 亮燈, 人眼看不出來有閃爍, 不過從 la 的波型可以看到 1ms 上下一次。
fig 2 顯示 1ms 亮/滅一次。
|
fig 2 1ms systick |
soure code:
https://github.com/descent/stm32f4_prog/tree/master/my_timer
沒有留言:
張貼留言
使用 google 的 reCAPTCHA 驗證碼, 總算可以輕鬆留言了。
我實在受不了 spam 了, 又不想讓大家的眼睛花掉, 只好放棄匿名留言。這是沒辦法中的辦法了。留言的朋友需要有 google 帳號。