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.

CC430F5137 driver for interfacing to SPI EEPROM M95M01 from STMicroelectronics. It is 1Mbps part.

Other Parts Discussed in Thread: CC430F5137

Hi,

Has anyone brought up SPI driver on CC430F5137 to communicate to M95M01 part from STMicro. It is 1Mbps EEPROM. I couldn't get the EEPROM send anything out on MISO line.

 

Thnanks,

Srinivas

  • There are lots of examples of low-level SPI drivers for MSP family of devices. It shouldn't be hard to find a working driver.

    As for the high-level driver for the STM device, you should be able to create that easily. As always, I recommend putting scope or logic analyzer probes on your communications bus and look at what is actually going over the line when things aren't working.

  • The EEPROM doesn't output anything on MISO. I have tried all the 4 spi mode settings. Would like to know if anybody brought up  M95M01-R part with CC430F5137. below is my code.

     #include <msp430.h>
    unsigned char MST_Data,SLV_Data, sr[6];
    #define SS_LOW (P1OUT &= ~0x04)
    #define SS_HIGH (P1OUT |= 0x04)

    #define WREN  6
    #define WRDI  4
    #define RDSR  5
    #define WRSR  1
    #define READ  3
    #define WRITE 2

    int main(void)
    {

      WDTCTL = WDTPW+WDTHOLD;                   // Stop watchdog timer
      int i;
      SS_HIGH;
      PMAPPWD = 0x02D52;                        // Get write-access to port mapping regs 
      P2MAP0 = PM_UCA0SIMO;               // Map UCA0SIMO output to P2.0
      P2MAP2 = PM_UCA0SOMI;               // Map UCA0SOMI output to P2.2
      P2MAP4 = PM_UCA0CLK;                   // Map UCA0CLK output to P2.4
      PMAPPWD = 0;                                       // Lock port mapping registers 
      P1OUT |= BIT2;                                       // CS                                           
      P1DIR |= BIT2 + BIT0;                          
      P2DIR |= BIT0 + BIT2 + BIT4;             
      P2SEL |= BIT0 + BIT2 + BIT4;             

      UCA0CTL1 |= UCSWRST;                      // **Put state machine in reset**
    // UCA0CTL0 |= UCMST+UCSYNC+UCCKPL+UCMSB;    // 3-pin, 8-bit SPI master
    //UCA0CTL0 |= UCMST+UCSYNC+UCCKPH+UCMSB;    // 3-pin, 8-bit SPI master
    //UCA0CTL0 |= UCMST+UCSYNC+UCCKPH+UCCKPL+UCMSB;    // 3-pin, 8-bit SPI master  UCA0CTL0 |= UCMST+UCSYNC+UCMSB;    // 3-pin, 8-bit SPI master
                                                                                      // Clock polarity high, MSB

      UCA0CTL1 |= UCSSEL_2;                     // SMCLK
      UCA0BR0 = 2;                                          // /2
      UCA0BR1 = 0;                                         //
      UCA0MCTL = 0;                                      // No modulation
      UCA0IE |= UCRXIE;                                   // Enable USCI_A0 RX interrupt
      UCA0CTL1 &= ~UCSWRST;                     // **Initialize USCI state machine**
      SS_HIGH;

      while(1)
      {
        SS_LOW;
        __delay_cycles(10);
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = WREN;
        while (!(UCA0IFG&UCTXIFG));
        SS_HIGH;

       SS_LOW;
       __delay_cycles(10);
       while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = WRSR;
       while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = 0x02;
       while (!(UCA0IFG&UCTXIFG));
       SS_HIGH;

       SS_LOW;
       while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = RDSR;
       while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = RDSR;
       while (!(UCA0IFG&UCRXIFG));
       sr[0] = UCA0RXBUF;
       while (!(UCA0IFG&UCTXIFG));
       SS_HIGH;

       SS_LOW;
       __delay_cycles(10);
       while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = WREN;
       while (!(UCA0IFG&UCTXIFG));
       SS_HIGH;

        SS_LOW;
        __delay_cycles(10);
        UCA0TXBUF = WRITE;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0xCD;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0xAB;
        while (!(UCA0IFG&UCTXIFG));
        SS_HIGH;

        SS_LOW;
        __delay_cycles(10);
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = READ;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0x00;
        while (!(UCA0IFG&UCTXIFG));
        UCA0TXBUF = 0xFF;
        while (!(UCA0IFG&UCTXIFG));
        SS_HIGH;

        while (!(UCA0IFG&UCRXIFG));
        sr[5] = UCA0RXBUF;

      }
    }

    BR.

  • Srinivas Chilukuri said:
    The EEPROM doesn't output anything on MISO. I have tried all the 4 spi mode settings.

    If the EEPROM doesn't send anything out on MISO, then it isn't getting proper data in on CS, CLK, and MOSI connections. I would advise looking at what the physical lines are doing to get an idea on what your software is doing wrong.


    I am not much for digging through other's source code here, but I notice that you are enabling the RXIE bit, but have no ISR routine. That means that when an RX interrupt happens, the MSP will look for an ISR that doesn't exist. I am not sure what your toolchain populates unused ISR vector locations with, so I don't know exactly what problem that will cause.

    Either way, since you are using a polled-mode, do not enable the RXIE bit.

  • Disabled RXIE.

    Seems EEPROM outputs the written data only for certain range of addresses. Debugging more. But has anyone seen this kind of behavior ? how to fix it ? write to WRSR register ? thanks for any inputs.

    -S

  •    while (!(UCA0IFG&UCTXIFG));
       UCA0TXBUF = RDSR;
       while (!(UCA0IFG&UCRXIFG));
       sr[0] = UCA0RXBUF;

    This sequence is trouble. There's a stale RXIFG that will keep the second spin loop from waiting properly.

    Pipelining the SPI is hazardous for reads (it's generally OK for writes). Except for cases where I really care about every clock cycle I use the RXIFG, not the TXIFG, to test for completion, and always read the RXBUF; the effect is to totally clear the pipeline for every byte -- slightly slower but very reliable.

  • may I get the correct code snippet ? please pardon my ignorance, I am trying to quickly prototype using CC430. is below correct  way of doing, say writing RDSR twice to get the status word from slave ?

       while (!(UCA0IFG&UCRXIFG));
       UCA0TXBUF = RDSR;


       sr[0] = UCA0RXBUF;

       while (!(UCA0IFG&UCRXIFG));
       UCA0TXBUF = RDSR;

       sr[0] = UCA0RXBUF;

     

     

    p.s. I have a working driver for block writes/reads finally with, but want to make sure I follow the correct primitves for accessing SPI core.

     

    thanks again.

    S

     

**Attention** This is a public forum