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.

MSP--EXP430FR5739 SPI

Other Parts Discussed in Thread: MSP-EXP430FR5739

I am trying to use the MSP-EXP430FR5739 to talk to a wireless module and when I set it up and attempt to communicate with it, it returns an invalid response. However, if I step through the code with the debugger it receives the expected response.

  WDTCTL = WDTPW+WDTHOLD;                   // Stop watchdog timer

  P1DIR |= (BIT0 + BIT4 +BIT3);
  P1OUT &= ~BIT0;
  P1OUT |= (BIT4 + BIT3);

  P1SEL1 |= BIT5;//+BIT4;
  P2SEL1 |= BIT0 + BIT1;

  UCA0CTLW0 |= UCSWRST;                     // **Put state machine in reset**
  UCA0CTLW0 |= UCMST|UCMSB|UCSYNC;//|UCMODE1|UCSTEM;  	    // 3-pin, 8-bit SPI master
  UCA0CTLW0 |= UCCKPH;                                          // Clock polarity low, MSB
  UCA0CTLW0 |= UCSSEL_2;                    // ACLK
  UCA0BR0 = 0x08;                           // /2
  UCA0BR1 = 0;                              //
//  UCA0STATW |= UCLISTEN;
  UCA0MCTLW = 0;                            // No modulation
  UCA0CTLW0 &= ~UCSWRST;                    // **Initialize USCI state machine**
  UCA0IE |= UCRXIE;                         // Enable USCI_A0 RX interrupt

  P1OUT &= ~BIT3;
  P1OUT |= BIT3;
  __delay_cycles(100);

//  radio_init();
//  unsigned char address[] ={0x22};
  while(1)
  {
     RXData = spi_read(0x22);

     _delay_ms(100);
//     RXData = 0;
  }

}

unsigned char spi_read(unsigned char address)
{
	unsigned char data = 0;
	P1OUT &= ~BIT4;
	data = UCA0RXBUF;
	while(UCA0STATW&UCBUSY == UCBUSY);
	UCA0TXBUF = address;
//	__delay_cycles(10);
	data = UCA0RXBUF;
//	while(UCA0STATW&UCBUSY == UCBUSY);
	_delay_ms(10);
	UCA0TXBUF = 0xff;
	data = UCA0RXBUF;
	P1OUT |= BIT4;

	return data;
}

I do not understand why it will get a valid response when stepping through and not when just executing the code.

Thanks for your help

  •     UCA0TXBUF = 0xff;

        data = UCA0RXBUF;

    This doesn't wait for the transaction to complete. When you Step, the transaction

    completes "behind the scenes" while you're staring at the screen. Try inserting:

    while((UCA0STATW&UCBUSY) == UCBUSY);


    before fetching UCA0RXBUF. (Note the parenthesization, which makes it work
    intentionally rather than accidentally)

  • Bruce McKenney47378 said:

        UCA0TXBUF = 0xff;

        data = UCA0RXBUF;

    This doesn't wait for the transaction to complete. When you Step, the transaction

    completes "behind the scenes" while you're staring at the screen. Try inserting:

    while((UCA0STATW&UCBUSY) == UCBUSY);


    before fetching UCA0RXBUF. (Note the parenthesization, which makes it work
    intentionally rather than accidentally)

    Thanks Bruce, it was indeed that missing parentheses that has seemed to fix the problem.

  • That has fixed that problem but I have created another, When I attempt to read from the long address the code hangs on my last while((UCA0STATW&UCBUSY) == UCBUSY);

    unsigned char spi_readlong(unsigned short int address)
    {
    	address = address << 5;
    	address = address | 0x8000;
    	unsigned char upperaddr = (address>>8);
    	unsigned char loweraddr = (address & 0xff);
    	unsigned char rxbuf;
    	P1OUT &= ~BIT4;
    	rxbuf = UCA0RXBUF;
    	while((UCA0STATW&UCBUSY) == UCBUSY);
    	UCA0TXBUF = upperaddr;
    	rxbuf = UCA0RXBUF;
    	while((UCA0STATW&UCBUSY) == UCBUSY);
    //	rxbuf = UCA0RXBUF;
    	UCA0TXBUF = loweraddr;
    	rxbuf = UCA0RXBUF;
    	while((UCA0STATW&UCBUSY) == UCBUSY);
    //	rxbuf = UCA0RXBUF;
    	UCA0TXBUF = 0xff;
    	while((UCA0STATW&UCBUSY) == UCBUSY);
    	rxbuf = UCA0RXBUF;
    //	__delay_cycles(10);
    	P1OUT |= BIT4;
    
    	return rxbuf;
    }

    Now if I comment it out I run into the same issue as before where I read invalid data due to incomplete transaction. Any suggestions as to why it would hang there?

     

  • No, as far as I know UCBUSY will update (eventually) if the SPI is enabled. I just patched this code into example ucsia0_spi_09 and it didn't hang, so I suspect whatever's wrong is outside the code you posted.

    Just to be clear: You should wait for completion between every pair of "UCA0TXBUF=x;y=UCA0RXBUF;", not just the final one.

  • Bruce McKenney47378 said:
    You should wait for completion between every pair of "UCA0TXBUF=x;y=UCA0RXBUF;", not just the final one.

    Or keep track of the interleave, to make advantage of the double-buffering the USCI offers (for seamless transfer = maximum throughput).

    Using paper and pencil and drawing a timeline with the send and receive events will help understanding what happens when.

**Attention** This is a public forum