找回密码
 注册
关于网站域名变更的通知
查看: 532|回复: 1
打印 上一主题 下一主题

DSP28335-ePWM

[复制链接]

该用户从未签到

跳转到指定楼层
1#
发表于 2021-9-22 13:41 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式

EDA365欢迎您登录!

您需要 登录 才可以下载或查看,没有帐号?注册

x
#include "DSP28x_Project.h"
- g# l8 e9 }: r% l# N9 f// Configure the period for each timer5 X9 ?; E& N& b) [' j- ^5 ?
#define EPWM1_TIMER_TBPRD  3750  // Period register 系统始终为150MHZ,下面的程序进行了4分频,即为37.5MHZ,这样得到的是10KHZ
3 _& s9 e5 ?) x2 ~+ F9 {; l7 M#define EPWM1_START_CMPA     1900//设置PWM通道A初始占空比# v% @- J( I' I- ^
#define EPWM1_START_CMPB     1900//设置PWM通道B初始占空比- e( b* L3 F. n0 \
void ChangeDuty(Uint16 Duty)//改变占空比函数/ {/ o/ i1 r& w) b
{
1 V8 _( }( m, ]' P0 _* b" b    if(Duty > EPWM1_TIMER_TBPRD) Duty = EPWM1_TIMER_TBPRD;0 Y0 h* |& r# z. T  H! l" ?
    if(Duty < 0) Duty = 0;
+ w% }; Y+ [, F6 ?    EPwm1Regs.CMPA.half.CMPA = Duty;     // Set compare A value+ a; v7 P" [  f! A
    EPwm1Regs.CMPB = Duty;               // Set Compare B value
# Z' ~9 d' q  T" u- W/ Y& F: `}0 l* l0 @, j& `
void PWM1_Init()//初始化PWM
$ B, ?& W  ^) M! ?0 P* \{- n) a  Y* d: p" {) w6 X6 {
/*首先进行的是PWM1引脚的初始化,因为PWM1的引脚为GPIO0和GPIO1,这两个引脚可以是普通的IO口,也可以复用输出PWM,这里选用复用功能*/
; _6 i! m* q3 g& Z7 \    EALLOW;. z/ {2 x" H" P9 @( r
    GpioCtrlRegs.GPAPUD.bit.GPIO0 = 0;    // Enable pull-up on GPIO0 (EPWM1A)
2 n0 {/ U3 I. G) y    GpioCtrlRegs.GPAPUD.bit.GPIO1 = 0;    // Enable pull-up on GPIO1 (EPWM1B)
8 l3 d9 O5 q7 u% n' c1 d& {1 K" s    GpioCtrlRegs.GPAMUX1.bit.GPIO0 = 1;   // Configure GPIO0 as EPWM1A复用功能设置,为0代表是普通IO口
. y  C3 }) p! ^- c1 y1 ^    GpioCtrlRegs.GPAMUX1.bit.GPIO1 = 1;   // Configure GPIO1 as EPWM1B: ?0 W: ?# y8 _" m, v' m8 i2 M
    EDIS;
2 H$ S$ p# x* l% M* B5 ]0 p    EALLOW;
! h$ ~, Y* M6 t- B    SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;      // Stop all the TB clocks
6 ]2 K2 }2 J% u; T; y' t- ^    EDIS;
# d' M: P+ F: z2 Y" r! U    // Setup TBCLK
! ]! z( l, ?( n3 a5 ~    EPwm1Regs.TBPRD = EPWM1_TIMER_TBPRD - 1;           // 设置周期
+ G$ ~; s( w8 q    EPwm1Regs.TBPHS.half.TBPHS = 0x0000;           // 这个代表的是相位,不明白什么东西
  S7 F/ E0 [6 \; m" u& K    EPwm1Regs.TBCTR = 0x0000;                      // Clear counter
4 H& u) e% ?& G+ x    // Set Compare values
" A4 r$ @7 Z$ y& G- J    EPwm1Regs.CMPA.half.CMPA = EPWM1_START_CMPA;     // Set compare A value
1 P+ K/ o; x. \7 @& v* A/ [  K    EPwm1Regs.CMPB = EPWM1_START_CMPB;               // Set Compare B value' p# }  E( j; i& R; O2 V
    // Setup counter mode' r7 e/ |  C$ p: @
    EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN; //计数模式
! D. y7 u0 x2 y# s    EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE;        // Disable phase loading2 e1 z6 i7 f7 ~! o8 W4 d
    EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV2;       // 这里是进行2分频
) h# ^4 k" y: |4 L    EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV2;          //这里也是2分频
* D* v" Z9 |+ Z, b4 P. j    // Setup shadowing6 w# p7 Q) \9 Z- k8 ~7 e+ j
    EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;   //采用影子寄存器跟新
" J2 s* Y. n1 j/ s. l    EPwm1Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;# S' U! j+ U9 S
    EPwm1Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;  // Load on Zero
* }6 Y: [$ O) T# p    EPwm1Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;  L7 |, H- F: ?# d- |5 n
    // Set actions7 W, ?# a( J; D7 d$ F" |
    EPwm1Regs.AQCTLA.bit.CAU = AQ_CLEAR;          // Set PWM1A on event A, up count6 k: o( n% q. I& c
    EPwm1Regs.AQCTLA.bit.CAD = AQ_SET;           // Clear PWM1A on event A, down count# [7 {# a) Q, ?( n
    EPwm1Regs.AQCTLB.bit.CBU = AQ_SET;             // Set PWM1B on event B, up count- F( l/ o% i% F1 j. s/ l
    EPwm1Regs.AQCTLB.bit.CBD = AQ_CLEAR;           // Clear PWM1B on event B, down count3 U0 j, R; Q, q
    EALLOW;
0 x6 n5 ]6 P/ z( D% M' o$ r: P    SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;         // Start all the timers synced) P0 Z+ d# o7 B# m# b) a; T
    EDIS;
. @, f. j/ |. Q, @$ W5 l}  I0 z( ^. P: I, H& u, D3 ]0 q3 ?
void All_Init()
" a3 e7 q& f8 _1 E7 F{& c9 }1 D/ z, W6 R
    InitSysCtrl();
, g4 v) q. E" [    DINT;
) r% E: T# S; d# f& g    InitPieCtrl();
. B$ j: _+ O; l" a    IER = 0x0000;7 b) Y' q7 J+ n+ q) T% J; w
    IFR = 0x0000;
' Q& w* I; Q2 r* S; N8 z# z9 J7 B    InitPieVectTable();
; r  U& X2 I: k3 r: }% D, X    PWM1_Init();
- q- b  ?; W5 X4 U6 z    EINT;   // Enable Global interrupt INTM
/ r8 z% _1 p7 X- G5 A) Y+ \    ERTM;   // Enable Global realtime interrupt DBGM
8 \) J- u/ D7 ^3 t" u}
/ M9 H6 g* @4 SUint16 Duty = 1900;
! P* b- p* [7 E# o! Rvoid main(void)
' ~$ V5 m' o$ a6 J{9 Y4 g- }5 A; R1 e* _, i& f2 ^
    All_Init();
+ S' q  _7 u, {1 @9 @    while(1)
% ^& r0 B  V5 w    {/ O2 Z! G( U8 c; K. }1 O
        ChangeDuty(Duty);3 G+ i8 Z+ v' _9 j: V  b
    }
4 l7 z! {! B4 a}3 ~+ F5 x  Z& [* @, [% p) H/ t4 S
$ I$ x* R5 c6 Z' E; n& a
产生PWM主要需要三个部件,
4 ?, O5 T& f2 i第一个是周期PRD,通过设定EPwm1Regs.TBPRD的值,来得到周期,我的代码中设定的是3750,系统时钟是150 M hz,经过四分频得到的是37.5Mhz,即1/(37.5M)秒,计数器每个时间间隔加一,加到3750需要的时间是3750 * 1 / (37.5M) = (1 / 10K)秒,即为计数周期,可知频率为10K。& `7 j+ m! u7 M, F
第二个是计数器CTR,计数器根据设定的时钟频率不断累加,我设定计数时钟频率是10K,即每过0.00001s,计数器自动加一。我这里设定的计数模式是增减模式,即计数器加到EPwm1Regs.TBPRD时再自动开始减小,当减到0时,又开始增加。. Z8 J$ F  s; w# W$ R
第三个是比较器COMPA,COMPA是我们自己设定的比较值,当这里设定的初始值1900,当计数器计数到1900的时候会产生事件,比如讲输出引脚置为1或者清为0。1 \! ]; ?6 H6 A, [
这里采用了影子(映射)寄存器(EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;),映射提供了一个保持寄存器与硬件同步更新的方法,当使用映射模式时,只能在特定的事件处更新当前工作的寄存器,这就防止了由于软件异步修改寄存器内容而引发的错误。
6 ^% c$ n7 P0 c& `( t. t4 j1 ^% Y* e计算器不断的累加,当计数器的值等于比较值时,就输出为1,当计数器的值等于周期值时,就输出为0.从图中也很容易看出方波的周期和占空比。
& G, U% n5 G3 m3 m$ W/ Q7 ?1 s0 ?1 W% Q% [& h4 K* M
( B5 A$ f2 h6 C

该用户从未签到

2#
发表于 2021-9-22 15:52 | 只看该作者
首先进行的是PWM1引脚的初始化,因为PWM1的引脚为GPIO0和GPIO1,这两个引脚可以是普通的IO口,也可以复用输出PWM
您需要登录后才可以回帖 登录 | 注册

本版积分规则

关闭

推荐内容上一条 /1 下一条

EDA365公众号

关于我们|手机版|EDA365电子论坛网 ( 粤ICP备18020198号-1 )

GMT+8, 2025-11-24 08:39 , Processed in 0.140625 second(s), 22 queries , Gzip On.

深圳市墨知创新科技有限公司

地址:深圳市南山区科技生态园2栋A座805 电话:19926409050

快速回复 返回顶部 返回列表