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

DSP28335-ePWM

[复制链接]

该用户从未签到

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

EDA365欢迎您登录!

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

x
#include "DSP28x_Project.h"
' |: U! C: B$ a: ]* k// Configure the period for each timer
% i# n$ B2 p4 Z6 t" `8 h2 u- O#define EPWM1_TIMER_TBPRD  3750  // Period register 系统始终为150MHZ,下面的程序进行了4分频,即为37.5MHZ,这样得到的是10KHZ8 I, n7 x' j! \! j0 Y
#define EPWM1_START_CMPA     1900//设置PWM通道A初始占空比
$ c) \8 ]# V8 }1 D# U#define EPWM1_START_CMPB     1900//设置PWM通道B初始占空比
& i; H; Q- v9 Q/ R' s* z6 ~$ evoid ChangeDuty(Uint16 Duty)//改变占空比函数
  J5 y0 R. V5 A( x) T{
5 y: _4 M& q# I2 U    if(Duty > EPWM1_TIMER_TBPRD) Duty = EPWM1_TIMER_TBPRD;, L) M) K% e5 e: E
    if(Duty < 0) Duty = 0;
4 o: t/ o2 K# {4 J8 G' a    EPwm1Regs.CMPA.half.CMPA = Duty;     // Set compare A value
% O  ^1 T/ [  `' F1 P* Q$ F    EPwm1Regs.CMPB = Duty;               // Set Compare B value& h4 z! c- T- J1 Z4 W9 I
}  n1 r- f# i' F' S% j
void PWM1_Init()//初始化PWM
& o% c6 k3 h" ]" G: y% U{4 n+ M2 r# X- `5 h, f
/*首先进行的是PWM1引脚的初始化,因为PWM1的引脚为GPIO0和GPIO1,这两个引脚可以是普通的IO口,也可以复用输出PWM,这里选用复用功能*/
/ ]4 N# h0 y9 z9 V0 w    EALLOW;
& Y8 l# |" y4 L4 k3 \" i    GpioCtrlRegs.GPAPUD.bit.GPIO0 = 0;    // Enable pull-up on GPIO0 (EPWM1A)1 i- q! _  p9 Y* ?: X( {
    GpioCtrlRegs.GPAPUD.bit.GPIO1 = 0;    // Enable pull-up on GPIO1 (EPWM1B)
% |5 f0 E9 R1 v- j# F    GpioCtrlRegs.GPAMUX1.bit.GPIO0 = 1;   // Configure GPIO0 as EPWM1A复用功能设置,为0代表是普通IO口
/ V* g+ c  d- X+ {3 d6 g    GpioCtrlRegs.GPAMUX1.bit.GPIO1 = 1;   // Configure GPIO1 as EPWM1B' _  r0 I1 b; E) Q+ |/ A, t
    EDIS;  L/ F- ]1 h3 x/ Q
    EALLOW;
' w- c9 Y8 ]" ]2 U    SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;      // Stop all the TB clocks7 ]: H6 ~7 x3 b. e" ?
    EDIS;3 m/ d4 t7 m9 J! E- \
    // Setup TBCLK! l0 S7 `4 m: n( V+ n
    EPwm1Regs.TBPRD = EPWM1_TIMER_TBPRD - 1;           // 设置周期
( a5 L3 _! V! R* N8 ?: z" I    EPwm1Regs.TBPHS.half.TBPHS = 0x0000;           // 这个代表的是相位,不明白什么东西; ?1 `# G* h, _0 N" M
    EPwm1Regs.TBCTR = 0x0000;                      // Clear counter! B8 g6 R) }4 Y0 |8 b. \/ A
    // Set Compare values
! Y; ~* e8 v5 b# r: P- }    EPwm1Regs.CMPA.half.CMPA = EPWM1_START_CMPA;     // Set compare A value" U' G( h+ E: i
    EPwm1Regs.CMPB = EPWM1_START_CMPB;               // Set Compare B value/ m/ `" w6 Z' r+ ?
    // Setup counter mode; u4 L  _% y$ `% m' E
    EPwm1Regs.TBCTL.bit.CTRMODE = TB_COUNT_UPDOWN; //计数模式* X* L; F. V+ G+ h, B& e
    EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE;        // Disable phase loading
( `2 j" t, A% O  X9 k    EPwm1Regs.TBCTL.bit.HSPCLKDIV = TB_DIV2;       // 这里是进行2分频
6 s3 R/ X0 J- I. ~" f% }    EPwm1Regs.TBCTL.bit.CLKDIV = TB_DIV2;          //这里也是2分频
: h9 ?; A# p4 z8 O% R8 ]    // Setup shadowing3 ^, ]% P; N# h7 y) ]5 C! u
    EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;   //采用影子寄存器跟新0 }7 U3 [7 \# w
    EPwm1Regs.CMPCTL.bit.SHDWBMODE = CC_SHADOW;
! J; @  g8 L3 H  x; j/ K! Y    EPwm1Regs.CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;  // Load on Zero
' U4 o& ^6 N* E" v    EPwm1Regs.CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
% \0 x/ B( f$ ~: L! `    // Set actions
3 K' O0 L% j6 x! y3 X    EPwm1Regs.AQCTLA.bit.CAU = AQ_CLEAR;          // Set PWM1A on event A, up count4 d0 P8 T* q; N( O
    EPwm1Regs.AQCTLA.bit.CAD = AQ_SET;           // Clear PWM1A on event A, down count
  e( w# k# q2 C8 i% {3 x    EPwm1Regs.AQCTLB.bit.CBU = AQ_SET;             // Set PWM1B on event B, up count
2 n1 K! y) n+ O+ x    EPwm1Regs.AQCTLB.bit.CBD = AQ_CLEAR;           // Clear PWM1B on event B, down count. a9 c0 O% k( N0 r% n
    EALLOW;. t3 R' t; T& J* s# s7 D
    SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;         // Start all the timers synced" s4 H2 V! n& R
    EDIS;/ R, L- C+ [- G, _; k- p
}
( R  ~/ J$ x4 ~- I- f% Gvoid All_Init()3 [: ]& O! `1 t( S* \8 V/ @6 ^
{* n* s0 H- v) S3 @
    InitSysCtrl();
% \8 ~: L3 S. o    DINT;0 B& @3 |+ [8 I# p5 F2 Q2 [, M
    InitPieCtrl();* o. |, S! W1 l
    IER = 0x0000;
; A; W$ A) Y# H2 ~    IFR = 0x0000;
& s( k' |8 }6 p/ _6 l7 Q    InitPieVectTable();
" k. y- [3 g. d* U( x7 ], ^    PWM1_Init();
) n4 l. f3 I; n7 J1 p    EINT;   // Enable Global interrupt INTM' c" [1 ?( l& R$ x
    ERTM;   // Enable Global realtime interrupt DBGM+ T/ N/ v. E9 {$ K: K4 d  b$ [& x- t
}
! i, I3 X( s. @6 I" z0 `1 Q( BUint16 Duty = 1900;
* l* ]& S+ H0 b. `1 Z, C2 lvoid main(void)
) d0 b* k% a; C5 z. F{7 @, ]  O9 @( q/ ]6 G, r
    All_Init();. Y7 s7 A/ E  h6 X% \: ~6 w8 [
    while(1)
# n* T) t# F- ?3 [; s+ p( ~0 g( R    {
! j, a4 T; m' ~/ A9 F1 I        ChangeDuty(Duty);" y8 ~3 ~4 p/ ]; \- i; Y3 z
    }5 r9 x3 h2 p) I. z
}0 c! A( a5 X: u7 E1 Q+ B0 O* Q

7 _  o# M7 c/ \! S( U( f& N* l产生PWM主要需要三个部件,
1 J4 I/ z* |0 m* v! ^# D第一个是周期PRD,通过设定EPwm1Regs.TBPRD的值,来得到周期,我的代码中设定的是3750,系统时钟是150 M hz,经过四分频得到的是37.5Mhz,即1/(37.5M)秒,计数器每个时间间隔加一,加到3750需要的时间是3750 * 1 / (37.5M) = (1 / 10K)秒,即为计数周期,可知频率为10K。
* j6 D7 z4 G# H# L6 F第二个是计数器CTR,计数器根据设定的时钟频率不断累加,我设定计数时钟频率是10K,即每过0.00001s,计数器自动加一。我这里设定的计数模式是增减模式,即计数器加到EPwm1Regs.TBPRD时再自动开始减小,当减到0时,又开始增加。# g  q$ C$ Z+ @8 l, Q% H
第三个是比较器COMPA,COMPA是我们自己设定的比较值,当这里设定的初始值1900,当计数器计数到1900的时候会产生事件,比如讲输出引脚置为1或者清为0。
: v6 t; J& a# z! a- f4 o) J这里采用了影子(映射)寄存器(EPwm1Regs.CMPCTL.bit.SHDWAMODE = CC_SHADOW;),映射提供了一个保持寄存器与硬件同步更新的方法,当使用映射模式时,只能在特定的事件处更新当前工作的寄存器,这就防止了由于软件异步修改寄存器内容而引发的错误。
+ f6 \7 e7 N, H* `计算器不断的累加,当计数器的值等于比较值时,就输出为1,当计数器的值等于周期值时,就输出为0.从图中也很容易看出方波的周期和占空比。) k: M  V) P8 I. I6 G
) V5 P  M' x3 s6 p) P
- j) H. n& w% ?. Y1 q

该用户从未签到

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

本版积分规则

关闭

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

EDA365公众号

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

GMT+8, 2025-11-24 03:21 , Processed in 0.140625 second(s), 23 queries , Gzip On.

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

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

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