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.

TMS320F28069M: I can see data in Rx Buffer, but SCIFFRX says it's not there.

Part Number: TMS320F28069M
Other Parts Discussed in Thread: C2000WARE, MOTORWARE

I’m working on the serial comm for a motor control board (MCB). I'm using InstaSpin Lab 05b as a model. I had serial communications working pretty flawlessly as a stand-alone application, using examples in C2000Ware as a starting point. When I tried integrating the MotorWare code for InstaSpin Lab 05b with this code, however, everything ground to a halt. A colleague suggested using serial communications code native to MotorWare - that way the risk of any definitions contained in header files, etc... would be in less danger of stepping on each other. This board must be able to communicate with, and take direction from an LCD module. The LCD module sends out requests for data, using the SLIP protocol, every 500 ms. It also sends commands whenever the user changes parameters via the LCD. The MCB must be able to collect the entire message from the LCD, respond to requests for data (using the SLIP protocol), and carry out any changes (to speed, torque limit, etc...) requested by the LCD module.

I can see data in the SCIRXBUF register, and the RXFFST bits of the SCIFFRX register indicate that there is data in the FIFO.

I was hoping that I could examine the SCIFFRX register’s FIFO status bits, and if their value matched that of the RXFFIL, I could consider the FIFO contents good data, and I could grab the data from the SCIRXBUF a number of times corresponding to the FIFO depth (RXFFIL). I started off just setting the FIFO depth to 1, just to see if I could grab a byte at a time. No luck there. I attributed the failure to the fact that the FIFO depth that I’d set didn’t match the number in the FIFO Status bits. I was probably wrong about that. I still don’t know why I couldn’t grab the buffer contents under those conditions. Anyway, I tried a somewhat different tack.

 

Using “SCI_getDataNonBlocking" (a comm function native to MotorWare) in the main loop, which calls “SCI_rxDataReady” written as follows:

 

static inline bool SCI_rxDataReady(SCI_Handle sciHandle)
{
  SCI_Obj *sci = (SCI_Obj *)sciHandle;
  bool status;

 // status = (sci->SCIRXST & SCI_SCIRXST_RXRDY_BITS) >> 6;
  status = (sci->SCIFFRX & SCI_SCIFFRX_FIFO_ST4_BIT) >> 10;
  

  return((bool)status);
} // end of SCI_rxDataReady() function

 

I defined SCI_SCIFFRX_FIFO_ST4_BIT as follows in sci.h (where a lot of similar defines occur):

#define SCI_SCIFFRX_FIFO_ST4_BIT      (1 << 10)

 

RXRDY is commented out and can’t be used because I’m employing the FIFO. I picked a depth of 4, because that’s where the RXFFST bits always seem to land. I’m not sure why, but the FIFO depth listed by the FIFO status bits is always 4. Whatever… I figured I could work with that. For some reason, though, ‘status’ always ends up zero. There is data in the buffer and the bit of interest (bit 11 of the SCIFFRX register) is set when I look at the registers, so I don’t see how this could be.

 

It’s my understanding (or perhaps misunderstanding) that when the value of the FIFO Status bits exceeds the value specified by the RXFFIL bits, then an interrupt flag (RXFFINT) is set. So, I figured I could use this flag to determine whether there were the requisite number of bytes in the FIFO, even if I’m not explicitly using the interrupt. So, SCI_rxDataReady is rewritten as:

 

 

//! \return    The receive data status
static inline bool SCI_rxDataReady(SCI_Handle sciHandle)
{
  SCI_Obj *sci = (SCI_Obj *)sciHandle;
  bool status;

 // status = (sci->SCIRXST & SCI_SCIRXST_RXRDY_BITS) >> 6;
 // status = (sci->SCIFFRX & SCI_SCIFFRX_FIFO_ST4_BIT) >> 10;
  status = (sci->SCIFFRX & SCI_SCIFFRX_INT_BITS) >> 7;

  return((bool)status);
} // end of SCI_rxDataReady() function

 

Where SCI_SCIFFRX_INT_BITS is defined (in sci.h) as:

#define SCI_SCIFFRX_INT_BITS          ( 1 << 7)

 

Status still comes up zero, even though I can see that the RXFFINT bit is a 1 in the register.

 

All I can think of is that I still must be missing something in setup, something specific to the FIFO, but I haven’t been able to determine what.

 

Here are the relevant subroutines for setting up the FIFO, and the serial comm in general.

void SCI_enableRxFifo(SCI_Handle sciHandle)
{
  SCI_Obj *sci = (SCI_Obj *)sciHandle;

  // Clear the appropriate RXFFIL bits.
  sci->SCIFFRX &= SCI_SCIFFRX_FIFO_RXFFIL_CLR_BITS;
  // Set the RXFFIL LSB to indicate a reset should be generated when there is 1 byte in FIFO.
  sci->SCIFFRX |= SCI_SCIFFRX_FIFO_RXFFIL_SET_BITS;

  // Set the FIFO Reset bit.
  sci->SCIFFRX |= SCI_SCIFFRX_FIFO_RESET_BITS;

  return;
} // end of SCI_enableRxFifo() function
 

 

Where the clear and set constants listed above are defined as follows:

#define SCI_SCIFFRX_FIFO_RXFFIL_CLR_BITS  0xffe4

#define SCI_SCIFFRX_FIFO_RXFFIL_SET_BITS  0x0004

 

The comments associated with the above code were originally written when I was trying to detect one byte. The FIFO status bits, however, always seem to indicate that 4 bytes had been collected, so I figured I’d just roll with that. (Didn’t think it was worth changing the comments, until I’ve settled on an actual FIFO level.)

 

void HAL_setupSciB(HAL_Handle handle)
{
  HAL_Obj   *obj = (HAL_Obj *)handle;

  SCI_reset(obj->sciBHandle); // *
  SCI_enableTx(obj->sciBHandle); // *
  SCI_enableTxFifoEnh(obj->sciBHandle); //*
  SCI_enableTxFifo(obj->sciBHandle); // *
  SCI_clearTxFifoInt(obj->sciBHandle); // *
  //SCI_setTxDelay(obj->sciBHandle,0x0018);
  SCI_enableRx(obj->sciBHandle); // *
  SCI_resetRxFifo(obj->sciBHandle); // Empty Rx FIFO
  SCI_enableRxFifo(obj->sciBHandle); // *
  SCI_clearRxFifoInt(obj->sciBHandle); // *

  SCI_setBaudRate(obj->sciBHandle,SCI_BaudRate_115_2_kBaud); // *
  SCI_setCharLength(obj->sciBHandle,SCI_CharLength_8_Bits); // *
  SCI_enable(obj->sciBHandle); // *
/* All of these were echoed in scib_loop_init & scib_fifo_init, though not in the same order.
   There are additional setup routines in scib_loop_init & scib_fifo_init:
   SCI_resetTxFifo(sci_Reg_Handle); // Empty Tx FIFO
   SCI_resetRxFifo(sci_Reg_Handle); // Empty Rx FIFO
   SCI_clearAutoBaudDetect(sci_Reg_Handle);
   SCI_disableAutoBaudAlign(sci_Reg_Handle);
   SCI_enableTxInt(sci_Reg_Handle);// Enable RXRDY/BRKDT & Enable TXRDY interrupts.
   SCI_enableRxInt(sci_Reg_Handle);
   SCI_disableTxInt(sci_Reg_Handle);
   SCI_disableRxBreakInt(sci_Reg_Handle);//Disable  Receiver-buffer break
   SCI_disableLoopBack(sci_Reg_Handle);

*/


  return;
}  // end of HAL_setupSciB() function

 

scib_loop_init & scib_fifo_init (mentioned in the comments, above) were the subroutines I used when communicating using the C2000Ware examples. I had working serial comm, but there was interference of some sort when I tried to integrate the C2000Ware code with MotorWare code. There are several subroutines listed in the comments at the end of “HAL_setupSciB.” Maybe I should use one or more of those? I’ve tried a couple of them, but I’m not sure of the appropriate order of operations here.

Thanks,

Dave

  • Hi Dave,

    So you are never able to see the RXRDY bit set even though there is data there and its the right data? What happens if you ignore the status bit and read in the data(this is just for debug)? Are the results as expected?

    Best Regards,

    Marlyn

  • Hi Marlyn,

    The RXRDY bit can't be used when employing the FIFO. I'm checking the RXFFST bits of the SCIFFRX register (or alternatively the RXINT bit of the SCIFFRX). When I look at the SCIFFRX register (just using the viewer in CCS), the RXFFST bits indicate that there are 4 'bytes' in the FIFO. However, when I try to retrieve that information and store it in a variable, it always comes back zero. Likewise, for the RXINT bit.

    I'm not sure whether the data is the right data, but I figure that's not the primary concern right now. Right now, if there's data in the buffer, I want to be able to retrieve it, regardless of whether it's right or not. I have tried removing all conditions on reading the RXBUF.

    Even though CCS's register viewer tells me there's data in there, it always comes up zero, when I try to read it in the code.

    I have the following code in the main loop:

    //      if(SCI_getRxFifoStatus(sci_Reg_Handle) != SCI_FifoStatus_Empty)
    //       {
             //
             rx_in = (unsigned char)(SCI_getDataNonBlocking(sci_Reg_Handle, &success) & 0xFF); // collect rx buffer contents
    //       }

    And here's "SCI_getDataNonBlocking":

    uint16_t SCI_getDataNonBlocking(SCI_Handle sciHandle, uint16_t * success)
    {
      SCI_Obj *sci = (SCI_Obj *)sciHandle;
    
      //if(SCI_rxDataReady(sciHandle))
    //    {
          *success = true;
          return(sci->SCIRXBUF); 
    //    }
    
    //  *success = false;
    //  return(NULL);
    } // end of SCI_getDataNonBlocking() function

    There's a bunch of code commented out in both examples, in hopes that, if there were no conditions on getting the data, then I could get at whatever is in the RXBUF. That approach did not work.

    Thanks,

    Dave

  • Dave,

    I recommend looking at the HAL user's guide within motorWare as below, and refer to chapter "6.7. Adding SCI/UART functionality to a project with InstaSPIN in Motorware”.

    Guide: motorware_hal_tutorial.pdf at "\ti\motorware\motorware_version\docs\tutorials\motorware_hal_tutorial.pdf"

    Best Regards,

    Marlyn

  • Thanks Marlyn! I didn't even know this existed.

    Best Regards,

    Dave