SSU_PWMOUT & PWMIN 使用参考


REVISION HISTORY

Revision No.
Description
Date
1.0
  • Initial release
  • 11/01/2022

    1. 概述

    1.1. 概述

    PWMOUT & PWMIN 主要用于电机的操控和电机转速状态反馈,PWMOUT输出PWM波形控制电机工作,PWMIN捕获PWM波形的周期占空比信息,以此形成反馈,得到电机当前的工作状态。

    1.2. 说明

    PWMOUT与同样是生成PWM波形的Traditional PWM(详见PWM使用参考)的区别在于,PWMOUT支持生成两路互补信号,基于两路互补信号能够产生一段死区时间,并且支持PWM的刹车功能。

    在介绍死区时间之前,需要了解的是,通常来说带有H桥或者三相桥的大功率电机在工作的时候,为了避免功率元件被烧毁,上半桥和下半桥是不允许同时导通,但是在实际工作的情况下,不可避免地会产生延时关断的效果,导致某个半桥在应该关断的时候没有关断,而此时另一个半桥已经打开。

    所以,为了处理这种情况,需要在某个半桥关断后,延迟一段时间再打开另一个半桥。而这个延迟时间就是死区。死区基于两路互补信号产生死区的原理是,正向信号基于PWM clock的相对上升沿产生delay,反向信号基于PWM clock的相对下降沿产生delay。PWM clock支持Traditional PWM的PWM0~PWM5通道生成。

    PWM的刹车功能是为了在发生紧急情况的时候可以立刻停止产生PWM波形,后续可以由软件恢复波形。

    PWMIN(PWM Input Capture),顾名思义,可以捕获PWM波形信息,包括周期、占空比、脉冲个数。PWMIN的原理是通过捕获PWM波形的上升沿和下降沿,从而得到PWM波形的信息,也正因如此,需要注意的是,PWMIN捕获的波形占空比范围应该在0% < duty < 100%,因为占空比为0%或者100%的时候,不存在上升沿和下降沿,无法捕捉到跳变来获取输入的PWM波形信息。

    当source clock 选择12M的时候,PWMOUT支持输出频率范围为45.78 ~ 6MHz的PWM 波形,支持长度0~85333ns的死区设定。

    当source clock选择12M的时候,为了保证波形捕获的稳定性,目前会滤除333ns以下的波形,所以PWMIN支持捕获的最大频率为3MHz。


    2. Kernel Sapce配置

    2.1. KERNEL CONFIG

    编译Kernel时:make menuconfig

    Device Drivers-->
    
        [*] SStar SoC platform drivers-->
    
            [*] PWM IN driver
            [*] PWM OUT driver
    

    2.2. DTSI配置

    PWMOUT&PWMIN在dtsi中的节点如下所示:

    1.   pwmout: pwmout {
    2.       compatible = "sstar,pwmout";
    3.       reg = <0x1F201A00 0x200>, <0x1F200E00 0x200>;
    4.       clocks = <&CLK_pwm_adc>;
    5.       interrputs = <GIC_SPI INT_FIQ_ADC_FIQ IRQ_TYPE_LEVEL_HIGH>;
    6.       frequency = <12000000>;
    7.       status = "ok";
    8.   };
    9.
    10.   pwmin: pwmin
    11.       compatible = "sstar,pwmin";
    12.       reg = <0x1F201A00 0x200>;
    13.       clocks = <&CLK_pwm_adc>;
    14.       interrputs = <GIC_SPI INT_IRQ_PWM_CAPTURE IRQ_TYPE_LEVEL_HIGH>;
    15.       status = "ok";
    16.   };
    

    2.3. PADMUX配置

    在padmux.dtsi中配置mode格式如下图的,"<>"中第一个值为PAD值,第二个值为要设置的mode,第三个值为PAD在该mode下对应的功能。

    //  PWM_OUT
    1. <PAD_PWM_OUT0    PINMUX_FOR_PWM0_PN_1    MDRV_PUSE_PWMOUT0_P>,
    2. <PAD_PWM_OUT1    PINMUX_FOR_PWM0_PN_1    MDRV_PUSE_PWMOUT0_N>,
    3. <PAD_PWM_OUT2    PINMUX_FOR_PWM1_PN_1    MDRV_PUSE_PWMOUT1_P>,
    4. <PAD_PWM_OUT3    PINMUX_FOR_PWM1_PN_1    MDRV_PUSE_PWMOUT1_N>,
    5. <PAD_PWM_OUT4    PINMUX_FOR_PWM2_PN_1    MDRV_PUSE_PWMOUT2_P>,
    6. <PAD_PWM_OUT5    PINMUX_FOR_PWM2_PN_1    MDRV_PUSE_PWMOUT2_N>,
    7. <PAD_PWM_OUT6    PINMUX_FOR_PWM3_PN_1    MDRV_PUSE_PWMOUT3_P>,
    8. <PAD_PWM_OUT7    PINMUX_FOR_PWM3_PN_1    MDRV_PUSE_PWMOUT3_N>,
    9. <PAD_PWM_OUT8    PINMUX_FOR_PWM4_PN_1    MDRV_PUSE_PWMOUT4_P>,
    10. <PAD_PWM_OUT9    PINMUX_FOR_PWM4_PN_1    MDRV_PUSE_PWMOUT4_N>,
    11. <PAD_PWM_OUT10   PINMUX_FOR_PWM5_PN_1    MDRV_PUSE_PWMOUT5_P>,
    12. <PAD_PWM_OUT11   PINMUX_FOR_PWM5_PN_1    MDRV_PUSE_PWMOUT5_N>,
    //  PWM_IN MDOE1
    1.  <PAD_KEY0        PINMUX_FOR_PWM_IN0_MODE_1   MDRV_PUSE_PWMIN0>,
    2.  <PAD_KEY1        PINMUX_FOR_PWM_IN1_MODE_1   MDRV_PUSE_PWMIN1>,
    3.  <PAD_KEY2        PINMUX_FOR_PWM_IN2_MODE_1   MDRV_PUSE_PWMIN2>,
    4.  <PAD_KEY3        PINMUX_FOR_PWM_IN3_MODE_1   MDRV_PUSE_PWMIN3>,
    5.  <PAD_KEY4        PINMUX_FOR_PWM_IN4_MODE_1   MDRV_PUSE_PWMIN4>,
    6.  <PAD_KEY5        PINMUX_FOR_PWM_IN5_MODE_1   MDRV_PUSE_PWMIN5>,
    7.  <PAD_KEY6        PINMUX_FOR_PWM_IN6_MODE_1   MDRV_PUSE_PWMIN6>,
    8.  <PAD_KEY7        PINMUX_FOR_PWM_IN7_MODE_1   MDRV_PUSE_PWMIN7>,
    //  PWM_IN MDOE2
    1.  <PAD_EMMC_D7       PINMUX_FOR_PWM_IN0_MODE_2  MDRV_PUSE_PWMIN0>,
    2.  <PAD_OUTN_TX1_CH_2 PINMUX_FOR_PWM_IN1_MODE_2  MDRV_PUSE_PWMIN1>,
    3.  <PAD_OUTP_TX1_CH_3 PINMUX_FOR_PWM_IN2_MODE_2  MDRV_PUSE_PWMIN2>,
    4.  <PAD_OUTN_TX1_CH_3 PINMUX_FOR_PWM_IN3_MODE_2  MDRV_PUSE_PWMIN3>,
    5.  <PAD_RGMII0_RXCLK  PINMUX_FOR_PWM_IN4_MODE_2  MDRV_PUSE_PWMIN4>,
    6.  <PAD_RGMII0_RXCTL  PINMUX_FOR_PWM_IN5_MODE_2  MDRV_PUSE_PWMIN5>,
    7.  <PAD_RGMII0_MDIO   PINMUX_FOR_PWM_IN6_MODE_2  MDRV_PUSE_PWMIN6>,
    8.  <PAD_RGMII0_MDC    PINMUX_FOR_PWM_IN7_MODE_2  MDRV_PUSE_PWMIN7>,
    //  PWM_IN MDOE3
    1.  <PAD_I2C5_SCL    PINMUX_FOR_PWM_IN0_MODE_3   MDRV_PUSE_PWMIN0>,
    2.  <PAD_I2C5_SDA    PINMUX_FOR_PWM_IN1_MODE_3   MDRV_PUSE_PWMIN1>,
    3.  <PAD_UART_RX1    PINMUX_FOR_PWM_IN2_MODE_3   MDRV_PUSE_PWMIN2>,
    4.  <PAD_UART_TX1    PINMUX_FOR_PWM_IN3_MODE_3   MDRV_PUSE_PWMIN3>,
    5.  <PAD_SAR_ADC_7   PINMUX_FOR_PWM_IN4_MODE_3   MDRV_PUSE_PWMIN4>,
    6.  <PAD_SAR_ADC_8   PINMUX_FOR_PWM_IN5_MODE_3   MDRV_PUSE_PWMIN5>,
    7.  <PAD_SAR_ADC_18  PINMUX_FOR_PWM_IN6_MODE_3   MDRV_PUSE_PWMIN6>,
    8.  <PAD_SAR_ADC_19  PINMUX_FOR_PWM_IN7_MODE_3   MDRV_PUSE_PWMIN7>,
    

    2.4. 驱动路径

    Kernel/drivers/sstar/pwm/drv_pwm_out.c

    Kernel/drivers/sstar/pwm/drv_pwm_in.c


    3. User Space的使用

    3.1. 互补波形和死区设置

    利用芯片内部普通pwm ip产生clock,提供给PWMOUT制造互补波形,因此配置了PWMOUT的通道,对应的普通PWM功能就不能使用,padmux中也不能配置该通道的普通PWM。

    3.1.1. 配置步骤

    1. 配置PWM clock

      1. // 以PWM$n为例
      2. echo $n > /sys/class/pwm/pwmchip0/export
      3. echo period_ns > /sys/class/pwm/pwmchip0/pwm$n/period
      4. echo duty_ns > /sys/class/pwm/pwmchip0/pwm$n/duty_cycle
      5. echo 1 > /sys/class/pwm/pwmchip0/pwm$n/enable
      
    2. enable正反向波形,可开关单根pin脚的输出波形

      1. echo $n 1 > /sys/devices/virtual/mstar/pwmout/outp_con // enable PWMn正向波形
      2. echo $n 1 > /sys/devices/virtual/mstar/pwmout/outn_con // enable PWMn反向波形
      
    3. 设置正反向波形的死区长度

      1. echo $n length > /sys/devices/virtual/mstar/pwmout/ddtp_con // 设置正向波形死区长度为length,单位ns
      2. echo $n length > /sys/devices/virtual/mstar/pwmout/ddtn_con // 设置反向波形死区长度为length,单位ns
      
    4. enable互补波形,即总开关

      1. echo $n 1 > /sys/devices/virtual/mstar/pwmout/out_en // enable PWMn的互补波形
      

    3.1.2. Sample

    1. echo 0 > /sys/class/pwm/pwmchip0/export
    2. echo 600000 > /sys/class/pwm/pwmchip0/pwm0/period
    3. echo 300000 > /sys/class/pwm/pwmchip0/pwm0/duty_cycle
    4. echo 1 > /sys/class/pwm/pwmchip0/pwm0/enable
    5. echo 0 1 > /sys/devices/virtual/mstar/pwmout/outp_con
    6. echo 0 1 > /sys/devices/virtual/mstar/pwmout/outn_con
    7. echo 0 80000 > /sys/devices/virtual/mstar/pwmout/ddtp_con
    8. echo 0 80000 > /sys/devices/virtual/mstar/pwmout/ddtn_con
    9. echo 0 1 > /sys/devices/virtual/mstar/pwmout/out_en
    

    3.2. 刹车功能

    可以通过命令触发或外部信号触发立马停止PWM的输出,并保持一种空闲电平,让电机处于停止转动的状态。其中命令触发称为sw trigger,外部信号触发称为hw trigger。外部信号触发只支持高电平触发,可复用引脚为:PAD_FUART_RTS或PAD_OUTN_TX_CH_4,在使用外部信号触发功能之前需要先配置PADMUX,两只脚选择其一进行配置。

    1.  <PAD_FUART_RTS       PINMUX_FOR_PWM_INT_MODE_1   MDRV_PUSE_PWM_INT>,
    2.  <PAD_OUTN_TX_CH_4    PINMUX_FOR_PWM_INT_MODE_2   MDRV_PUSE_PWM_INT>,
    

    3.2.1. 配置步骤

    1. 设置PWM$n的刹车触发方式:1表示sw&hw trigger,0表示sw trigger;设置空闲电平:1表示高电平,0表示低电平

      1. echo $n trigger_mode idle_status > /sys/devices/virtual/mstar/pwmout/bkin_con
      
    2. 命令触发PWM$n的刹车功能

      1. echo $n > /sys/devices/virtual/mstar/pwmout/bkin_tri
      
    3. 获取当前刹车状态,打印“break input active”表示目前处于刹车状态,打印“break input inactive”表示目前处于非刹车状态

      1.  echo $n > /sys/devices/virtual/mstar/pwmout/bkin_status
      
      2.  cat  /sys/devices/virtual/mstar/pwmout/bkin_status
      
    4. 恢复PWM$n的波形

      1. echo $n 1 > /sys/devices/virtual/mstar/pwmout/out_en
      

    3.2.2. Sample

    1. echo 0 1 0 > /sys/devices/virtual/mstar/pwmout/bkin_con
    2. echo 0 > /sys/devices/virtual/mstar/pwmout/bkin_tri
    3. echo 0 1 > /sys/devices/virtual/mstar/pwmout/out_en
    

    3.3. 捕获功能

    捕获输入的波形并计算出占空比和周期。

    3.3.1. 配置步骤

    1. disable channel$n的input capture功能

      1. echo $n 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
      
    2. 设置为每2^k个脉冲再进行捕获波形的信息计算,k越大计算精度越高,k支持设置为0、1、2、3。设置时需要先关闭channel$n的input capture功能。

      1.  echo $n k > /sys/devices/virtual/mstar/pwmin/pwm_in_pul_div
      
    3. enable channel$n的input capture功能

      1. echo $n 1 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
      
    4. 获取捕获信息

      1. echo $n > /sys/devices/virtual/mstar/pwmin/pwm_in_get
      2. cat /sys/devices/virtual/mstar/pwmin/pwm_in_get
      

    3.3.2. Sample

    1. echo 0 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
    2.  echo 0 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_pul_div
    3. echo 0 1 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
    4. echo 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_get
    5. cat /sys/devices/virtual/mstar/pwmin/pwm_in_get
    

    3.4. 脉冲计数

    根据设置的触发边沿类型,对脉冲个数进行计数。

    3.4.1. 配置步骤

    1. disable channel$n的input capture功能

      1. echo $n 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
      
    2. 选择channeln计数的边沿类型,edge为0表示下边沿,1表示上边沿,2表示双边沿。设置时需要先关闭channeln的input capture功能。

      1. echo $n enable edge > /sys/devices/virtual/mstar/pwmin/pwm_in_pul_cal
      
    3. enable channel$n的input capture功能

      1. echo $n 1 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
      
    4. 获取脉冲个数,获取后计数还会继续,计满0xFFFF个脉冲刷新计数值,可使用上述命令2将计数功能disable来主动清零,再enable开启新一轮计数。

      1. echo $n > /sys/devices/virtual/mstar/pwmin/pwm_in_get_pul
      

    3.4.2. Sample

    1. echo 0 1 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
    2. echo 0 1 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_pul_cal
    3. echo 0 1 > /sys/devices/virtual/mstar/pwmin/pwm_in_en
    4. echo 0 > /sys/devices/virtual/mstar/pwmin/pwm_in_get_pul