This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] MSP430FR2675:TA0.1生成具有双预期周期的 PWM

Guru**** 1127450 points
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/microcontrollers/msp-low-power-microcontrollers-group/msp430/f/msp-low-power-microcontroller-forum/1025440/msp430fr2675-ta0-1-produces-pwm-with-double-expected-period

器件型号:MSP430FR2675
主题中讨论的其他器件:MSP430WARE

我使用 driverlib SDKTimer_A_outputPWM() 函数在 TA0.1上生成 PWM 信号。  PWM 信号以正确的占空比产生、但周期是我预期的两倍。

根据我的计算、周期应为20ms、但生成的波形的周期为40ms。  SMCLK 以大约2MHz 的频率运行。  我已使用验证了这一点CS_getSMCLK()。  我要将时钟信号除以40、再除以50 KHz。  1000 / 50 KHz 应该是20毫秒、还是我缺少什么?

GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P1, GPIO_PIN1, GPIO_SECONDARY_MODULE_FUNCTION);
Timer_A_outputPWMParam TimerParams;
TimerParams.clockSource = TIMER_A_CLOCKSOURCE_SMCLK;
TimerParams.clockSourceDivider = TIMER_A_CLOCKSOURCE_DIVIDER_40;
TimerParams.timerPeriod = 1000 - 1;
TimerParams.compareRegister = TIMER_A_CAPTURECOMPARE_REGISTER_1;
TimerParams.compareOutputMode = TIMER_A_OUTPUTMODE_RESET_SET;
TimerParams.dutyCycle = 750;
Timer_A_outputPWM(TA0_BASE, &TimerParams);
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我添加了一个包装程序、并在 FR2476上运行它、这大概是同一代。 我得到20ms 的周期。

    建议是在该代码之外执行一些操作。 如何设置 SMCLK? 您可以尝试在 P1.7上输出 SMCLK。

    #include "driverlib.h"
    uint32_t SMCLK_Hz;
    int main(void) {
        WDT_A_hold(WDT_A_BASE);
    
        //  SMCLK=2MHz
        __bis_SR_register(SCG0);                // disable FLL
        CSCTL3 |= SELREF__REFOCLK;              // Set REFO as FLL reference source
        CSCTL1 = DCOFTRIMEN_1 | DCOFTRIM0 | DCOFTRIM1 | DCORSEL_1;// DCOFTRIM=3, DCO Range = 2MHz
        CSCTL2 = FLLD_0 + 60;                  // DCODIV = 2MHz
        __delay_cycles(3);
        __bic_SR_register(SCG0);                // enable FLL
        CSCTL4 = SELMS__DCOCLKDIV | SELA__REFOCLK; // set default REFO(~32768Hz) as ACLK source, ACLK = 32768Hz
        SMCLK_Hz = CS_getSMCLK();
    
        //  Run PWM on P1.1 (TA0.1)
        PM5CTL0 &= ~LOCKLPM5;
        GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P1, GPIO_PIN1, GPIO_SECONDARY_MODULE_FUNCTION);
        Timer_A_outputPWMParam TimerParams;
        TimerParams.clockSource = TIMER_A_CLOCKSOURCE_SMCLK;
        TimerParams.clockSourceDivider = TIMER_A_CLOCKSOURCE_DIVIDER_40;
        TimerParams.timerPeriod = 1000 - 1;
        TimerParams.compareRegister = TIMER_A_CAPTURECOMPARE_REGISTER_1;
        TimerParams.compareOutputMode = TIMER_A_OUTPUTMODE_RESET_SET;
        TimerParams.dutyCycle = 750;
        Timer_A_outputPWM(TA0_BASE, &TimerParams);
    
        while (1)
        {
            LPM0;
        }
        /*NOTREACHED*/
        return (0);
    }
    

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    谢谢您。  我已确定中的返回值(~4MHz)CS_getSMCLK()与测量的 SMCLK 值(~2MHz)不一致。  测得的2MHz 值就是我所期望的值。  中的错误值CS_getSMCLK()是影响我计算的结果。  您对CS_getSMCLK()为什么返回错误值有什么想法吗?  可能是 driverlib 中的错误?

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!  

    您是否使用外部时钟/晶体?  我看到有一条有关 cs_getSMCLK()的注释,如果使用外部时钟源,则需要首先调用 CS_setExternalClockSource() API。   

    谢谢、

    JD

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    否、仅使用内部振荡器。  SMCLK 由 DCO 驱动。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我相信 getSMCLK 大部分时间都能正常工作、因此听起来好像你跳过了一种欺骗方法。 这就是为什么我想知道你为设置它所做的什么。

    getSMCLK 根据当前 CS 设置从"第一原则"计算数字。 在我的案例中、它是正确的(1998848 Hz)。 那里有很多代码、因此了解您的 CS 设置实际上会让我有一个头像头。

    [编辑:我可能还应该问您使用的是哪个版本的 driverlib (MSP430Ware)。 我使用的是3.80.13.03。]

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    真有意思。  我相信我正在使用较旧版本的 MSP430Ware;它是使用 BOOSTXL-CAPKEYPAD 的演示代码预编译的。  version.h 文件。 表示我使用的是2.91.12.08。  我可以尝试更新。  但是、我认为 version.h 文件可能不会保持最新。  我机器上的 MSP430Ware 安装文件夹指示版本3.80.13.03、但 MSP430Ware_3_80_13_03/driverlib/driverlib/MSP430FR2xx_4xx/inc/version.h 下的版本文件指示版本2.21.13.01。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    我尝试更新到 MSP430Ware_3_80_13_03、但问题仍然存在。  随附了我的 board.c 文件、其中包含时钟初始化代码。  它基本上从   BOOSTXL-CAPKEYPAD 的演示代码中删除 、但进行了一些小的修改以支持 printf。

     当附加文件中用于启用 printf 的代码被禁用时 ,CS_getSMCLK()返回正确的值。  但是   ,当启用 printf 的代码被激活时,CS_getSMCLK()返回错误的双倍值。  在这两种情况下、测得的 SMCLK 频率都是正确的。

    e2e.ti.com/.../2781.board.c

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    在我看来,它就像 getSMCLK 中的一个错误--我没有看到任何东西说明 SMCLK 分频器不仅是(仅) DIVS,而是(DIV* DIVM)。 [参考用户指南(SLAU445I)图3-2和表3-9]

    任何时候都是如此  

    > CS_initClockSignal (CS_MCLK、CS_DCOCLKDIV_SELECT、CS_CLOCK 分频器_2);

    使用 CS_Clock_divider 1以外的任何内容调用、它将由该分频器因子关闭。 可能的修补程序是将此修补程序添加到 CS_getSMCLK 中(在 cs.c:1040之后):

    #if 1 || BMC
        uint16_t MCLKSourceDivider =  HWREG16(CS_BASE + OFS_CSCTL5) & DIVM_7;
        SMCLKSourceDivider += (MCLKSourceDivider >> 0); // 2^(DIVM+DIVS) implied
    #endif
    

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    该补丁程序似乎可以解决问题。  BMC 的意义是什么

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    BMC 就是 Bruce MCKenney。 我想用某种方式标记它、但不想太杂乱。

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    感谢 Bruce