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.

msp430Fr6879: I2c interfacing

Part Number: MSP430FR6879
Other Parts Discussed in Thread: MSP430FR6879

i am trying to use an rtc (idt1338) and  have interfaced it with msp430fr6879  via I2c protocol . The problem that i am facing is that sometimes , most of the times my code does not enters the I2c interrupt routine. that is the communication is not established. But once the communication gets established that is it enters the switch case of the interrupt routine everything works fine , but this seldom happens. what can be the possible issue.
On the hardware side I have pulled up the sda and scl pins with 4.7K resistor .
 
 

  • Hello Noble,

    Thank you for your post. The "Solutions to Common eUSCI and USCI Serial Communication Issues on MSP430 MCUs" document covers I2C on page 10. This will cover the most common I2C issues and how to check for them and may help solve your issue. Let me know if you have any questions about the document.

    Also, can you post the output from a logic analyzer or oscilloscope monitoring the communication lines when the devices are attempting to communicate?

    Regards,

    Matthew

  •                   The controller fails to properly generate the start or stop pulse, I assume that the controller is unable to drive the pins properly, since my program gets stuck after I call for a start condition or stop condition.and the ustp or the ucstt remains set, which as per my knowledge means that the controller couldn't complete generating a start or stop pulse. another peculiar thing is noticed is that when I connnect the CRO with the sda line the start or stop pulse gets generated.
      Kindly guide.
            

    herin is my code 

    #include <msp430.h>
    
    
    volatile unsigned char TXData[] = { 0x00,0x12, 0x13, 0x14, 0x01,0x02,0x10,0x17};
    volatile unsigned char TXByteCtr;
    volatile unsigned char flag=0;
    volatile unsigned int counter=0;
    volatile unsigned char flow=0;
    volatile unsigned char RxData[7];
    
    
    
    void clockInit(void);
    
    int main(void)
    {
    WDTCTL = WDTPW | WDTHOLD;
    
    clockInit();
    P6DIR |= BIT3;
    P6DIR |= BIT2;
    
    P6OUT &= ~BIT3;
    P6OUT &= ~BIT2;
    
    
    
    //_______________________________________I2C INITIALIZATION_______________________________________________
    //------------------- Configure GPIO-------------------------------
    P4SEL1 |= BIT6 | BIT7; // I2C pins
    P4SEL0 &= ~(BIT6 | BIT7); // I2C pins
    LCDCPCTL0 = 0x0000;
    
    // Configure USCI_B0 for I2C mode
    UCB1CTLW0 |= UCSWRST; // put eUSCI_B in reset state
    UCB1CTLW0 |= UCMODE_3 | UCMST | UCSYNC; // I2C master mode, SMCLK
    
    UCB1I2CSA =0x68 ; // configure slave address
    UCB1BRW = 0x04; // baudrate = SMCLK / 2
    UCB1CTLW0 &= ~UCSWRST; // clear reset register
    UCB1IE |= UCTXIE + UCNACKIE + UCRXIE; // transmit and NACK interrupt enable
    
    __bis_SR_register(GIE);
    
    //________________________________________________END OF I2C INTIT_________________________________________________
    
    
    __delay_cycles(3000000); // 250ms delay
    //---------------flow = 0 => write time----------------------------------------------
    flow=0;
    TXByteCtr = 8; // Load TX byte counter
    
    while (UCB1CTLW0 & UCTXSTP); // Ensure stop condition got sent
    UCB1CTLW0 |= UCTR ;
    __delay_cycles(120000);
    
    UCB1CTLW0 |= UCTXSTT; // I2C TX, start condition
    
    while(flag == 0);
    flag=0;
    
    __delay_cycles(3000000);
    //---------------------------flow= 1 => write address pointer ----------------------------------------
    flow=1;
    TXByteCtr = 1; // Load TX byte counter
    
    while (UCB1CTLW0 & UCTXSTP); // Ensure stop condition got sent
    
    
    UCB1CTLW0 |= UCTR | UCTXSTT; // I2C TX, start condition
    
    while(flag == 0);
    flag=0;
    
    //------------------------------flow 2 read time------------------------------------------------
    
    flow=2;
    TXByteCtr = 7; // Load TX byte counter
    
    
    UCB1CTLW0 &= ~UCTR;
    UCB1CTLW0 |= UCTXSTT; // I2C TX, start condition
    while(flag == 0);
    flag=0;
    __delay_cycles(120);
    while (UCB1CTLW0 & UCTXSTP){
    UCB1CTLW0 &= ~UCTXSTP;
    UCB1CTLW0 |= UCTXSTP;// Ensure stop condition got sent
    __delay_cycles(120); // 12 usecs
    }
    
    while(1)
    {
    //---------------------------flow 1 write pointer ----------------------------------------
    __delay_cycles(120);
    flow=1;
    TXByteCtr = 1; // Load TX byte counter
    while (UCB1CTLW0 & UCTXSTP); // Ensure stop condition got sent
    UCB1CTLW0 |= UCTR | UCTXSTT; // I2C TX, start condition
    while(flag == 0);
    flag=0;
    
    //------------------------------flow 2 read time------------------------------------------------
    __delay_cycles(120);
    flow=2;
    TXByteCtr = 7; // Load TX byte counter
    // while (UCB1CTLW0 & UCTXSTP); // Ensure stop condition got sent
    
    UCB1CTLW0 &= ~UCTR;
    UCB1CTLW0 |= UCTXSTT; // I2C TX, start condition
    while(flag == 0);
    flag=0;
    __delay_cycles(120);
    while (UCB1CTLW0 & UCTXSTP){
    UCB1CTLW0 &= ~UCTXSTP;
    UCB1CTLW0 |= UCTXSTP;// Ensure stop condition got sent
    __delay_cycles(120); // 12 usecs
    }
    
    }
    }
    
    
    
    #if defined(__TI_COMPILER_VERSION__) || defined(__IAR_SYSTEMS_ICC__)
    #pragma vector = USCI_B1_VECTOR
    __interrupt void USCI_B1_ISR(void)
    #elif defined(__GNUC__)
    void __attribute__ ((interrupt(USCI_B1_VECTOR))) USCI_B1_ISR (void)
    #else
    #error Compiler not supported!
    #endif
    {
    switch(__even_in_range(UCB1IV, USCI_I2C_UCBIT9IFG))
    {
    case USCI_NONE: break; // Vector 0: No interrupts
    
    case USCI_I2C_UCNACKIFG: // Vector 4: NACKIFG
    UCB1CTLW0 |= UCTXSTT; // resend start if NACK
    
    break;
    
    case USCI_I2C_UCRXIFG0:
    UCB1IFG &= ~UCRXIFG;
    if(flow==2)
    {
    if (TXByteCtr) // Check TX byte counter
    { RxData[7-TXByteCtr] = UCB1RXBUF; // Load TX buffer
    TXByteCtr--;
    if(TXByteCtr==0)
    {
    UCB1CTLW0 |= UCTXSTP; // I2C stop condition
    flag=1;
    P6OUT ^=BIT2; // Decrement TX byte counter
    }
    }
    }
    break; // Vector 22: RXIFG0
    case USCI_I2C_UCTXIFG0: // Vector 24: TXIFG0
    if(flow==0)
    {if ((TXByteCtr)) // Check TX byte counter
    { UCB1TXBUF = TXData[8-TXByteCtr]; // Load TX buffer
    TXByteCtr--; // Decrement TX byte counter
    if(TXByteCtr==0)
    { flag=1;
    UCB1CTLW0 |= UCTXSTP; // I2C stop condition
    UCB1IFG &= ~UCTXIFG; // Clear USCI_B0 TX int flag
    P6OUT ^=BIT2;
    }
    
    }
    
    }
    if(flow == 1)
    { if(TXByteCtr)
    { UCB1TXBUF = 0x00; // Load TX buffer
    TXByteCtr--; // Decrement TX byte counter
    }
    else { flag=1;
    }
    }
    UCB1IFG &= ~UCTXIFG;
    break;
    default: break;
    }
    }

  • Hello Noble,

    The document I posted above has steps to debug your setup. On page 2 there is general eUSCI information and debugging steps, and on page 10 there is I2C specific information and debugging steps. If you go through these steps with your project, you will most likely find the issue.

    If you have access to one of them,  a logic analyzer or an oscilloscope will be extremely helpful in debugging your setup. If you'd like, you can post the output here and I will help you decipher it.

    Additionally, you can find code examples for reference on resource explorer. Here is a I2C example for the MSP430FR6879, and there are several more there you can look through.

    Regards,

    Matt

  • hello MR. Matthew,

    As you had suggested I went through the document and the code examples too.

    I am more or less near to the issue this is what I have found,

    Generally, the code runs fine.If in case by any fault (like a power off ) the communication is not completed that is a stop condition is not generated , the clk line is held low by msp430 controller, in turn, the busy flag and the scl low flag of the status register are set ,

    now even after reinitializing(using reset) the module or restarting(power up) the entire board , the status flags still remain the same i.e. busy and clk low remain set . On further analysis on CRO it was found out that the data line remained low even after restarting the device and the clk line too,  both of which should actually be pulled up at the power on state. no sooner you touch the clk line with the probe it gets pulled up and along with that the data line also gets pulled up. and the device starts working again.

    kindly help me with this.

    Regards,

    Noble Ajay. 

     

  • Hello Noble,

    When the MSP430FR6879 is reset, is the slave device also reset? If the slave device is not being reset, it may be holding the lines low, which would cause the clock and busy flags to be set.

    Regards,
    Matthew
  • Hello Noble,

    Do you have any updates on this issue?

    Regards,
    Matthew

**Attention** This is a public forum