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/AM5728: SPI driver for M4 with Linux host

Part Number: AM5728
Other Parts Discussed in Thread: SYSBIOS

Tool/software: TI-RTOS

I am working with AM5728 EVM. I running Linux on A15 and RTOS on DSP and M4 cores. I am trying to setup SPI on M4. I have enabled spi4 using the device tree and am able to verify that on A15/Linux. As per my project requirements, I need to setup SPI on M4 processor.

I am trying to set-up the SPI on M4 like this -

// …
SPI_init(); //----If Linux is setting up IO, is this required?
SPI_Params spiParams;
SPI_Params_init(&spiParams);
// … …
SPI_open(CSL_MPU_MCSPI4, &spiParams);


But the M4 core crashes during call to SPI_open() -

“remoteproc0: crash detected in 58820000.ipu: type device exception”


All IO driver examples in the rtos sdk seem to support RTOS-only or bare-metal/standalone use-cases, i.e. without Linux host. Are there any IO driver examples for TI-RTOS with Linux host? How to read/write SPI on M4 with Linux host?

The RTOS SDK and Linux SDK versions are 03.01.00.06.

Thanks,

Jimit

  • The RTOS team have been notified. They will respond here.
  • Jimit,

    We recently have had many such requests to enable peripherals on the M4 when ARM  Linux is booted up hence, we have created a wiki article that talks through this process for both the DSP and M4. Currently the examples we used were GPIO on DSP and UART on the M4 and the steps to recreate the setup have been provided here:

    I hope this can provide you guidance in terms of how to go about creating M4 firmware that can be loaded using remoteproc:

    I have summarized the changes that you need :

    List of changes required to get IPC+PDK firmware running in Processor SDK:

    • Disable peripheral instances used in Linux kernel from device tree
    • Modify Carveouts and Resource table to adjust memory map/allocation (Optional Step. Start with default resource table in IPC)
    • Merge PDK driver code on IPU/DSP with IPC MessageQ code 
    • Change RTOS setup to use memory map from DRA7xx IPC resource table
    • Remove board library initialization and use CSL code to configure PRCM and clock. (All global pinmux and DPLL initialization should be done in uboot)
    • IPU specific changes: Remove AMMU configuration and use L2 MMU configuration from IPC. Requires changing driver code to use virtual address to access peripheral configuration registers.

    Please review the article and then let us know if you have any questions regarding this topic.

    Regards,

    Rahul

    PS: For resource table and memory map changes, refer to 

    http://processors.wiki.ti.com/index.php/IPC_Resource_customTable

     

  • Thanks Rahul, I will go over the wiki and would try to setup SPI. I would let you know how it goes. 

    Regards,

    Jimit

  • Rahul, 

    I followed the instructions from:

    processors.wiki.ti.com/.../Linux_IPC_on_AM57xx

    and I tried building the UART example with IPC (I used the default resource table in IPC). I get this error:

    **** Build of configuration Debug for project IPC_UART_Ex ****

    /home/hmedev/ti/ccsv6/utils/bin/gmake -k all
    Building file: ../uart_m4_evmAM572x.cfg
    Invoking: XDCtools
    "/home/hmedev/ti/xdctools_3_32_00_06_core/xs" --xdcpath="/home/hmedev/ti/edma3_lld_2_12_01_25/packages;/home/hmedev/ti/ipc_3_43_02_04/packages;/home/hmedev/ti/bios_6_45_01_29/packages;/home/hmedev/ti/pdk_am57xx_1_0_4/packages;/home/hmedev/ti/ndk_2_24_03_35/packages;/home/hmedev/ti/ccsv6/ccs_base;" xdc.tools.configuro -o configPkg -t ti.targets.arm.elf.M4 -p ti.platforms.evmAM572X:ipu2 -r debug -b "/home/hmedev/projects/IPC_UART_Ex/config.bld" -c "/home/hmedev/ti/ccsv6/tools/compiler/ti-cgt-arm_15.12.1.LTS" --cfgArgs "{ configBld: \"config.bld\" }" "../uart_m4_evmAM572x.cfg"
    configuring uart_m4_evmAM572x.xem4 from package/cfg/uart_m4_evmAM572x_pem4.cfg ...
    subdir_rules.mk:42: recipe for target 'configPkg/linker.cmd' failed
    warning: ti.sysbios.BIOS: "/home/hmedev/ti/bios_6_45_01_29/packages/ti/sysbios/BIOS.xs", line 314: ti.sysbios.BIOS heapSize: BIOS.heapSize and Memory.defaultHeapInstance have both been set. BIOS.heapSize ignored. Using Memory.defaultHeapInstance.

    error: ti.trace.SysMin: "/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs", line 51: ti.trace.SysMin : .tracebuf section found, but not in Program.cpu.memoryMap

     

    js: "/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs", line 55: TypeError: Cannot read property "len" from undefined (/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs#55)
    gmake: *** [package/cfg/uart_m4_evmAM572x_pem4.xdl] Error 1
    js: "/home/hmedev/ti/xdctools_3_32_00_06_core/packages/xdc/tools/Cmdr.xs", line 51: Error: xdc.tools.configuro: configuration failed due to earlier errors (status = 2); 'linker.cmd' deleted.
    gmake: *** [configPkg/linker.cmd] Error 1
    gmake: Target 'all' not remade because of errors.

    **** Build Finished ****

    I was not able to import the full CCS project downloaded from the wiki into my workspace because I have SDK version 03.01.00.06.I will update the SDK on my workstation and will try building the UART with IPC example.

    Thanks,

    Jimit

  • Jimit,

    IPC product requires AM57xx users to define their platform as 

    • For Target, select ti.targets.arm.elf.M4
    • For Platform, select ti.platforms.evmDRA7XX

    In your build, I still see the platform defined as  ti.platforms.evmAM572X:ipu2. 

    Can you change that try to rebuild this project.

    Regards,

    Rahul

  • Hi Rahul,

    I tried setting the target to ti.targets.arm.elf.M4 and platform to ti.platforms.evmDRA7XX. But, I still get the same error.

    **** Build of configuration Debug for project IPC_UART_Ex ****

    /home/hmedev/ti/ccsv6/utils/bin/gmake -k all
    Building file: ../uart_m4_evmAM572x.cfg
    Invoking: XDCtools
    "/home/hmedev/ti/xdctools_3_32_00_06_core/xs" --xdcpath="/home/hmedev/ti/edma3_lld_2_12_01_25/packages;/home/hmedev/ti/ipc_3_43_02_04/packages;/home/hmedev/ti/bios_6_45_01_29/packages;/home/hmedev/ti/pdk_am57xx_1_0_4/packages;/home/hmedev/ti/ndk_2_24_03_35/packages;/home/hmedev/ti/ccsv6/ccs_base;" xdc.tools.configuro -o configPkg -t ti.targets.arm.elf.M4 -p ti.platforms.evmDRA7XX -r debug -b "/home/hmedev/projects/IPC_UART_Ex/config.bld" -c "/home/hmedev/ti/ccsv6/tools/compiler/ti-cgt-arm_15.12.1.LTS" --cfgArgs "{ configBld: \"config.bld\" }" "../uart_m4_evmAM572x.cfg"
    configuring uart_m4_evmAM572x.xem4 from package/cfg/uart_m4_evmAM572x_pem4.cfg ...
    subdir_rules.mk:42: recipe for target 'configPkg/linker.cmd' failed
    warning: ti.sysbios.BIOS: "/home/hmedev/ti/bios_6_45_01_29/packages/ti/sysbios/BIOS.xs", line 314: ti.sysbios.BIOS heapSize: BIOS.heapSize and Memory.defaultHeapInstance have both been set. BIOS.heapSize ignored. Using Memory.defaultHeapInstance.


    error: ti.trace.SysMin: "/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs", line 51: ti.trace.SysMin : .tracebuf section found, but not in Program.cpu.memoryMap


    js: "/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs", line 55: TypeError: Cannot read property "len" from undefined (/home/hmedev/ti/ipc_3_43_02_04/packages/ti/trace/SysMin.xs#55)
    gmake: *** [package/cfg/uart_m4_evmAM572x_pem4.xdl] Error 1
    js: "/home/hmedev/ti/xdctools_3_32_00_06_core/packages/xdc/tools/Cmdr.xs", line 51: Error: xdc.tools.configuro: configuration failed due to earlier errors (status = 2); 'linker.cmd' deleted.
    gmake: *** [configPkg/linker.cmd] Error 1
    gmake: Target 'all' not remade because of errors.

    **** Build Finished ****

    I have attached my CCS project for reference. 

    IPC_UART_Ex.tar.gz

    Thanks,

    Jimit

  • Jimit,

    IF you look at the section Add_IPC_to_the_UART_Example, you need to add the core for which you plan to run to the option as well.

    For example if you want to build this for ipu1  or the dsp2,  you need to use "ti.platforms.evmDRA7XX:ipu1" or "ti.platforms.evmDRA7XX:dsp2".

    You had previously done this so I didn`t indicate it in my earlier response.

    A good way to check if you have correct project settings in CCS is to look at the compiler and RTSC settings in the makefile in IPC examples.

    ipc_3_46_00_02\examples\DRA7XX_linux_elf\ex02_messageq\ipu2

    Regards,

    Rahul

  • Rahul,

    Thanks! By setting the platform to "ti.platforms.evmDRA7XX:ipu2", I was able to get past this error.

    But, now I get compilation error about missing source file - which I think is because I am still using 03.01.00.06. I searched for csl_utils.h file in <sdk_install_path>/pdk_am57xx_1_0_4/packages/ti/csl/ directory and it's not there.

    >> Compilation failure
    subdir_rules.mk:21: recipe for target 'UART_soc.obj' failed
    "../UART_soc.c", line 39: fatal error #1965: cannot open source file "ti/csl/csl_utils.h"
    1 catastrophic error detected in the compilation of "../UART_soc.c".
    Compilation terminated.
    gmake: *** [UART_soc.obj] Error 1
    Building file: ../main_uart_example.c


    Thanks,
    Jimit
  • Jimit,

    That is correct, csl_utils.h seems to have been added in Processor SDK RTOS 3.03. you can find the CSL file in the public repos here:
    git.ti.com/.../csl_utils.h

    Regards,
    Rahul
  • Rahul,

    How to build this example for IPU1 instead of IPU2? I changed

    1) The platform definition to "ti.platforms.evmDRA7XX:ipu1",

    2) In the xdcscript, I set the Program.global.procName to "IPU1", and set the Core.ipuId to 1

    When I build and run the example with these changes, the /sys/kernel/debug/remoteproc/remoteproc0/state lists the IPU1 as offline. I compared the xdcscripts for IPU1 and IPU2 in the IPC example "ex02_messageq" and they seem to differ in clock configuration.

    What is the reason for commenting out the TICK section in the xdcscript for UART + IPC CCS project setup as described in the wiki: 

    processors.wiki.ti.com/.../Linux_IPC_on_AM57xx

    I am able to build and run the ex02_messageq on the IPU1, and want to run this integrated UART + IPC example on IPU1 too. In my project, I have requirement to use both IPU cores.

    Thanks,

    Jimit

  • I was able to run this on IPU1 after defining VAYU_IPU_1 in rsc_table_vayu_ipu.c.

    -Jimit

  • Yes, I was reviewing your post when you posted this. That was the only change that I was going to recommend for IPU1 :)

    I will get back to you on the issue of removing the TICK code in the configuration in a few days. One of my colleagues had recommended this change probably due to conflicts with timer usage in Linux but I will confirm that when he gets back from vacation.

    the other issue could be that the GPtimer, memory mapping needs to be adjusted based on resource Virtual address mapping. 

    Please go ahead and mark the issue resolved and close the ticket. If you have any further questions, feel free to open a new thread

    Regards,
    Rahul

  • Rahul,

    I extended the UART example to setup MCSPI4. I added this to board_init():

    CSL_FINST(l4PerCmReg->CM_L4PER_MCSPI4_CLKCTRL_REG,
    L4PER_CM_CORE_COMPONENT_CM_L4PER_MCSPI4_CLKCTRL_REG_MODULEMODE, ENABLE);

    while(CSL_L4PER_CM_CORE_COMPONENT_CM_L4PER_MCSPI4_CLKCTRL_REG_IDLEST_FUNC !=
    CSL_FEXT(l4PerCmReg->CM_L4PER_MCSPI4_CLKCTRL_REG,
    L4PER_CM_CORE_COMPONENT_CM_L4PER_MCSPI4_CLKCTRL_REG_IDLEST));

    And, then created a spi_test task, which initializes SPI and sends test data - 

    SPI_init();

    SPI_Params spiParams; /* SPI params structure */
    SPI_Handle handle; /* SPI handle */
    SPI_Transaction transaction; /* SPI transaction */


    SPI_Params_init(&spiParams);

    // Set params 
    spiParams.transferMode = SPI_MODE_BLOCKING;
    spiParams.transferTimeout = SPI_WAIT_FOREVER;
    spiParams.mode = SPI_MASTER;
    spiParams.bitRate = 500000;
    spiParams.transferCallbackFxn = NULL;
    spiParams.dataSize = 8;
    spiParams.frameFormat = SPI_POL1_PHA0;

    //////////////////////////////////////////////////////////////////////

    /* Open MCSPI4 */
    handle = SPI_open(3, &spiParams);

    if (handle)
    {
    System_printf("SPI opened : %x\n", handle);
    }

    //////////////////////////////////////////////////////////////////////

    while (handle)
    {

    // Buffer containing the data to be sent out
    uint8_t txBuf[10U] = {0xAAU, 0xBBU, 0xCCU, 0xDDU, 0xEEU, 0xFFU, 0x01, 0x02, 0x03, 0x04};

    // Buffer containing the received data
    //uint8_t rxBuf[1U] = {0xFFU};

    transaction.count = 1;
    transaction.txBuf = &txBuf[0];
    transaction.rxBuf = NULL; 

    System_printf("SPI sending data...\n");

    int retVal = SPI_transfer(handle, &transaction); // never returns from this method
    if ( !retVal )
    {
    System_printf("SPI failed to send data : %d \n", retVal);
    }
    else
    {
    System_printf("SPI sent data : %d \n", retVal);
    }

    }

     

    I tested out this code, SPI_open succeeds but it seems that it never returns from SPI_transfer() call. I see data being sent out on the logic analyzer, but sclk and cs0 don't toggle back. I verified that device tree had SPI4 enabled. I had updated the SPI_soc.c to include the 0x20000000 offset for CSL_IPU_MCSPI4_REGS, and added this to the xdc script:

     var Spi = xdc.loadPackage('ti.drv.spi');

    Thanks,

    Jimit

  • Jimit,

    Before integrating this in IPC environment, did you test the code by independently running it on the IPU ? I would use that as a starting point and isolate the debug to SPI driver or IPC related issue.

    Another thing is as we indicate on the wiki. If the SPI instance is used from the IPU, it needs to be disabled in the device tree so that IPU can control the resource as we did with UART instance. Can you disable this in Linux device tree and try. From the ARM Linux, we only require Uboot to setup the pinmux correctly for SPI4.

    Since you are not using DMA, MCSPI_primeTransfer_v1 will be used to transfer the data out. Please look at that function and try to isolate the issue inside that function call. If you are using interrupt mode then you also need to ensure that the

    Another potential place to check is for the SPI3 examples that we have in the SDK for this device, we make a call to MCSPI_Board_crossbarInit which sets up the cross bar and some clock enables which may be required even with SPI4 code. Note this may not be performed by

    Regards,
    Rahul