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.

Does not work SPI

Other Parts Discussed in Thread: SYSBIOS

F28M35H52C1, ARM,  CSS 6.1.2, TI-RTOS, SPITivaDMA.c

I try to read spi from 2 theads. i try read at different times. I made a function to safe access to SPI

const struct SPI_Params paramsSPI =
{
    .transferMode = SPI_MODE_BLOCKING,
    .transferTimeout = SPI_WAIT_FOREVER,
    .transferCallbackFxn = NULL,
    .mode = SPI_MASTER,
    .bitRate = 1000000, //(Hz)
    .dataSize = 8,//(bits)
    .frameFormat = SPI_POL0_PHA0,
    .custom = NULL
};

bool readW5100(SPIName numW5100, uint8_t *array, int len, int adrInW5100)
{
    //взять мьютекс
    Semaphore_Handle sem = (numW5100 == SPI_W5100_1) ? semW5100_1 : semW5100_2;
    bool isSemPend;
    isSemPend = Semaphore_pend(sem, 1000);
    assert(isSemPend);

    SPI_Handle spiHandler = SPI_open(numW5100, (SPI_Params *)&paramsSPI);
    if(spiHandler == NULL)
    {
        System_abort("Error initializing spi");
        System_flush();
        assert(1);
        return false;
    }

    for(int i = 0; i < len; i++)
        array[i] = readByte(spiHandler, adrInW5100++);

    SPI_close(spiHandler);

    Semaphore_post(sem);
    return true;
}

void writeByte(SPI_Handle handler, uint16_t adrReg, uint8_t data)
{
    unsigned char txBuffer[5] =
    { 0xf0 };
    unsigned char rxBuffer[5];
    txBuffer[1] = adrReg >> 8;
    txBuffer[2] = adrReg;
    txBuffer[3] = data;

    SPI_Transaction masterTransaction;
    masterTransaction.count = 4;
    masterTransaction.rxBuf = (Ptr)rxBuffer;
    masterTransaction.txBuf = (Ptr)txBuffer;

    SPI_transfer(handler, &masterTransaction);
}

1)When i read SPI from one task, i can see normal transaction. I can see MISO, MOSI, CS, CLK on SPI lines. When i try to read SPI from another task, i can see only MISO, CLK and CS. The MOSI lineю These is low level on MOSI line. Why?

2) I can see calls macros in your spi driver, SPITivaDMA.c

 Log_error1("SPI:(%p) transaction still in progress",
                   hwattrs->baseAddr);


but i can not see this log. Which displays this macro logging?

  • Hi Juvf,

    What version of TI-RTOS are you using?  If one task is in the middle of a SPI transaction, the other task will not be able to perform a SPI transaction until the first one completes.  To enable logging, use the instrumented version of TI-RTOS in your application's .cfg file:

    /* ================ TI-RTOS drivers' configuration ================ */
    var driversConfig = xdc.useModule('ti.drivers.Config');
    /*
     * Include TI-RTOS drivers
     *
     * Pick one:
     *  - driversConfig.LibType_NonInstrumented (default)
     *      Use TI-RTOS drivers library optimized for footprint and performance
     *      without asserts or logs.
     *  - driversConfig.LibType_Instrumented
     *      Use TI-RTOS drivers library for debugging with asserts and logs enabled.
     */
    //driversConfig.libType = driversConfig.LibType_NonInstrumented;
    driversConfig.libType = driversConfig.LibType_Instrumented;

    Then you should be able to view the Log data in CCS using ROV.

    Best regards,

        Janet

  • i use tirtos_c2000_2_16_01_14.

    "If one task is in the middle of a SPI transaction, the other task will not be able to perform a SPI transaction until the first one completes." I know this. I try to read from different rask at different times Why does not work only ONE line (MOSI)? when i read spi from another task?

    There is my application's .cfg

    /* ================ TI-RTOS drivers' configuration ================ */
    var driversConfig = xdc.useModule('ti.drivers.Config');
    /*
     * Include TI-RTOS drivers
     *
     * Pick one:
     *  - driversConfig.LibType_NonInstrumented (default)
     *      Use TI-RTOS drivers library optimized for footprint and performance
     *      without asserts or logs.
     *  - driversConfig.LibType_Instrumented
     *      Use TI-RTOS drivers library for debugging with asserts and logs enabled.
     */
    driversConfig.libType = driversConfig.LibType_Instrumented;
    //driversConfig.libType = driversConfig.LibType_Instrumented;

    What is it ROV? How to use it?

    I want to debug step-by-step C code in func SPITivaDMA_transfer() in SPITivaDMA.c.  How to do it?

    ps

    Log_print1(Diags_USER1,"SPI:(%p) DMA transfer enabled", hwAttrs->baseAddr); - Where can I see this output?

        Log_print5(Diags_USER2,"SPI:(%p) DMA transaction: %p, "
                               "rxBuf: %p; txBuf: %p; Count: %d",
                                hwAttrs->baseAddr,
                                (UArg)transaction,
                                (UArg)transaction->rxBuf,
                                (UArg)transaction->txBuf,
                                (UArg)transaction->count);   - Log_print5!!! FIVE!!! wtf? Where can I see this output?

    Can u help me? please

  • Hi Juvf,

    You will also need to add a Log to your .cfg file, otherwise the Log_print statements will be optimized out of your code.  The easiest way to do this is to add the following line to your .cfg file:

    var LoggingSetup = xdc.useModule('ti.uia.sysbios.LoggingSetup');

    Then rebuild your program.  When you load your program in CCS, in the CCS Debug view,  you will find ROV under the Tools menu.  It's called "RTOS Object View (ROV)".  You will see output from the drivers in the LoggerStopMode Main logger in ROV.  Here is an example:

    You should be able to step into SPITivaDMA_transfer().  You can set a break point there, or step through your code and step into SPI_transfer().  The debugger may ask you where the source files are, which you can browse to (<TI-RTOS/products/tidrivers_tivac_2_xx_xx_xx/packages/ti/drivers).

    Best regards,

    Janet

  • Thank u very mach!!! I found this log!!!

    But the problem remained. I made func for read from spi

    bool readW5100(SPIName numW5100, uint8_t *array, int len, int adrInW5100)
    {
        //взять мьютекс
        Semaphore_Handle sem = (numW5100 == SPI_W5100_1) ? semW5100_1 : semW5100_2;
        bool isSemPend;
        isSemPend = Semaphore_pend(sem, 1000);
        assert(isSemPend);

        SPI_Handle spiHandler = SPI_open(numW5100, (SPI_Params *)&paramsSPI);
        if(spiHandler == NULL)
        {
            System_abort("Error initializing spi");
            System_flush();
            return false;
        }

        for(int i = 0; i < len; i++)
            array[i] = readByte(spiHandler, adrInW5100++);

        SPI_close(spiHandler);

        Semaphore_post(sem);    //отдать мьютекс
        return true;
    }

    uint8_t readByte(SPI_Handle handler, uint16_t adrReg)
    {
        unsigned char txBuffer[5] =
        { 0x0f };
        unsigned char rxBuffer[5];
        txBuffer[1] = adrReg >> 8;
        txBuffer[2] = adrReg;

        SPI_Transaction masterTransaction;
        masterTransaction.count = 4;
        masterTransaction.arg = 0;
        masterTransaction.rxBuf = (Ptr)rxBuffer;
        masterTransaction.txBuf = (Ptr)txBuffer;

        assert(SPI_transfer(handler, &masterTransaction));
        return rxBuffer[3];
    }


    i call it from different task. If from task one - spi work good. u can see log and screen from oscilloscope

    D4 - is MOSI (D1 - cs, D0 - MISO, D5 - sclk). i can see normal mosi. The first byte on MOSI is 0x0f! Now i try call my readW5100() from another task

    D4 - ZERO!!! Where is 0x0f? I can see sclk, miso and clk. But i can not see only MOSI. Why? Why SPI does not work from another task?

  • You should be able to step into SPITivaDMA_transfer().  You can set a break point there, or step through your code and step into SPI_transfer().  The debugger may ask you where the source files are, which you can browse to (<TI-RTOS/products/tidrivers_tivac_2_xx_xx_xx/packages/ti/drivers).

    Yes, i think that i should be able to step into SPITivaDMA_transfer() too. But realy debugger does not work step by step. I step into SPITivaDMA_transfer() and try step by step.... u can see result in attach

    Why the debugger jumps in undefined order? How to get the debugger to step line by line in order?

    https://e2e.ti.com/cfs-file/__key/communityserver-discussions-components-files/355/2133.steps.7z

  • Hi Juvf,

    The jumping around in the debugger is due to optimization of code.  You might have an easier time if you copy the file SPITivaDMA.c to your project directory, and then build your project.

    Best regards,

    Janet


  • Hello

    You might have an easier time if you copy the file SPITivaDMA.c to your project directory, and then build your project.

     

    And so I did. Spike method.

    Why SPI does not work from another task? What can block MOSI? Maybe when context switching, any registers GPIO falling off? Where and what can I check?

    Help me, please.

  • Hi Juvf,

    We think we have found the problem in your  code.  The SPI driver uses DMA, and on your device, the buffers that the DMA uses must be in regions that the DMA can access.  If you look in the linker command file, TMDXDOCKH52C1_M3.cmd, you will see the section, ".dma":

        .dma        : > S07SHRAM

    with     S07SHRAM (RWX)  : origin = 0x20008000, length = 0x10000


    In the first task, the buffers fall in the .dma section: rxBuf = 0x20012dfe, txBfuf = 0x20012df6.  For the second task, they do not:: rxBuf = 0x20002116, txBuf = 0x2000210e.

    You could make these buffers static and use #pragma to place them in the .dma section.  Here is an example from the board file:

    #pragma DATA_SECTION(spiTivaDMAscratchBuf, ".dma");

    uint32_t spiTivaDMAscratchBuf[TMDXDOCKH52C1_SPICOUNT];

    Best regards,

    Janet

  • Hello Janet

    u are right! I made these buffers static and used #pragma to place them in the .dma section. The SPI works good now!!! Thanks u a lot!!!!

    Best regards,

    Juvf!
  • Great!  I'm glad to hear that solved the problem.

    Best regards,

    Janet