神农鼎 发表于 2022-12-8 09:46:58

如何让PWM输出0 | 见 数据手册

有研发问: 怎么让 PWM 输出 0
===我找了下芯片手册





神农鼎 发表于 2022-12-8 09:55:53

不知从数据手册中找到的内容是否能回答上述用户问题,要等梁工,陈工,他们确认,我已不是研发多年

梁工 发表于 2022-12-8 13:46:44

PCA-PWM连续输出0或1的方法,以PCA0(PWM0-CCP0)为例:
PCA_PWM0 &= ~0x02;        // PWM0正常输出
PCA_PWM0 |= 0x3f, CCAP0H = 0xff, CCAP0L = 0xff;        // PWM0一直输出0
PCA_PWM0 &= 0xc0, CCAP0H = 0,    CCAP0L = 0;        // PWM0一直输出1
===========================================

STC8A8K64D4的8路15位增强型PWM,连续输出0或1有3种方法(以PWM0--P1.0为例):

1、禁止输出PWM,对应IO成为普通IO,禁止PWM输出后,由这个IO直接输出高或低电平。
PWM0CR |= 0x80;   // ENO=1:允许PWM输出
delay_ms(5);      // PWM输出5ms
P10 = 1;          // 连续输出高电平
PWM0CR &= ~0x80;// ENO=0:禁止PWM输出
delay_ms(5);      // P1.0输出高电平5ms
               
PWM0CR |= 0x80;   // ENO=1:允许PWM输出
delay_ms(5);      // PWM输出5ms
P10 = 0;          // 连续输出低电平
PWM0CR &= ~0x80;// ENO=0:禁止PWM输出
delay_ms(5);      // P1.0输出低电平5ms

2、PWM0T2设置输出高电平时刻,PWM0T1设置输出低电平时刻,PWM0T1-PWM0T2就是输出高电平时间。
   如果将PWM0T1设置的数值比周期值大,则连续输出高电平,输出100%占空比。
   如果将PWM0T2设置的数值比周期值大,则连续输出低电平,输出0%占空比。

3、使用“PWM通道电平保持控制寄存器 PWMnHLD”直接设置输出高或低,
   这个寄存器就是专门用于设置连续输出高或低的。
   PWM0HLD = 0x00;//PWM正常输出
   PWM0HLD = 0x01;//PWM输出连续低电平
   PWM0HLD = 0x02;//PWM输出连续高电平
===========================================

STC8G2K64S4的45路15位增强型PWM,连续输出0或1有3种方法(以PWM00为例):

1、禁止输出PWM,对应IO成为普通IO,禁止PWM输出后,由这个IO直接输出高或低电平。
PWM00CR |= 0x80;   // ENO=1:允许PWM输出
delay_ms(5);       // PWM输出5ms
P00 = 1;         // 连续输出高电平
PWM00CR &= ~0x80;// ENO=0:禁止PWM输出
delay_ms(5);       // P0.0输出高电平5ms
               
PWM00CR |= 0x80;   // ENO=1:允许PWM输出
delay_ms(5);       // PWM输出5ms
P00 = 0;         // 连续输出低电平
PWM00CR &= ~0x80;// ENO=0:禁止PWM输出
delay_ms(5);       // P0.0输出低电平5ms

2、PWM00T2设置输出高电平时刻,PWM00T1设置输出低电平时刻,PWM00T1-PWM00T2就是输出高电平时间。
   如果将PWM00T1设置的数值比周期值大,则连续输出高电平,输出100%占空比。
   如果将PWM00T2设置的数值比周期值大,则连续输出低电平,输出0%占空比。

3、使用“PWM通道电平保持控制寄存器 PWMnHLD”直接设置输出高或低,
   这个寄存器就是专门用于设置连续输出高或低的。
   PWM00HLD = 0x00;//PWM正常输出
   PWM00HLD = 0x01;//PWM输出连续低电平
   PWM00HLD = 0x02;//PWM输出连续高电平
===========================================

STC8H系列的高级PWM,连续输出0或1有2种方法(以PWM1P为例):

1、使用PWMx_ENO禁止输出PWM,对应IO成为普通IO,禁止PWM输出后,由这个IO直接输出高或低电平。
PWMA_ENO |= 0x01;   // 允许PWM1P输出
delay_ms(5);      // P1.0输出PWM 5ms
P10 = 1;            // P1.0输出高电平
PWMA_ENO &= ~0x01;// 关闭PWM输出
delay_ms(5);      // P1.0输出高电平5ms
               
PWMA_ENO |= 0x01;   // 允许PWM1P输出
delay_ms(5);      // P1.0输出PWM 5ms
P10 = 0;            // P1.0输出低电平
PWMA_ENO &= ~0x01;// 关闭PWM输出
delay_ms(5);      // P1.0输出高电平5ms

2、设置PWMx_CCMRn,强制PWM输出有效(高)电平/无效(低)电平。
PWMA_CCMR1 = (PWMA_CCMR1 & ~0x70) | 0x60;// PWM正常输出
delay_ms(5);                               // PWM输出5ms
PWMA_CCMR1 = (PWMA_CCMR1 & ~0x70) | 0x40;// 强制PWM输出无效(低)电平
delay_ms(5);                               // PWM输出低电平5ms
PWMA_CCMR1 = (PWMA_CCMR1 & ~0x70) | 0x60;// PWM正常输出
delay_ms(5);                               // PWM输出5ms
PWMA_CCMR1 = (PWMA_CCMR1 & ~0x70) | 0x50;//强制PWM输出有效(高)电平
delay_ms(5);                               // PWM输出高电平5ms

菜鸟大神 发表于 2023-2-11 20:58:56

梁工 发表于 2022-12-8 13:46
PCA-PWM连续输出0或1的方法,以PCA0(PWM0-CCP0)为例:
PCA_PWM0 &= ~0x02;        // PWM0正常输出
PCA_PWM0 |= 0x ...

STC32 如何处理呢

神农鼎 发表于 2023-2-11 21:22:08


神农鼎 发表于 2023-2-11 21:24:55

STC32的PWM 同 STC8H的PWM

梁工 发表于 2023-2-12 10:54:45

对的,STC32G的PWM处理方式与上面“STC8H系列的高级PWM,连续输出0或1有2种方法”的一样。

alanma 发表于 2024-3-10 20:51:03

本帖最后由 alanma 于 2024-3-10 21:03 编辑

梁工 发表于 2022-12-8 13:46
PCA-PWM连续输出0或1的方法,以PCA0(PWM0-CCP0)为例:
PCA_PWM0 &= ~0x02;      // PWM0正常输出
PCA_PWM0 |= 0x ...
我也遇到同样的问题,可否帮看下代码地方有问题?
;******************************************/

$include (/STC8H.INC)

;====================
STACK_POIRTER   EQU   0D0H    ;堆栈开始地址

;*************本地变量声明    **************/
PWM1_Flag       BIT   20H.0
PWM1_Duty_H   DATA    30H
PWM1_Duty_L   DATA    31H
INT_TIME BIT 20H.1

;*******************************************************************
;*******************************************************************
      ORG   0000H               ;reset
      LJMP    F_Main

      ORG   000BH               ;1Timer0 interrupt
      LJMP    F_Timer0_Interrupt

;******************** 主程序 **************************/
      ORG   0100H       ;reset
F_Main:
    ORL   P_SW2, #080H    ;扩展寄存器(XFR)访问使能

    MOV   P0M0,#07H                   ;设置P0.3为高阻输入,P0.0-0.2为推挽输出
    MOV   P0M1,#08H
    MOV   P1M0,#01H                  ;设置P1.0为推挽输出模式,P1.1,P1.3,P1.4,P1.6,P1.7为高阻输入
    MOV   P1M1,#0DAH
    MOV   P2M0,#07H                   ;设置P2.0~P2.2为推挽输出
    MOV   P2M1,#00H
    MOV   P3M0,#08H                  ;设置P3
    MOV   P3M1,#00H
    MOV   P4M0,#00H                  
    MOV   P4M1,#00H
      MOV   P5M0,#10H                  ;设置P5.4为推挽输出
    MOV   P5M1,#00H
    MOV   SP, #STACK_POIRTER
    MOV   PSW, #0
    USING   0       ;选择第0组R0~R7
   
    MOV   SP, #STACK_POIRTER
    MOV   PSW, #0
    USING   0       ;选择第0组R0~R7
                        
      CLR P3.6;测试用

;================= 用户初始化程序 ====================================
    CLR   PWM1_Flag

    MOV   PWM1_Duty_L, #0
    MOV   PWM1_Duty_H, #0

    CLR   TR0

      MOV TMOD,#00000001B       ;置T1为方式1,16位自动重载定时方式,置T0为方式1,16为不自动重载定时方式,         
       MOV TL1,#0C0H               ;T1定时20ms
      MOV TH1,#063H
      MOV TL0,#0E0H            ;定时10mS常数
      MOV TH0,#0B1H
      SETB ET0                                                                        
                SETB TR0
      SETB EA                   ;开中断
      
    LCALL   F_PWM_Init          ; PWM初始化

;=================== 主循环 ==================================
L_Main_Loop:

    LJMP    L_Main_Loop

;========================================================================
; 函数: F_PWM_Init
; 描述: PWM初始化程序.
; 参数: none
; 返回: none.
; 版本: V1.0, 2021-3-3
;========================================================================
F_PWM_Init:
    CLR   A                   ;写 CCMRx 前必须先清零 CCxE 关闭通道
    MOV   DPTR,#PWMA_CCER1
    MOVX    @DPTR,A

      
    MOV   A,#068H             ;设置 PWMx 模式1 输出
    MOV   DPTR,#PWMA_CCMR1
    MOVX    @DPTR,A

      
    MOV   A,#03H             ;配置通道输出使能和极性
    MOV   DPTR,#PWMA_CCER1
    MOVX    @DPTR,A

    MOV   A,#3                ;设置周期时间
    MOV   DPTR,#PWMA_ARRH
    MOVX    @DPTR,A
    MOV   A,#0FFH
    MOV   DPTR,#PWMA_ARRL
    MOVX    @DPTR,A

    MOV   A,#01H             ;使能 PWM1P 输出
    MOV   DPTR,#PWMA_ENO
    MOVX    @DPTR,A
   
    MOV   A,#01H            ;高级 PWM 通道输出脚选择位, P2.0为01H,P1.0为00H
    MOV   DPTR,#PWMA_PS
    MOVX    @DPTR,A

   MOV   A,#080H             ;使能主输出
    MOV   DPTR,#PWMA_BKR
    MOVX    @DPTR,A

    MOV   DPTR,#PWMA_CR1
    MOVX    A,@DPTR
    ORL   A,#01H            ;开始计时
    MOVX    @DPTR,A      
   
    RET

;========================================================================
; 函数: F_UpdatePwm
; 描述: 更新PWM占空比值.
; 参数: : pwm占空比值.
; 返回: none.
; 版本: V1.0, 2021-3-3
;========================================================================
F_UpdatePwm:
    MOV   A, PWM1_Duty_H      ;设置占空比时间
    MOV   DPTR, #PWMA_CCR1H
    MOVX    @DPTR, A
    MOV   A, PWM1_Duty_L
    MOV   DPTR, #PWMA_CCR1L
    MOVX    @DPTR, A

    RET

;**************** 中断函数 ***************************************************
F_Timer0_Interrupt: ;Timer0 1ms中断函数
    PUSH    PSW   ;PSW入栈
    PUSH    ACC   ;ACC入栈
   
      CLR TR0
    MOV      TL0,#00H      ;T0定时10毫秒
    MOV      TH0,#00H
      
      CPL INT_TIME
      MOV C,INT_TIME
      JCF_INT2
      
    MOV   A,#0H             ;关闭PWM输出
    MOV   DPTR,#PWMA_ENO
    MOVX    @DPTR,A            
      NOP
      NOP
      CLR P2.0                  ;输出脚拉低      
      
    JMP INT_END
      
      
F_INT2:
      
      MOV   A,#01H             ;使能 PWM1P 输出
    MOV   DPTR,#PWMA_ENO
    MOVX    @DPTR,A
    JMP INT_END

F_QuitTimer0:
    LCALL   F_UpdatePwm
      INT_END:
      SETB TR0
    POP   ACC   ;ACC出栈
    POP   PSW   ;PSW出栈
    RETI


;======================================================================

    END

神农鼎 发表于 2024-3-10 21:20:31


神农鼎 发表于 2024-3-10 21:22:05








页: [1] 2
查看完整版本: 如何让PWM输出0 | 见 数据手册