找回密码
 立即注册
查看: 569|回复: 11

PWM没有输出

[复制链接]

该用户从未签到

3

主题

15

回帖

83

积分

注册会员

积分
83
发表于 2023-6-24 18:49:27 | 显示全部楼层 |阅读模式
端午节抽时间重新玩了下STC32G,想使用pwm产生一组450hz的正弦波,按照例子想修改成P1^4引脚,也就是PWM3P输出pwm波的程序,没想到一下子就卡住了,以前也尝试修改过其他引脚成功过,但是有可能是水平太差的原因找了很久还是没找到无输出的原因,虽然有点不好意思,但还是上来求助。改的代码如下,希望各位大佬可以指出这个错误
  1. <blockquote>#include "stc32g.h"
复制代码


回复 送花

使用道具 举报

该用户从未签到

3

主题

15

回帖

83

积分

注册会员

积分
83
 楼主| 发表于 2023-6-24 18:50:01 | 显示全部楼层
  1. #include "stc32g.h"
  2. #include "intrins.h"
  3. #define ARR_f 1000
  4. #define CCR_f 300
  5.         sbit Debug_LED=P0^1;
  6. void PWMA_ISR() interrupt 26{
  7.        
  8.         Debug_LED=!Debug_LED;
  9.   PWMA_SR1=0x00;
  10.        
  11. }
  12. void PWM_setup(void){
  13.        
  14.   PWMA_PS    = 0x0F; //使能PWMA3P,3N
  15.        
  16.         PWMA_PSCRH = 0x00;
  17.         PWMA_PSCRL = 0x00;
  18.        
  19.         PWMA_CCER1 = 0x00; //写 CCMRx 前必须先清零 CCERx 关闭通道
  20.         PWMA_CCMR3 = 0x60; //设置 CC1 为 PWMA 输出模式
  21.         PWMA_CCER1 = 0x01; //使能 CC1 通道
  22.        
  23.         PWMA_CCR3H = CCR_f>>8; //设置占空比时间
  24.         PWMA_CCR3L = CCR_f;       
  25.         PWMA_ARRH  = ARR_f>>8; //设置周期时间
  26.         PWMA_ARRL  = ARR_f;       
  27.        
  28.         PWMA_ENO   = 0x10; //使能 PWM3P 端口输出
  29.         PWMA_BKR   = 0x80; //使能主输出
  30.        
  31.         PWMA_IER   = 0x02; //使能中断
  32.         PWMA_CR1   = 0x01; //开始计时
  33.   EA = 1;
  34.           
  35. }
  36. void setup(){
  37.        
  38.         EAXFR = 1;
  39.         CKCON = 0x00;
  40.         WTST  = 0x00;
  41.         XOSCCR = 0xc0; //启动外部晶振
  42.         while (!(XOSCCR & 1)); //等待时钟稳定
  43.         CLKDIV = 0x00; //时钟不分频
  44.         CLKSEL = 0x01; //选择外部晶振       
  45.        
  46.         P1M0 = 0x10;
  47.         P1M1 = 0x00;
  48.         P3M0 = 0x00;
  49.         P3M1 = 0x00;       
  50.         PWM_setup();
  51.        
  52. }
  53. void loop(){
  54.        
  55. }
  56.        
  57. void main(){
  58.         setup();
  59. while(1){
  60.         loop();               
  61.         }
  62. }
复制代码
回复 支持 反对 送花

使用道具 举报

该用户从未签到

3

主题

15

回帖

83

积分

注册会员

积分
83
 楼主| 发表于 2023-6-24 18:51:33 | 显示全部楼层
可能看手册还不仔细,这种低级错误居然找不到
回复 支持 反对 送花

使用道具 举报

  • TA的每日心情
    开心
    3 小时前
  • 签到天数: 124 天

    [LV.7]常住居民III

    34

    主题

    399

    回帖

    2059

    积分

    荣誉版主

    积分
    2059
    发表于 2023-6-24 20:48:42 | 显示全部楼层
    lumen 发表于 2023-6-24 18:51
    可能看手册还不仔细,这种低级错误居然找不到

    你好,可以试一下将这一行语句
    1. PWMA_CCER1 = 0x01; //使能 CC1 通道
    复制代码

    改成这个样子
    1. PWMA_CCER2 = 0x01; //使能 CC3 通道
    复制代码
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    552

    主题

    9541

    回帖

    1万

    积分

    管理员

    积分
    14056
    发表于 2023-6-24 21:24:06 | 显示全部楼层
    感谢楼上的支持,我不懂程序了,只能贴些图,方便大家按图索骥
    1.png

    2.png
    第85个演示程序

    3.png
    深圳国芯人工智能有限公司-实验箱 (stcai.com)

    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    552

    主题

    9541

    回帖

    1万

    积分

    管理员

    积分
    14056
    发表于 2023-6-24 21:24:22 | 显示全部楼层
    /*************        功能说明        **************

    本例程基于STC32G为主控芯片的实验箱9.6进行编写测试。

    使用Keil C251编译器,Memory Model推荐设置XSmall模式,默认定义变量在edata,单时钟存取访问速度快。

    短接实验箱J1跳线,在J15的第1脚可测到1KHz的正弦波,在J15的第3脚可测到1KHz的方波。

    P1.1脚输出PWM信号通过转换电路转成DAC,短接J14的1、2脚,通过ADC3可采集DAC电压值。

    下载时, 选择默认时钟 35MHz.

    ******************************************/

    #include        "stc.h"

    /*************        本地常量声明        **************/

    #define MAIN_Fosc        35000000UL

    /*************        IO口声明        **************/


    /*************        本地变量声明        **************/


    /*************        本地函数声明        **************/

    void        Timer4_Config(void);
    void        PWMA_config(void);
    void        PWMB_config(void);

    /****************  外部函数声明和外部变量声明 *****************/


    /****************  主函数 *****************/
    void main(void)
    {
            WTST  = 0;
            CKCON = 0;
        EAXFR = 1;        //允许访问扩展寄存器

        P0M1 = 0x00;   P0M0 = 0x80;   //设置为准双向口,设置P0.7推挽输出
        P1M1 = 0x00;   P1M0 = 0x00;   //设置为准双向口
        P2M1 = 0x00;   P2M0 = 0x00;   //设置为准双向口
        P3M1 = 0x00;   P3M0 = 0x00;   //设置为准双向口
        P4M1 = 0x00;   P4M0 = 0x00;   //设置为准双向口
        P5M1 = 0x00;   P5M0 = 0x00;   //设置为准双向口
        P6M1 = 0x00;   P6M0 = 0x00;   //设置为准双向口
        P7M1 = 0x00;   P7M0 = 0x00;   //设置为准双向口
           
            Timer4_Config();        //Timer4初始化, 输出1000Hz方波.
            PWMA_config();                //PWM控制垂直位移
            PWMB_config();                //输出1000Hz正弦波
           
            EA = 1;

            while (1)
            {
            }
    }

    //========================================================================
    // 函数: void Timer4_Config(void)
    // 描述: timer3初始化函数.
    // 参数: none.
    // 返回: none.
    // 版本: V1.0, 2018-12-20
    //========================================================================
    void Timer4_Config(void)
    {
            T4T3M &= 0x0f;                //停止计数, 定时模式, 12T模式, 不输出时钟

            T4T3M |=  (1<<5);        //1T mode
            T4H = (u8)((65536UL - MAIN_Fosc/2000) /256);
            T4L = (u8)((65536UL - MAIN_Fosc/2000) %256);

            T3T4PS = 0x00;                //选择IO, 0x00: T3--P0.4, T3CLKO--P0.5, T4--P0.6, T4CLKO--P0.7;    0x01: T3--P0.0, T3CLKO--P0.1, T4--P0.2, T4CLKO--P0.3;
            T4T3M |=  (1<<4);        //允许输出时钟
            T4T3M |=  (1<<7);        //开始运行
    }

    //========================================================================
    // 函数: void PWMA_config(void)
    // 描述: PWMA初始化函数.
    // 参数: none.
    // 返回: none.
    // 版本: V1.0, 2022-6-25
    //========================================================================
    void PWMA_config(void)
    {
            u8        ccer1;
            u8        ccer2;
            u8        ps;
            u8        eno;
            u8        PWMA_ISR_En;

            P_SW2 |= 0x80;                //SFR enable   
            PWMA_ENO    = 0;        // IO输出禁止
            PWMA_IER    = 0;        // 禁止中断
            PWMA_SR1    = 0;        // 清除状态
            PWMA_SR2    = 0;        // 清除状态
            ccer1 = 0;
            ccer2 = 0;
            ps    = 0;
            eno   = 0;
            PWMA_ISR_En = 0;

            PWMA_PSCRH = 0x00;                // 预分频寄存器, 分频 Fck_cnt = Fck_psc/(PSCR[15:0}+1), 边沿对齐PWM频率 = SYSclk/((PSCR+1)*(AAR+1)), 中央对齐PWM频率 = SYSclk/((PSCR+1)*(AAR+1)*2).
            PWMA_PSCRL = 0x00;
            PWMA_DTR   = 0;                        // 死区时间配置, n=0~127: DTR= n T,   0x80 ~(0x80+n), n=0~63: DTR=(64+n)*2T,  
                                                            //                                0xc0 ~(0xc0+n), n=0~31: DTR=(32+n)*8T,   0xE0 ~(0xE0+n), n=0~31: DTR=(32+n)*16T,
            PWMA_ARRH   = 256/256;        // 自动重装载寄存器,  控制PWM周期
            PWMA_ARRL   = 256%256;

            PWMA_CCMR1  = 0x68;                // 通道模式配置, PWM模式1, 预装载允许
            PWMA_CCR1H  = 128/256;        // 比较值, 控制占空比(高电平时钟数)
            PWMA_CCR1L  = 128%256;
            ccer1 |= 0x07;                        // 开启比较输出, 低电平有效
            ps    |= 0;                                // 选择IO, 0:选择P1.0 P1.1, 1:选择P2.0 P2.1, 2:选择P6.0 P6.1,
            eno   |= 0x02;                        // IO输出允许,  bit7: ENO4N, bit6: ENO4P, bit5: ENO3N, bit4: ENO3P,  bit3: ENO2N,  bit2: ENO2P,  bit1: ENO1N,  bit0: ENO1P
    //        PWMA_ISR_En|= 0x02;                // 使能中断

            PWMA_CCER1  = ccer1;        // 捕获/比较使能寄存器1
            PWMA_CCER2  = ccer2;        // 捕获/比较使能寄存器2
            PWMA_PS     = ps;                // 选择IO
            PWMA_IER    = PWMA_ISR_En;        //设置允许通道1~4中断处理

            PWMA_BKR    = 0x80;                // 主输出使能 相当于总开关
            PWMA_CR1    = 0x81;                // 使能计数器, 允许自动重装载寄存器缓冲, 边沿对齐模式, 向上计数,  bit7=1:写自动重装载寄存器缓冲(本周期不会被打扰), =0:直接写自动重装载寄存器本(周期可能会乱掉)
            PWMA_EGR    = 0x01;                //产生一次更新事件, 清除计数器和预分频计数器, 装载预分频寄存器的值
            PWMA_ENO    = eno;                // 允许IO输出
    }
    //        PWMA_PS   = (0<<6)+(0<<4)+(0<<2)+0;        //选择IO, 4项从高到低(从左到右)对应PWM1 PWM2 PWM3 PWM4, 0:选择P1.x, 1:选择P2.x, 2:选择P6.x,
    //  PWMA_PS    PWM4N PWM4P    PWM3N PWM3P    PWM2N PWM2P    PWM1N PWM1P
    //    00       P1.7  P1.6     P1.5  P1.4     P1.3  P5.4     P1.1  P1.0
    //    01       P2.7  P2.6     P2.5  P2.4     P2.3  P2.2     P2.1  P2.0
    //    02       P6.7  P6.6     P6.5  P6.4     P6.3  P6.2     P6.1  P6.0
    //    03       P3.3  P3.4      --    --       --    --       --    --

    //========================================================================
    // 函数: void PWMB_config(void)
    // 描述: PWMA初始化函数.
    // 参数: none.
    // 返回: none.
    // 版本: V1.0, 2022-6-25
    //========================================================================
    void PWMB_config(void)
    {
            u8        ccer1;
            u8        ccer2;
            u8        ps;
            u8        eno;
            u8        PWMB_ISR_En;

            PWMB_ENO    = 0;        // IO输出禁止
            PWMB_IER    = 0;        // 禁止中断
            PWMB_SR1    = 0;        // 清除状态
            PWMB_SR2    = 0;        // 清除状态
            ccer1 = 0;
            ccer2 = 0;
            ps    = 0;
            eno   = 0;
            PWMB_ISR_En = 0;

            PWMB_PSCRH = 0x00;                // 预分频寄存器, 分频 Fck_cnt = Fck_psc/(PSCR[15:0}+1), 边沿对齐PWM频率 = SYSclk/((PSCR+1)*(AAR+1)), 中央对齐PWM频率 = SYSclk/((PSCR+1)*(AAR+1)*2).
            PWMB_PSCRL = 6;
            PWMB_ARRH  = 0;                        // 自动重装载寄存器,  控制PWM周期, PWM频率 = 35000000/(6+1)/250=20000
            PWMB_ARRL  = 250-1;

            PWMB_CCMR4  = 0x68;                // 通道模式配置, PWM模式1, 预装载允许
            PWMB_CCR8H  = 0;                // 比较值, 控制占空比(高电平时钟数)
            PWMB_CCR8L  = 87;
            ccer2 |= 0x50;                        // 开启比较输出, 高电平有效
            ps    |= (0<<6);                // 选择IO, 0:选择P2.3, 1:选择P3.4, 2:选择P0.3, 3:选择P7.7,
            eno   |= 0x40;                        // IO输出允许,  bit6: ENO8P, bit4: ENO7P,  bit2: ENO6P,  bit0: ENO5P
            PWMB_ISR_En = 0x01;                // 使能更新中断

            PWMB_CCER1  = ccer1;        // 捕获/比较使能寄存器1
            PWMB_CCER2  = ccer2;        // 捕获/比较使能寄存器2
            PWMB_PS     = ps;                // 选择IO
            PWMB_IER    = PWMB_ISR_En;        //设置允许通道1~4中断处理

            PWMB_BKR    = 0x80;                // 主输出使能 相当于总开关
            PWMB_CR1    = 0x81;                // 使能计数器, 允许自动重装载寄存器缓冲, 边沿对齐模式, 向上计数,  bit7=1:写自动重装载寄存器缓冲(本周期不会被打扰), =0:直接写自动重装载寄存器本(周期可能会乱掉)
            PWMB_EGR    = 0x01;                //产生一次更新事件, 清除计数器和预分频计数器, 装载预分频寄存器的值
            PWMB_ENO    = eno;                // 允许IO输出
    }
    //        PWMB_PS   = (0<<6)+(0<<4)+(0<<2)+0;        //选择IO, 4项从高到低(从左到右)对应PWM8 PWM7 PWM6 PWM5
    //  PWMB_PS    PWM8    PWM7    PWM6    PWM5
    //    00       P2.3    P2.2    P2.1    P2.0
    //    01       P3.4    P3.3    P5.4    P1.7
    //    02       P0.3    P0.2    P0.1    P0.0
    //    03       P7.7    P7.6    P7.5    P7.4

    //========================================================================
    // 函数: void PWMA_ISR(void) interrupt PWMA_VECTOR
    // 描述: PWMA中断处理程序. 捕获数据通过 TIM1-> CCRnH / TIM1-> CCRnL 读取
    // 参数: None
    // 返回: none.
    // 版本: V1.0, 2021-6-1
    //========================================================================
    #include        "SineTable.h"
    u8        SineIndex;
    void PWMB_ISR(void) interrupt PWMB_VECTOR
    {
            u8        sr1;

            sr1 = PWMB_SR1;        //为了快速, 中断标志用一个局部变量处理
            PWMB_SR1 = 0;        //清除中断标志
            PWMB_SR2 = 0;        //清除中断标志
            if(sr1 & 0x01)        //更新中断标志
            {
                    PWMB_CCR8L = T_SIN[SineIndex];                //P1.1输出1000Hz正弦波
                    if(++SineIndex == 20)        SineIndex = 0;
            }
    }


    回复 支持 1 反对 0 送花

    使用道具 举报

    该用户从未签到

    552

    主题

    9541

    回帖

    1万

    积分

    管理员

    积分
    14056
    发表于 2023-6-24 21:25:47 | 显示全部楼层
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    3

    主题

    15

    回帖

    83

    积分

    注册会员

    积分
    83
     楼主| 发表于 2023-6-25 11:05:17 | 显示全部楼层
    王昱顺 发表于 2023-6-24 20:48
    你好,可以试一下将这一行语句

    改成这个样子

    感谢!确实是这个问题,重新去看了一下规格书,豁然开朗,谢谢!
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    3

    主题

    15

    回帖

    83

    积分

    注册会员

    积分
    83
     楼主| 发表于 2023-6-25 11:09:24 | 显示全部楼层
    神农鼎 发表于 2023-6-24 21:24
    /*************        功能说明        **************

    本例程基于STC32G为主控芯片的实验箱9.6进行编写测试。

    谢谢朋友,我研究一下
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    3

    主题

    15

    回帖

    83

    积分

    注册会员

    积分
    83
     楼主| 发表于 2023-6-25 12:18:09 | 显示全部楼层
    神农鼎 发表于 2023-6-24 21:25
    信号发生器演示视频,STC32G12K128实验箱,老梁示波器 - STC 实验箱/核心功能实验板,原理图,MCU结构讨 ...

    已经调出,感谢各位
    884d64300b8936acb6911f8f9acc70a.jpg
    回复 支持 反对 送花

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|深圳国芯人工智能有限公司 ( 粤ICP备2022108929号-2 )

    GMT+8, 2024-5-20 13:49 , Processed in 0.083434 second(s), 68 queries .

    Powered by Discuz! X3.5

    © 2001-2024 Discuz! Team.

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