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.

Two PWM signals with Dead time. MSP430G2452 (another PWM post)

Other Parts Discussed in Thread: MSP430G2452, MSP430F2011, MSP430F2013, MSP430F477, MSP430G2553

Hello,

 

i am using the MSP430G2452, i have it in the Launch Pad and am trying to use it to produce two PWM signals that are comliments of eachother with some dead-time between transitions. The chip has one Timer0_A3 and 3 CC registers so its should be able to do it.

i have looked in the family user guide and want to do something like the picutre below (pg.364 of the MSP430x2xx family user guide)

IThis is my code

#include  <msp430g2452.h>

void main(void)
{
  WDTCTL = WDTPW + WDTHOLD;                 // Stop WDT
 
  P1DIR |= 0x06;                            // P1.2 and P1.1 to output
  P1SEL |= 0x06;                           
 
  CCR0 = 1000;     //PWM Period - Freq = (SMCLK freq)/(CCR0 value)
                                 //eg,SMCLK = 1MHZ so 1MHZ/1000 = 1Khz is the PWM Freq
  CCTL1 = OUTMOD_6;                         //CCR1 toggle/set
  CCTL2 = OUTMOD_2;                            //CCR2 toggle/reset
  CCR1 = 250;                               //CCR1 PWM duty cycle
  CCR2 = 50;                                //Dead time = CCR1 - CCR2 = 250 - 50 = 200
  TACTL = TASSEL_2 + MC_3; // TACTL = timer_A ctrl, TASSEL_2 = SMCLK, MC_3 = up/down mode

  _BIS_SR(LPM0_bits);                        // Enter LPM0
}

 

I can see the PWM on P1.2 but not on P1.1, obviously there is something wrong with my code, i was wondering if anyone could help me. I have looked at alot of the PWM dead-time related forum topics

http://e2e.ti.com/support/microcontrollers/msp43016-bit_ultra-low_power_mcus/f/166/p/19031/73691.aspx#73691

http://e2e.ti.com/support/microcontrollers/msp43016-bit_ultra-low_power_mcus/f/166/p/56142/205122.aspx#205122

http://e2e.ti.com/support/microcontrollers/msp43016-bit_ultra-low_power_mcus/f/166/p/104860/369006.aspx#369006

http://e2e.ti.com/support/microcontrollers/msp43016-bit_ultra-low_power_mcus/f/166/p/116416/413109.aspx#413109

But can't really seem to get it working

 

Thanks in advance

Michael Dalton

  • Michael Dalton said:
    I can see the PWM on P1.2 but not on P1.1

    For a reason: P1.1 is connected with TA0.0, that is the output of the CCR0 unit. Your second PWM is from CCR2 which is the TA0.2 signal on P1.4.

    So
      P1DIR |= 0x14;                            // P1.2 and P1.4 to output
      P1SEL |= 0x14;                           
    should do the trick.

    And of course the two PWMs are on (physical) pin 4 and 6 and not on pin 3 and 4.

  • Jens-Michael Gross said:

    I can see the PWM on P1.2 but not on P1.1

    For a reason: P1.1 is connected with TA0.0, that is the output of the CCR0 unit. Your second PWM is from CCR2 which is the TA0.2 signal on P1.4.

    So
      P1DIR |= 0x14;                            // P1.2 and P1.4 to output
      P1SEL |= 0x14;                           
    should do the trick.

    And of course the two PWMs are on (physical) pin 4 and 6 and not on pin 3 and 4.

    [/quote]

    Hey Jens,

    I changed the code to reflect what you suggested, Below are the waveforms coming from P1.2(CH1) and P1.4(CH2)

    CH1 is behaving properly i.e. duty cycle of 75% with a frequency of [(SMCLK/CCR0)/2] = [(1MHz/1000)/2] = 500Hz

    But CH2 (P1.4) is outputting a waveform at 50% duty cycle with a frequency of SMCLK. I have tried changing the value for CCR2 but this seems to change nothing. I have also tried changing the mode for CCTL2 but with no results. Below is the waveform of CH2 (P1.4)

     

    Do you have any suggestions?

     

    Regards

    Michael Dalton

  • Hi Michael,

    Here's a snippet from the data sheet.  Looks like you must also set BIT4 in the P1SEL2 register (but not BIT2).

    This table also explains why you saw SMCLK on P1.4.  It gets tricky keeping track of all the pin configurations.

    Jeff

  • Jeff Tenney said:

    Hi Michael,

    Here's a snippet from the data sheet.  Looks like you must also set BIT4 in the P1SEL2 register (but not BIT2).

    This table also explains why you saw SMCLK on P1.4.  It gets tricky keeping track of all the pin configurations.

    Jeff

     

    Jeff,

    Thanks that was it!!! :)

    So if anyone is interested the code remains the same at the start except for these lines (plus one)

    P1DIR |= 0x14;

    P1SEL |= 0x14;

    P1SEL2 |= BIT4;

    The following pictures show CCR2 at different values

    Here CCR2 = 220, so the dead time = CCR1 - CCR2 = 250 - 220 = 30

    Here CCR2 = 100, so the dead time = CCR1 - CCR2 = 250 - 100 = 150

     

    Thanks again, Jeff and Jens

    Regards

    Michael Dalton

  • Hi Guys

    I am using MSP430F2011, why I cannot use CCR2 on this part ??

    Thanks

  • Because it only has 2 capture and compare registers (CCR0 and CCR1).

  • Thanks, Bernhard

    The reason of my question is, I have a code( part  of it is bellow)  that generates 1Khz PWM all the time, which generates an interrupt every 300000. In other words it does some type of mathematic calculation and keeps tracking of solar power of solar panel for the entire day doing it every 5 minutes. I want to be able to hook up an eZ430 board and use its UART to monitor through a software called realterm so I can data log over the days. I am no so familiar with UART but every example I saw and try has something to do with the Time_A so it interferes to the code, because at night the code goes to this subroutine putting out the PWM throughout P1.6 which then controls a LED driver so when it happens because the UART part of the code the LED start to blink and the PWM of 1Khz goes crazy. Any sugetion ???

    Thanks

    Bellow is part of the code..

     

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

    //PWM Frequency 1Khz

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

    #define PWM_PERIOD 1000

    //

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


    //Configure IO

      P1OUT &= ~ 0X40;                         // Sets the output to low GPIO//P1OUT &= ~ 0X40;                            // Sets the output to low GPIO

      P1DIR |= 0X40;                             // Set pin P1.6 to output direction//P1DIR |= 0X40;

      P1SEL &= ~0x40;                           // Turn LED ON//P1SEL &= ~0x40;                          // Turn LED OFF

     

     

     

    //Configure timer A

      TACCTL0 = CCIE;                                               // TACCR0 interrupt enabled

      TACCTL1 = OUTMOD_7;                                   // TACCR1 Reset/Set

      TACCR0 = PWM_PERIOD;                                // Set PWM for 1Khz operation

      TACCR1 = PWM_PERIOD >> 1;                        // Start with 50% duty cycle

      TACTL = TASSEL_2 + MC_1 + TACLR;              // SMCLK (1MHz), Clear TAR, Up mode

     

     

    //Main loop starts here

      while(1)

      {

      SD16CCTL0 |= SD16SC;                   // Set bit to start conversion

     _BIS_SR(LPM0_bits + GIE);               // Enter LPM0 take off  _BIS_SR(LPM0_bits + GIE);

     

    //LED driver control starts here

        if (Solar_Volts >= 5024)                                                             // If Solar panel is more than  1 Volts turn LED OFF;

           P1SEL &= ~0x40;                                                                     // Turn LED OFF;

        if ((Solar_Volts >= 15072) && (Bat_Volts >= 25170))        // If solar  Vp = 3 Volts // battery Vbat = 5.01 Volts, reset the code, in other words consider battery is above 3 V so wait for dark then turn LED ON; 

           i = 1;                                                                      // Reset i = 1;

        if (Bat_Volts <= 25170)                                        // If Battery is less than 5.01 Volts;

        {    

           i = 0;                                                                  // i = 0;

           P1SEL &= ~0x40;                                         // Turn LED OFF;P1SEL &= ~0x04

        }

        if ((Solar_Volts <= 3014) && (Bat_Volts >= 25170) && (i))  //4521   3014=600mV

        {      

           TACCR1 =  535;                                                                               //305 = 30% = 120mA

           P1SEL |= 0x40;                                                                                  // Turn  LED ON;

        }

      }

     

     

    // Timer A0 interrup service routine

      #pragma vector = TIMERA0_VECTOR

    __interrupt  void Timer_A (void)

    {

        pwmCycles++;               //Increment PWM cycle count

        if(pwmCycles == 300000)    //Has 5 minuts passed

        {

           Power_Count();          //Do the Power calculation

           pwmCycles = 0;          //Reset the counter

        }

    }


     

  • marcelo deoliveira said:
    I am no so familiar with UART but every example I saw and try has something to do with the Time_A


    This is because the 2011 does not have an UART. So it uses a tiemr to trigger interrupts when a bit should be sent,, and uses a tiemr to keep track of input line changes to calculate the incoming bits. This is called a 'sfotware uart'. And yes, software UART and PWM interfere with each other.
    I don't know whether the typical software UART requires two CCR units (all the 2011 has). I think it could be done with just one, and  alittle bit more math or RX error.
    However, if you know the UART timer tick and interrupt frequency, you may be able to combine a software UART and your long-time timer wakeup.

    Also, there's nothing that keeps you from switchign between two uses, if you don't need them at the same time.

  • Thanks Jens

    I am actually using MSP430F2013. I am using the 16-Bit Sigma-Delta A/D Converter of it as well for 3 channels, do you know any other part that would allow me to do Timer_A and UART independent of each other keeping the 16_Bit Sigma-Delta software  ?

    Thanks 

     

  • It looks like there are no 2x family devices with both, SD16 and hardware UART.
    At least not according to the selection guide.

    There are several 4x family devices with this combination, e.g. the MSP430F477.

    Be aware that there might be subtle differences between families.

     

     

  • Thanks Jens

    Do you know and have any piece of code that I can connect a MSP430F2013 to the PC and monitor 3 ADC SD16. I need to see in real time what is going on, I am going back and forth and cannot get this done.

    Thanks 

     

  • Sorry, I never used an MSP with SD16 myself.
    And all my projects with ADC usage were based on ADC12.

  • why you are using there Two OUTMODS.  (OUTMOD_2, OUTMOD_6)

  • Jens-Michael Gross said:
    It looks like there are no 2x family devices with both, SD16 and hardware UART.

    If only UART TX needed, then easy and elegant solution is to emulate UART using USI peripheral. In case you are able to calibrate DCO for let's say, 1.2288 MHz (which is doable too) then sending byte out of USI in SPI mode is piece of cake:

    // Use USI in SPI mode, clock SMCLK/128 = 9600bps

    USISR = (TXbyte << 1) | 0xFE00; // Sets word to be sent, formats with start and stop bits
    USICNT = USI16B + 11; // 16 bit mode, sends 11 bits ( 1start + 8data + 2stop )
    while (!(USIIFG & USICTL1))
      ;

  • Thank you.

     But I have some of confusions on Emulation Can you give Some Explanation of That.

  • Mallappa Tarageri said:
     But I have some of confusions on Emulation Can you give Some Explanation of That.

    First read about emulation here http://en.wikipedia.org/wiki/Emulation

    Then here http://e2e.ti.com/search/default.aspx#q=emulator&g=93

    Only then ask if you are still confused.

  • Hi,

    will this work in case of MSP430G2553.

    I want to generate two pwm signal with 180 degree phase shift using msp430g2553 launchpad.

    Thanks in advance..!!

  • >I want to generate two pwm signal with 180 degree phase shift using msp430g2553 launchpad.

    Yes. You shall set dead time to 0 and will get what you are looking for. There's another option using up mode

  • void timer_init(void)

    {

     P2DIR |= BIT1|BIT4;                          //set as output pin P2.1/TA1.1(O/P OF CCR1 Register), P2.4/TA1.2(O/P OF CCR2 Register)

     P2SEL |= BIT1|BIT4;                         //pin selected for special purpose; here for pwm

     TA1CTL |= TASSEL_2 + MC_3;       //SMCLK and up down mode

    TA1CCR0 |= 160 ;                             //pwm frequency 100 khz; DCO = MCLK = SMCLK = 16 Mhz i.e. 16M/160 = 100KHZ

     TA1CCR1 |= Duty;                              //VARIABLE Duty cycle

     TA1CCR2 |= Duty;                               // VARIBLE Duty Cycle

     TA1CCTL1 |= OUTMOD_6;               // TA1CCR1, toggle/set

     TA1CCTL2 |= OUTMOD_2;              // TA1CCR2, toggle/reset

    }

    As per your guideline i have written the timer configuration. is it correct?

    Pin Diagram:

    NOTE: I have used TIMER_A1 in UP DOWN MODE and i want the output as shown below.

     

  • >As per your guideline i have written the timer configuration. is it correct?
    Scope will tell. You shall load your code into msp and measure output.
  • I don't have oscilloscope to check the output right now.

    Is there any other method to verify the same other then using oscilloscope??

    Thank you in advance.!!

  • AMIT said:
    Is there any other method to verify the same other then using oscilloscope

    You can attach some basic logic on the two lines. An OR will get a constant high (maybe with glitches at the switchng point), an AND will get a constant low (again with glitches) , an XOR will also give a constant high. You can measure the output wiht a normal multimeter. The direct output measured with a multimeter shoudl give you 50% of VCC while the logic gate outputs will give you VCC or 0V

    I'd prefer a scope, but if you don't have access to it, this is the second best that comes in mind.

  • >I don't have oscilloscope to check the output right now.
    In such case you can use your eyes. - Connect LEDs to all outputs you want to monitor and run timer(s) from very slow clock so you are able to discern how LEDs are blinking.

**Attention** This is a public forum