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.

RTOS/SW-EK-TM4C129EXL: SPI Datatransfer Issues

Part Number: SW-EK-TM4C129EXL
Other Parts Discussed in Thread: EK-TM4C129EXL

Tool/software: TI-RTOS

Hi Ralph,

           I am trying to interface EK-TM4C129EXL with the 8*8 LED module to display some characters. When I try to send 0x00 (Value - 0) through SPI the LED's in the display module should not glow, but it glows. I am not able to find why tose led glows.. Here is the code 

/* XDCtools Header files */
#include <xdc/std.h>
#include <xdc/runtime/System.h>
#include <xdc/runtime/Error.h>

/* BIOS Header files */
#include <ti/sysbios/BIOS.h>
#include <ti/sysbios/knl/Semaphore.h>

/* TI-RTOS Header files */
#include <ti/drivers/GPIO.h>
#include <xdc/runtime/System.h>
//#include <xdc/cfg/global.h>

/* BIOS Header files */
#include <ti/sysbios/knl/Task.h>

/* TI-RTOS Header files */
#include <ti/drivers/GPIO.h>
#include <ti/drivers/SPI.h>
#include <ti/sysbios/BIOS.h>


#include <stdint.h>
#include <stdbool.h>
#include "inc/hw_types.h"
#include "inc/hw_memmap.h"
#include "driverlib/sysctl.h"
#include "driverlib/gpio.h"



#define TASKSTACKSIZE 1024
Task_Struct task0Struct;
Char task0Stack[TASKSTACKSIZE];

void spiDataSend();
void multiplexing();

volatile int rowSelect = 0;
volatile int count = 0;
extern Semaphore_Handle sem1;
extern Semaphore_Handle sem2;
 
UChar transmitBuffer[1] = {0x00};
  
/* Board Header file */
#include "Board.h"

void timerFunc()
{
    //static int count = 0;
    if (count++ & 1) {
        Semaphore_post(sem2);
    }
    else {
        Semaphore_post(sem1);
    }
}

/*Task1 is in a loop pending on sem1*/

tsk1Func(UArg arg0, UArg arg1)
{
    //GPIO_toggle(Board_LED1);
    while (1) {
    Semaphore_pend(sem1, BIOS_WAIT_FOREVER);
    multiplexing();
    /* task1 work here */

    }
}
/*Task2 is in a loop pending on sem2*/

tsk2Func(UArg arg0, UArg arg1)
{
    //GPIO_toggle(Board_LED0);
    while (1) {
    Semaphore_pend(sem2, BIOS_WAIT_FOREVER);
    spiDataSend();
     /* task2 work here */

   }
}


void spiDataSend()
{

    SPI_Handle spi;
    SPI_Params spiParams;
    SPI_Params_init(&spiParams);
    spiParams.dataSize = 1; /* dataSize can range from 4 to 8 bits */
    spiParams.transferMode = SPI_MODE_BLOCKING;
    spiParams.mode = SPI_MASTER;
    spiParams.bitRate = 2000000;
    spiParams.transferCallbackFxn = NULL;
    spi = SPI_open(Board_SPI0, &spiParams); 
    if (spi == NULL) {
    /* Error opening SPI */
    }
    SPI_Transaction spiTransaction;
    spiTransaction.count = 8;
    spiTransaction.txBuf =  transmitBuffer;
    spiTransaction.rxBuf =  NULL;
    SPI_transfer(spi, &spiTransaction);
    SPI_close(spi);
}


void multiplexing()
{

    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 1);  // LED Driver part of code this part works fine...
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , 1);  
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 0);  
    GPIOPinWrite(GPIO_PORTE_BASE, (GPIO_PIN_0|GPIO_PIN_1) , rowSelect);
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , 0);  
    rowSelect++;
    if (rowSelect > 3)
    {
      rowSelect = 0;
    }

}


/*
 *  ======== main ========
 */
int main(void)
{
    /* Call board init functions */
    Board_initGeneral();
    Board_initGPIO();
    Board_initSPI();
	
    GPIOPinTypeGPIOOutput(GPIO_PORTE_BASE, (GPIO_PIN_0|GPIO_PIN_1)); // Initializing the Decoder part
    GPIOPinTypeGPIOOutput(GPIO_PORTD_BASE,(GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3)); // Initializing the SPI Driver part
   
    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOE);
    while(!SysCtlPeripheralReady(SYSCTL_PERIPH_GPIOE))
    {
    }
    
    Task_Params taskParams;
    Task_Params_init(&taskParams);
    taskParams.priority = 2;
    taskParams.stackSize = TASKSTACKSIZE;
    taskParams.stack = &task0Stack;
    Task_construct(&task0Struct, (Task_FuncPtr)spiDataSend, &taskParams, NULL);
    /* Start BIOS */
    BIOS_start();
    return (0);
}

You can notice that the value in the tranmitbuffer is 0x00 Still the LED glows.... 

I am having certain doubts, 

spi = SPI_open(Board_SPI0, &spiParams); 
----> Do Board_SPI0 open the SPI on PORTD ???

 ----> In which register the value in the transmit buffer will be writeen ???

 ----> I can't able to see data value in SSI_DR_DATA - SSI Receive/Transmit Data 

     

  • which pin(s) is your LED?

    I'm not sure what you are trying to do with the below three lines.

    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 1); // LED Driver part of code this part works fine...
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , 1);
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 0);

    Note that the second argument of the GPIOPinWrite is a bit-packed representation of the pin(s). In your second line I think you are trying to set the GPIO_PIN_2, correct? If this is your intention you should write GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , GPIO_PIN_2 ) or GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , 0x4) instead. What you are doing will not set GPIO_PIN_2.
  • Hi Charles,

          Those three lines makes the LED Driver to turn "ON"..Those three lines works fine. I am having doubts in SPI datatransfer.. I am able to write the values in trasnsmitBuffer but I can't able to see those values in the SSI_DR_DATA - SSI Receive/Transmit Data register.. btw I had changed the value 1  to 0x4.. That doesn't seem to a problem...

    What about those three questions????

    spi = SPI_open(Board_SPI0, &spiParams);
    
    ----> Do Board_SPI0 open the SPI on PORTD ??? 
    
     ----> In which register the value in the transmit buffer will be writeen ???
    
     ----> I can't able to see data value in SSI_DR_DATA - SSI Receive/Transmit Data
         

  • Naveen Kumar29 said:
    Those three lines makes the LED Driver to turn "ON"..Those three lines works fine.

    Indeed - just as Vendor's Charles noted - your LINE #2 (hi-lite, below) surely DOES NOT WORK -  AND MOST CERTAINLY,  IS NOT FINE!

    Charles went so far as to explain that your, 'Parameter 3 choice proved improper' - it proves UNWISE for you to resist such (detailed) CORRECTION!

    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 1);
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_2 , 1);   //  SO VERY WRONG - your '1' here -  WILL NEVER TURN ON  BIT 'D2'!   Charles' '4' -  WILL.
    GPIOPinWrite(GPIO_PORTD_BASE, GPIO_PIN_0 , 0);

    Such would have been apparent to you - had you (carefully) probed/measured 'PD2' - had you not done that?     And - if so - what is your 'basis' for stating, 'Works FINE?'     (it is sure - that either you had not measured 'PD2' - or that if you had made the attempt - your connection or method was improper...)

    It is advisable to 'ACCEPT COACHING' - and to develop 'adequate' diagnostic techniques...

  • Hi,

      If you look at the Board.h file the Board_SPI0 is mapped to the SPI2 of the TM4C129. In the datasheet, the SPI2 is mapped to PDx pins. This is your problem. You need to change the mapping to your desired SPI instance in the Board.h, EK_TM4c129EXL.c and EK_TM4C129EXL.h accordingly. 

  • Hi cb1_mobile,

               After Charles said, I am writing 0x4 value to the pin 2 on the PORTD still the issue remains.   What I meant in my above post was "btw I had changed the value 1  to 0x4.. and thereby the code for Driver part works fine!!". When I tried set a breakpoint on "Spi_close(spi)", I can't able to get any values on the SSI_DR_DATA - SSI Receive/Transmit Data register. Also we don't have Scope facility in our workplace.

  • Hi charles,

            Thanks charles, that clarifies my doubt, let us assume that

    UChar transmitBuffer[8] = {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};

     spiTransaction.txBuf =  transmitBuffer;

    What happens after this line???

    In what register the value in the Transmit buffer will be written??? Do these  values will be transferred to SSI2XDAT0 (SSI2TX)pin???

    With regards,

    Naveen 

  • When the SPI_transfer(spi, &spiTransaction) is executed will the SPI transfers begin. The spiTransaction.txBuf = transmitBuffer only assign the txBuf to point to the beginning of the transmitBuffer array.

    Once the SPI transfers start the data pointed to by spiTransaction.txBuf will be copied to the SPI module TX FIFO. The data in the FIFO will then be copied to shift register. This is when you will see the transmission on the SSI2TX or whatever SPI instance you are using.
  • Hi Charles,
    Can I be able to see the data on SPI module TX FIFO or Shift register while debugging???
  • Without a scope - it (may) be possible to gain some evidence of data activity by (temporarily) hooking a (series resistor protected) Led to your 'SPI_TX pin.'

    Unless your SPI Data Rate is greatly reduced - you'll not be able to note the individual SPI 'bits' - yet you WILL gain confirmation that the SPI is, 'Outputting Data.'

    With sufficiently 'slowed' SPI Data Rate - and setting the SPI Data to '0X55 or 0XAA' - you just may note the, 'Bit by bit toggle' of those SPI transmitted bytes...
  • Hi,
    The FIFO and the Shift register are not memory mapped. The best method to debug is still to use either a scope or logic analyzer. You can also connect the SPITX and SPIRX pins in a loopback. This way you can also verify if you are receiving the same data that you transmitted out if you don't have the scope.
  • 'KISS' would direct that, 'Seeing (some) data/activity' - quickly & easily (i.e. as the Led provides) - should precede 'loopback!' 

    Such proves so as 'multiple code segments and an interconnect' prove more difficult to implement than a single Led connection... And - should the loopback fail - there exist (at least) 4 'likely suspects.' (i.e. failed: loopback mode config; failed interconnect; failed SPI Output; and failed SPI Input!)