[TOC] # 前言 - 本篇以實現PWM輸出為目標,主要介紹EV_Timer的PWM輸出、和比較單元的PWM輸出,見 手把手12.2.5和12.3節 - 微處理器的比較功能可以在 timer 計時到特定時刻時翻轉電平,產生PWM波形 - F2812 最多可以有16個 PWM 輸出 Channel - EV 可以有兩種PWM產生方法 1. 使用 timer 內的比較暫存器 2. 使用比較單元的比較暫存器,能進一步做到死區時間控制 - 這邊主要介紹timer 內的比較暫存器生成的PWM,比較單元的生成方式相同,只是相關控制與比較暫存器在比較單元內。 # PWM 簡介 - 基礎概念見[微處理器基礎](https://hackmd.io/6Rj1vNC5S2ya2y2MNScFbg?both#%E5%AE%9A%E6%99%82%E8%88%87%E8%A8%88%E6%99%82%E5%8A%9F%E8%83%BD)或自己查 ## 生成原理 - 非對稱PWM波形 - 藉由比較 Counter 和 Compare 的值輸出高或低電位,調整Compare的值可以調整Duty Cycle - 一個計時週期內的PWM波形不是對稱於週期中心 - 計數模式使用<font color="red">up counting mode</font> -  - 對稱PWM波形 - 輸出原理與上述相同 - 因為Counter 計數方式改為 "上下數" 的模式,一個計時週期內的PWM波形對稱於週期中心 - 計數模式使用 <font color="red">continuous up/down counting mode</font> -  ## 死區控制的PWM - 這部分可自行參考<手把手教你DSP> 12.3 </br> </br> # 使用 timer 內的比較暫存器生成PWM ## 暫存器設定 - TxCON 暫存器的TECMPR位(bit 1)設為 1 可以使能比較功能 - TxCMPR 暫存器儲存要比較的值 - GPTCONx 暫存器的TCMPOE位 設為1,可以使能比較輸出功能 - GPTCONx 暫存器的TxPIN位 決定PWM輸出極性 - 低/高 電平有效表示計數值大於比較值時維持 低/高電平 - 強制 高/低 就是一直維持 高/低 電平 -  # PWM輸出範例 ## 設定流程 - 選擇EVB timer3 的比較暫存器輸出非對稱PWM,設定T3CON暫存器 - 時鐘源選內部時鐘 - 計數模式改為 up counting mode - timer3 預除頻設為1 - 使能timer3的比較功能 - 啟用timer3 - 設定T3PR暫存器,決定PWM的週期 - 設定GPTCONB 的TCMPOE位,使能比較輸出功能 - 把GPTCONB 的T3PIN位設為低電平有效,也就是當計數值大於比較值時,腳位輸出低電位 - 設定GPIO腳位為PWM輸出 ## 範例程式 ``` c++= //======== GPTCONx Parameter =========== // Compare Output enable #define GPTIM_CO_ENABLE 1 #define GPTIM_CO_DISABLE 0 // Compare Polarity #define GPTIM_CP_FORCED_LOW 0 #define GPTIM_CP_EFF_LOW 1 #define GPTIM_CP_EFF_HIGH 2 #define GPTIM_CP_FORCED_HIGH 3 //======== TxCON Parameter =========== #define UP_DOWN_COUNTING_MODE 1 #define UP_COUNTING_MODE 2 #define DIR_UP_DOWN_COUNTING_MODE 3 #define GPTIM_PRESCALAR_1 0 #define GPTIM_PRESCALAR_2 1 #define GPTIM_PRESCALAR_4 2 #define GPTIM_PRESCALAR_8 3 #define GPTIM_PRESCALAR_16 4 #define GPTIM_ENABLE 1 #define GPTIM_DISABLE 0 #define GPTIM_CLK_SRC_INTERNAL 0 #define GPTIM_CLK_SRC_EXTERNAL 1 #define GPTIM_CLK_SRC_RESERVED 2 #define GPTIM_CLK_SRC_QEPINTERNAL 3 #define GPTIM_CAP_ENABLE 1 #define GPTIM_CAP_DISABLE 0 void GPIO_select(void){ // for IMU GPIO pin select EALLOW; //--------------------------------------------------------------------------- // Set GPIO B pin 6 as output PWM. GpioMuxRegs.GPBMUX.bit.T3PWM_GPIOB6 = 1; GpioMuxRegs.GPBDIR.bit.GPIOB6 = 1; EDIS; } void init_evb_timer3(void){ // Using for PWM // Initialize EVB Timer3: //--------------------------------------------------------------------------- // Count up, internal clk/1 (HSPCLK/10 = 25MHz), enable Timer // EvbRegs.T3CON.all = 0xD871; // 11-0-10-000-0-1-00-00-1-0 EvbRegs.T3CON.bit.FREE = 1; EvbRegs.T3CON.bit.SOFT = 1; EvbRegs.T3CON.bit.TMODE = UP_COUNTING_MODE; EvbRegs.T3CON.bit.TPS = GPTIM_PRESCALAR_1; EvbRegs.T3CON.bit.TCLKS10 = GPTIM_CLK_SRC_INTERNAL; EvbRegs.T3CON.bit.TECMPR = GPTIM_CAP_ENABLE; EvbRegs.T3CON.bit.TENABLE = GPTIM_ENABLE; // PWM frequency = (clk/1) / 5000 = 5 kHz EvbRegs.T3PR = 5000-1; // Timer3 counter reset EvbRegs.T3CNT = 0x0000; // Timer3 compare value EvbRegs.T3CMPR = 0x0000; // Compare Output Enable EvbRegs.GPTCONB.bit.TCMPOE = GPTIM_CO_ENABLE; // Timer3 Compare Output Polarity = active low EvbRegs.GPTCONB.bit.T3PIN = GPTIM_CP_EFF_LOW; } ```
×
Sign in
Email
Password
Forgot password
or
By clicking below, you agree to our
terms of service
.
Sign in via Facebook
Sign in via Twitter
Sign in via GitHub
Sign in via Dropbox
Sign in with Wallet
Wallet (
)
Connect another wallet
New to HackMD?
Sign up