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.

AM625: PRU memory error

Part Number: AM625
Other Parts Discussed in Thread: SYSCONFIG

Basically, at the beginning, I have a serial code, which runs in code composer, however, when I increase the size of the transmission buffer, the error occurs. When I increase the stack size, the error disappears, but, if I use the TEXAS INSTRUMENTS example code for the virtio RPMSG protocol, the same error breaks the code again and, even increasing the stack size, it never loads into the PRU. The compiler compiles the code normally, only the loading fails.

  • The Code Composer Studio version is 12.6.0

  • Hello Rafael,

    My Linux computer just died, so I am temporarily unable to run tests on my side.

    When you build your binaries, do you generate a .map file in the outputs folder? Does inspecting the .map file offer any clues about how the memory is getting allocated, and whether any of your memory regions are not large enough for the data that you want to place in them?

    virtio RPMsg will probably not work with Linux if the code is loaded from CCS instead of Linux. Linux has no way of knowing that the PRU cores have been initialized by someone else, so I would expect that the PRU program would just hang in the while loop below comment "Make sure the Linux drivers are ready for RPMsg communication"
    https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/examples/am62x/PRU_RPMsg_Echo_Interrupt0/main.c

    However, I would NOT expect the unmodified virtio RPMsg code to prevent CCS from even initializing the PRU core.

    Regards,

    Nick

  • The problem is that it's not just with RPSmsg, but, as I showed in the example video, even increasing a string while having a low stack value ( 0x100 ) already reproduces the same error, but at different addresses. I believe it's a problem in the stack.

    The .map file is this:

    ******************************************************************************
                         PRU Linker PC v2.3.3                      
    ******************************************************************************
    >> Linked Wed Mar 13 11:16:29 2024
    
    OUTPUT FILE NAME:   <Teste.out>
    ENTRY POINT SYMBOL: "_c_int00_noinit_noargs"  address: 00000000
    
    
    MEMORY CONFIGURATION
    
             name            origin    length      used     unused   attr    fill
    ----------------------  --------  ---------  --------  --------  ----  --------
    PAGE 0:
      PRU_IMEM              00000000   00003000  0000028c  00002d74  RWIX
    
    PAGE 1:
      PRU0_DMEM_0           00000000   00002000  0000105c  00000fa4  RWIX
      PRU0_DMEM_1           00002000   00002000  00000000  00002000  RWIX
    
    PAGE 2:
      PRU_RAT0              00008000   00000854  00000000  00000854  RWIX
      PRU_SHAREDMEM         00010000   00008000  00000000  00008000  RWIX
      PRU_INTC              00020000   00001504  00000000  00001504  RWIX
      PRU0_CTRL             00022000   00000030  00000000  00000030  RWIX
      RSVD14                00024800   00000100  00000000  00000100  RWIX
      PRU_CFG               00026000   00000100  00000000  00000100  RWIX
      PRU_CFG_0x100         00026100   00000098  00000000  00000098  RWIX
      RSVD12                00027000   00000100  00000000  00000100  RWIX
      PRU_UART              00028000   00000038  00000038  00000000  RWIX
      RSVD10                0002a000   00000100  00000000  00000100  RWIX
      RSVD13                0002c000   00000100  00000000  00000100  RWIX
      PRU_IEP0              0002e000   00000100  00000000  00000100  RWIX
      PRU_IEP0_0x100        0002e100   0000021c  00000000  0000021c  RWIX
      PRU_IEP1              0002f000   00000100  00000000  00000100  RWIX
      PRU_IEP1_0x100        0002f100   0000021c  00000000  0000021c  RWIX
      PRU_ECAP              00030000   00000060  00000000  00000060  RWIX
      RSVD27                00032000   00000100  00000000  00000100  RWIX
      RSVD21                00032400   00000100  00000000  00000100  RWIX
      RSVD9                 00033000   00000100  00000000  00000100  RWIX
      RSVD15                60000000   00000100  00000000  00000100  RWIX
      RSVD16                70000000   00000100  00000000  00000100  RWIX
      RSVD17                80000000   00000100  00000000  00000100  RWIX
      RSVD18                90000000   00000100  00000000  00000100  RWIX
      RSVD19                a0000000   00000100  00000000  00000100  RWIX
      RSVD20                b0000000   00000100  00000000  00000100  RWIX
      RSVD23                c0000000   00000100  00000000  00000100  RWIX
      RSVD29                d0000000   00010000  00000000  00010000  RWIX
      RSVD30                e0000000   00010000  00000000  00010000  RWIX
      RSVD31                f0000000   00010000  00000000  00010000  RWIX
    
    
    SECTION ALLOCATION MAP
    
     output                                  attributes/
    section   page    origin      length       input sections
    --------  ----  ----------  ----------   ----------------
    .text:_c_int00* 
    *          0    00000000    0000001c     
                      00000000    0000001c     rtspruv3_le.lib : boot.c.obj (.text:_c_int00_noinit_noargs)
    
    .text      0    0000001c    00000270     
                      0000001c    00000260     main.obj (.text:main)
                      0000027c    00000008     rtspruv3_le.lib : exit.c.obj (.text:abort)
                      00000284    00000008                     : exit.c.obj (.text:loader_exit)
    
    .stack     1    00000000    00001000     UNINITIALIZED
                      00000000    00000004     rtspruv3_le.lib : boot.c.obj (.stack)
                      00000004    00000ffc     --HOLE--
    
    .cinit     1    00000000    00000000     UNINITIALIZED
    
    .rodata    1    00001058    00000004     
                      00001058    00000004     main.obj (.rodata:.string)
    
    .resource_table 
    *          1    00001000    00000058     
                      00001000    00000058     main.obj (.resource_table:retain)
    
    .creg.PRU_UART.noload.near 
    *          2    00028000    00000000     NOLOAD SECTION
    
    .creg.PRU_UART.near 
    *          2    00028000    00000000     UNINITIALIZED
    
    .creg.PRU_UART.noload.far 
    *          2    00028000    00000038     NOLOAD SECTION
                      00028000    00000038     main.obj (.creg.PRU_UART.noload.far)
    
    .creg.PRU_UART.far 
    *          2    00028038    00000000     UNINITIALIZED
    
    MODULE SUMMARY
    
           Module         code   ro data   rw data
           ------         ----   -------   -------
        .\
           main.obj       608    4         144    
        +--+--------------+------+---------+---------+
           Total:         608    4         144    
                                                  
        C:\ti\ccs1260\ccs\tools\compiler\ti-cgt-pru_2.3.3\lib\rtspruv3_le.lib
           boot.c.obj     28     0         0      
           exit.c.obj     16     0         0      
        +--+--------------+------+---------+---------+
           Total:         44     0         0      
                                                  
           Stack:         0      0         4096   
        +--+--------------+------+---------+---------+
           Grand Total:   652    4         4240   
    
    
    SEGMENT ATTRIBUTES
    
        id tag      seg value
        -- ---      --- -----
         0 PHA_PAGE 1   1    
         1 PHA_PAGE 2   1    
         2 PHA_PAGE 3   1    
    
    
    GLOBAL SYMBOLS: SORTED ALPHABETICALLY BY Name 
    
    page  address   name                          
    ----  -------   ----                          
    0     00000284  C$$EXIT                       
    2     00028000  CT_UART                       
    abs   00022000  __PRU_CREG_BASE_PRU0_CTRL     
    abs   00000000  __PRU_CREG_BASE_PRU0_DMEM_0   
    abs   00002000  __PRU_CREG_BASE_PRU0_DMEM_1   
    abs   00026000  __PRU_CREG_BASE_PRU_CFG       
    abs   00026100  __PRU_CREG_BASE_PRU_CFG_0x100 
    abs   00030000  __PRU_CREG_BASE_PRU_ECAP      
    abs   0002e000  __PRU_CREG_BASE_PRU_IEP0      
    abs   0002e100  __PRU_CREG_BASE_PRU_IEP0_0x100
    abs   0002f000  __PRU_CREG_BASE_PRU_IEP1      
    abs   0002f100  __PRU_CREG_BASE_PRU_IEP1_0x100
    abs   00020000  __PRU_CREG_BASE_PRU_INTC      
    abs   00008000  __PRU_CREG_BASE_PRU_RAT0      
    abs   00010000  __PRU_CREG_BASE_PRU_SHAREDMEM 
    abs   00028000  __PRU_CREG_BASE_PRU_UART      
    abs   0002a000  __PRU_CREG_BASE_RSVD10        
    abs   00027000  __PRU_CREG_BASE_RSVD12        
    abs   0002c000  __PRU_CREG_BASE_RSVD13        
    abs   00024800  __PRU_CREG_BASE_RSVD14        
    abs   60000000  __PRU_CREG_BASE_RSVD15        
    abs   70000000  __PRU_CREG_BASE_RSVD16        
    abs   80000000  __PRU_CREG_BASE_RSVD17        
    abs   90000000  __PRU_CREG_BASE_RSVD18        
    abs   a0000000  __PRU_CREG_BASE_RSVD19        
    abs   b0000000  __PRU_CREG_BASE_RSVD20        
    abs   00032400  __PRU_CREG_BASE_RSVD21        
    abs   c0000000  __PRU_CREG_BASE_RSVD23        
    abs   00032000  __PRU_CREG_BASE_RSVD27        
    abs   d0000000  __PRU_CREG_BASE_RSVD29        
    abs   e0000000  __PRU_CREG_BASE_RSVD30        
    abs   f0000000  __PRU_CREG_BASE_RSVD31        
    abs   00033000  __PRU_CREG_BASE_RSVD9         
    abs   0000000b  __PRU_CREG_PRU0_CTRL          
    abs   00000018  __PRU_CREG_PRU0_DMEM_0        
    abs   00000019  __PRU_CREG_PRU0_DMEM_1        
    abs   00000004  __PRU_CREG_PRU_CFG            
    abs   00000005  __PRU_CREG_PRU_CFG_0x100      
    abs   00000003  __PRU_CREG_PRU_ECAP           
    abs   0000001a  __PRU_CREG_PRU_IEP0           
    abs   00000008  __PRU_CREG_PRU_IEP0_0x100     
    abs   00000001  __PRU_CREG_PRU_IEP1           
    abs   00000002  __PRU_CREG_PRU_IEP1_0x100     
    abs   00000000  __PRU_CREG_PRU_INTC           
    abs   00000016  __PRU_CREG_PRU_RAT0           
    abs   0000001c  __PRU_CREG_PRU_SHAREDMEM      
    abs   00000007  __PRU_CREG_PRU_UART           
    abs   0000000a  __PRU_CREG_RSVD10             
    abs   0000000c  __PRU_CREG_RSVD12             
    abs   0000000d  __PRU_CREG_RSVD13             
    abs   0000000e  __PRU_CREG_RSVD14             
    abs   0000000f  __PRU_CREG_RSVD15             
    abs   00000010  __PRU_CREG_RSVD16             
    abs   00000011  __PRU_CREG_RSVD17             
    abs   00000012  __PRU_CREG_RSVD18             
    abs   00000013  __PRU_CREG_RSVD19             
    abs   00000014  __PRU_CREG_RSVD20             
    abs   00000015  __PRU_CREG_RSVD21             
    abs   00000017  __PRU_CREG_RSVD23             
    abs   0000001b  __PRU_CREG_RSVD27             
    abs   0000001d  __PRU_CREG_RSVD29             
    abs   0000001e  __PRU_CREG_RSVD30             
    abs   0000001f  __PRU_CREG_RSVD31             
    abs   00000009  __PRU_CREG_RSVD9              
    1     00001000  __TI_STACK_END                
    abs   00001000  __TI_STACK_SIZE               
    abs   ffffffff  __c_args__                    
    0     00000000  _c_int00_noinit_noargs        
    1     00000000  _stack                        
    0     0000027c  abort                         
    0     0000001c  main                          
    1     00001000  resourceTable                 
    
    GLOBAL SYMBOLS: SORTED BY Symbol Address 
    
    page  address   name                          
    ----  -------   ----                          
    0     00000000  _c_int00_noinit_noargs        
    0     0000001c  main                          
    0     0000027c  abort                         
    0     00000284  C$$EXIT                       
    1     00000000  _stack                        
    1     00001000  __TI_STACK_END                
    1     00001000  resourceTable                 
    2     00028000  CT_UART                       
    abs   00000000  __PRU_CREG_BASE_PRU0_DMEM_0   
    abs   00000000  __PRU_CREG_PRU_INTC           
    abs   00000001  __PRU_CREG_PRU_IEP1           
    abs   00000002  __PRU_CREG_PRU_IEP1_0x100     
    abs   00000003  __PRU_CREG_PRU_ECAP           
    abs   00000004  __PRU_CREG_PRU_CFG            
    abs   00000005  __PRU_CREG_PRU_CFG_0x100      
    abs   00000007  __PRU_CREG_PRU_UART           
    abs   00000008  __PRU_CREG_PRU_IEP0_0x100     
    abs   00000009  __PRU_CREG_RSVD9              
    abs   0000000a  __PRU_CREG_RSVD10             
    abs   0000000b  __PRU_CREG_PRU0_CTRL          
    abs   0000000c  __PRU_CREG_RSVD12             
    abs   0000000d  __PRU_CREG_RSVD13             
    abs   0000000e  __PRU_CREG_RSVD14             
    abs   0000000f  __PRU_CREG_RSVD15             
    abs   00000010  __PRU_CREG_RSVD16             
    abs   00000011  __PRU_CREG_RSVD17             
    abs   00000012  __PRU_CREG_RSVD18             
    abs   00000013  __PRU_CREG_RSVD19             
    abs   00000014  __PRU_CREG_RSVD20             
    abs   00000015  __PRU_CREG_RSVD21             
    abs   00000016  __PRU_CREG_PRU_RAT0           
    abs   00000017  __PRU_CREG_RSVD23             
    abs   00000018  __PRU_CREG_PRU0_DMEM_0        
    abs   00000019  __PRU_CREG_PRU0_DMEM_1        
    abs   0000001a  __PRU_CREG_PRU_IEP0           
    abs   0000001b  __PRU_CREG_RSVD27             
    abs   0000001c  __PRU_CREG_PRU_SHAREDMEM      
    abs   0000001d  __PRU_CREG_RSVD29             
    abs   0000001e  __PRU_CREG_RSVD30             
    abs   0000001f  __PRU_CREG_RSVD31             
    abs   00001000  __TI_STACK_SIZE               
    abs   00002000  __PRU_CREG_BASE_PRU0_DMEM_1   
    abs   00008000  __PRU_CREG_BASE_PRU_RAT0      
    abs   00010000  __PRU_CREG_BASE_PRU_SHAREDMEM 
    abs   00020000  __PRU_CREG_BASE_PRU_INTC      
    abs   00022000  __PRU_CREG_BASE_PRU0_CTRL     
    abs   00024800  __PRU_CREG_BASE_RSVD14        
    abs   00026000  __PRU_CREG_BASE_PRU_CFG       
    abs   00026100  __PRU_CREG_BASE_PRU_CFG_0x100 
    abs   00027000  __PRU_CREG_BASE_RSVD12        
    abs   00028000  __PRU_CREG_BASE_PRU_UART      
    abs   0002a000  __PRU_CREG_BASE_RSVD10        
    abs   0002c000  __PRU_CREG_BASE_RSVD13        
    abs   0002e000  __PRU_CREG_BASE_PRU_IEP0      
    abs   0002e100  __PRU_CREG_BASE_PRU_IEP0_0x100
    abs   0002f000  __PRU_CREG_BASE_PRU_IEP1      
    abs   0002f100  __PRU_CREG_BASE_PRU_IEP1_0x100
    abs   00030000  __PRU_CREG_BASE_PRU_ECAP      
    abs   00032000  __PRU_CREG_BASE_RSVD27        
    abs   00032400  __PRU_CREG_BASE_RSVD21        
    abs   00033000  __PRU_CREG_BASE_RSVD9         
    abs   60000000  __PRU_CREG_BASE_RSVD15        
    abs   70000000  __PRU_CREG_BASE_RSVD16        
    abs   80000000  __PRU_CREG_BASE_RSVD17        
    abs   90000000  __PRU_CREG_BASE_RSVD18        
    abs   a0000000  __PRU_CREG_BASE_RSVD19        
    abs   b0000000  __PRU_CREG_BASE_RSVD20        
    abs   c0000000  __PRU_CREG_BASE_RSVD23        
    abs   d0000000  __PRU_CREG_BASE_RSVD29        
    abs   e0000000  __PRU_CREG_BASE_RSVD30        
    abs   f0000000  __PRU_CREG_BASE_RSVD31        
    abs   ffffffff  __c_args__                    
    
    [72 symbols]
    

    As you can see, the stack is always full. Can you help me find the problem? I've been stuck in this same mistake for a week.

  • Hi,

    Can you try increasing the stack size and run the example?

    Meanwhile, I will try to run the example on my setup and check.

    Regards,

    Nitika

  • In the video example, I change the stack size on the properties of the project, at PRU linker part, and it just change the address of the error message

  • To make the problem clearer, I made a complete video running the program and showing the errors, looking at the .map.

    I apologize for the gaffes in English. It's not my native language!

    Where did I get the example from:

    git.ti.com/.../PRU_RPMsg_Echo_Interrupt0

  • I have include the rpmsg.lib file and the UNDEFED functions error has ben solved, but the memory  error is still here:

    PRU_ICSS_PRU_0: File Loader: Verification failed: Values at address 0x000014F0@Data_Memory do not match Please verify target memory and memory map.
    PRU_ICSS_PRU_0: GEL: File: C:\Users\rafael.volkmer\workspace_v12\Teste\Debug\Teste.out: a data verification error occurred, file load failed.

  • Hello Rafael,

    thanks for the update. I'm not sure if Nitika was able to replicate your test results from this thread before she had to pass the thread back to me. I am planning to take a closer look at this thread once I'm back from vacation the first week of April.

    Regards,

    Nick

  • Hello, Nick!

    I was testing the MCU - M4F0, for AM62x too. Now, i have the same problem that i had with the PRU.

    This is the error that i have with the actual load .out from my project at CCS:

    But, if i load a .out build at SDK with the gmake in Power Shwll, like the code below, it is work.

    gmake -s -C \ti\mcu_plus_sdk_am62x_08_03_00_07\examples\hello_world\am62x-sk\m4fss0-0_nortos\ti-arm-clang

    For example, the hello_word.out in the examples folder, it's run nice. That makes me thing this is a problem with some CCS configuration, maybe.

    I will wait you to reply me next week. I really need some especif help with that. Is my first time use ti IDE.

  • I think the problem is with syscfg. Can you help-me configure the syscfg with PRU and M4F?

  • Hello Rafael,

    I'm quickly checking in with you before I'm back on vacation on Friday (I'll still be back the first week of April as promised. The first week of April is when I'll try to port the UART example to AM62x).

    make from the command line vs make from CCS 

    Have you already gone through the PRU Getting Started Labs? If not, please go through those for me. 
    https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_01_00_08/exports/docs/common/PRU-ICSS/PRU-Getting-Started-Labs.html 

    The last time I used CCS to build a PRU project was with AM62x SDK 8.3 while I was writing those labs. Let's see if you are still running into issues after following all the steps to set up your CCS environment.

    SysConfig settings?

    With PRU projects, we do not typically do any sysconfig configuration. This isn't too bad if the PRU only controls peripherals within the PRU subsystem - you just need to make sure you add the PRU pinmuxing to the Linux devicetree somewhere within an existing pinmux setting.

    If the PRU needs to control another peripheral on the processor, it gets more complex since we need a way to tell SYSFW that the PRU is getting ownership of those peripherals. I have not had time to dig into what that looks like for K3 devices like AM62x and AM64x - it is definitely possible and it has been done by some of my team members, but it is not straightforward with our current tools.

    For M4F, you DO configure the M4F using SysConfig. If you have not yet followed the MCU+ SDK docs, I would start by looking at this page:
    https://software-dl.ti.com/mcu-plus-sdk/esd/AM62X/09_01_00_39/exports/docs/api_guide_am62x/SYSCONFIG_INTRO_PAGE.html

    Regards,

    Nick

  • For more informations:

    This is my video try to load the firmware per CCS, but build the .out by gmake cmd command at the example of PRU SUPPORT PACKAGE 6.3.0

    Here is the video of the bug in real time:

    In using the base image provide by texas on a sd card to boot my device kit: tisdk-default-image-am62xx-evm.wic 

    .map is here:

    ******************************************************************************
                         PRU Linker PC v2.3.3                      
    ******************************************************************************
    >> Linked Mon Apr  1 09:52:18 2024
    
    OUTPUT FILE NAME:   <gen/PRU_RPMsg_Echo_Interrupt1.out>
    ENTRY POINT SYMBOL: "_c_int00_noinit_noargs"  address: 00000000
    
    
    MEMORY CONFIGURATION
    
             name            origin    length      used     unused   attr    fill
    ----------------------  --------  ---------  --------  --------  ----  --------
    PAGE 0:
      PRU_IMEM              00000000   00003000  000004d4  00002b2c  RWIX
    
    PAGE 1:
      PRU1_DMEM_1           00000000   00002000  00000354  00001cac  RWIX
      PRU1_DMEM_0           00002000   00002000  00000000  00002000  RWIX
    
    PAGE 2:
      PRU_RAT1              00009000   00000854  00000000  00000854  RWIX
      PRU_SHAREDMEM         00010000   00008000  00000000  00008000  RWIX
      PRU_INTC              00020000   00001504  00001504  00000000  RWIX
      PRU1_CTRL             00024000   00000030  00000000  00000030  RWIX
      RSVD14                00024800   00000100  00000000  00000100  RWIX
      PRU_CFG               00026000   00000100  00000000  00000100  RWIX
      PRU_CFG_0x100         00026100   00000098  00000000  00000098  RWIX
      RSVD12                00027000   00000100  00000000  00000100  RWIX
      PRU_UART              00028000   00000038  00000000  00000038  RWIX
      RSVD10                0002a000   00000100  00000000  00000100  RWIX
      RSVD13                0002c000   00000100  00000000  00000100  RWIX
      PRU_IEP0              0002e000   00000100  00000000  00000100  RWIX
      PRU_IEP0_0x100        0002e100   0000021c  00000000  0000021c  RWIX
      PRU_IEP1              0002f000   00000100  00000000  00000100  RWIX
      PRU_IEP1_0x100        0002f100   0000021c  00000000  0000021c  RWIX
      PRU_ECAP              00030000   00000060  00000000  00000060  RWIX
      RSVD27                00032000   00000100  00000000  00000100  RWIX
      RSVD21                00032400   00000100  00000000  00000100  RWIX
      RSVD9                 00033000   00000100  00000000  00000100  RWIX
      RSVD15                60000000   00000100  00000000  00000100  RWIX
      RSVD16                70000000   00000100  00000000  00000100  RWIX
      RSVD17                80000000   00000100  00000000  00000100  RWIX
      RSVD18                90000000   00000100  00000000  00000100  RWIX
      RSVD19                a0000000   00000100  00000000  00000100  RWIX
      RSVD20                b0000000   00000100  00000000  00000100  RWIX
      RSVD23                c0000000   00000100  00000000  00000100  RWIX
      RSVD29                d0000000   00010000  00000000  00010000  RWIX
      RSVD30                e0000000   00010000  00000000  00010000  RWIX
      RSVD31                f0000000   00010000  00000000  00010000  RWIX
    
    
    SECTION ALLOCATION MAP
    
     output                                  attributes/
    section   page    origin      length       input sections
    --------  ----  ----------  ----------   ----------------
    .text:_c_int00* 
    *          0    00000000    0000001c     
                      00000000    0000001c     rtspruv3_le.lib : boot.c.obj (.text:_c_int00_noinit_noargs)
    
    .text      0    0000001c    000004b8     
                      0000001c    000000e4     rpmsg_lib.lib : pru_rpmsg.object (.text:pru_rpmsg_send)
                      00000100    000000d8                   : pru_rpmsg.object (.text:pru_rpmsg_receive)
                      000001d8    000000c0     main.object (.text:main)
                      00000298    00000060     rpmsg_lib.lib : pru_rpmsg.object (.text:pru_rpmsg_init)
                      000002f8    00000060                   : pru_virtqueue.object (.text:pru_virtqueue_get_avail_buf)
                      00000358    00000060                   : pru_virtqueue.object (.text:pru_virtqueue_init)
                      000003b8    0000005c                   : pru_virtqueue.object (.text:pru_virtqueue_add_used_buf)
                      00000414    00000054                   : pru_rpmsg.object (.text:pru_rpmsg_channel)
                      00000468    00000034     rtspruv3_le.lib : memcpy.asm.obj (.text)
                      0000049c    00000028     rpmsg_lib.lib : pru_virtqueue.object (.text:pru_virtqueue_kick)
                      000004c4    00000008     rtspruv3_le.lib : exit.c.obj (.text:abort)
                      000004cc    00000008                     : exit.c.obj (.text:loader_exit)
    
    .bss       1    00000000    000001f0     UNINITIALIZED
                      00000000    000001f0     (.common:payload)
    
    .stack     1    000001f0    00000100     UNINITIALIZED
                      000001f0    00000004     rtspruv3_le.lib : boot.c.obj (.stack)
                      000001f4    000000fc     --HOLE--
    
    .cinit     1    00000000    00000000     UNINITIALIZED
    
    .rodata    1    00000348    0000000c     
                      00000348    0000000c     main.object (.rodata:.string)
    
    .resource_table 
    *          1    000002f0    00000058     
                      000002f0    00000058     main.object (.resource_table:retain)
    
    .pru_irq_map 
    *          0    00000000    00000005     COPY SECTION
                      00000000    00000005     main.object (.pru_irq_map:retain)
    
    .creg.PRU_INTC.noload.near 
    *          2    00020000    00000000     NOLOAD SECTION
    
    .creg.PRU_INTC.near 
    *          2    00020000    00000000     UNINITIALIZED
    
    .creg.PRU_INTC.noload.far 
    *          2    00020000    00001504     NOLOAD SECTION
                      00020000    00001504     main.object (.creg.PRU_INTC.noload.far)
    
    .creg.PRU_INTC.far 
    *          2    00021504    00000000     UNINITIALIZED
    
    MODULE SUMMARY
    
           Module                 code   ro data   rw data
           ------                 ----   -------   -------
        gen\
           main.object            192    12        5964   
        +--+----------------------+------+---------+---------+
           Total:                 192    12        5964   
                                                          
        ../../../lib/rpmsg_lib.lib
           pru_rpmsg.object       624    0         0      
           pru_virtqueue.object   324    0         0      
        +--+----------------------+------+---------+---------+
           Total:                 948    0         0      
                                                          
        C:\ti\ccs1250\ccs\tools\compiler\ti-cgt-pru_2.3.3\lib\rtspruv3_le.lib
           memcpy.asm.obj         52     0         0      
           boot.c.obj             28     0         0      
           exit.c.obj             16     0         0      
        +--+----------------------+------+---------+---------+
           Total:                 96     0         0      
                                                          
           Stack:                 0      0         256    
        +--+----------------------+------+---------+---------+
           Grand Total:           1236   12        6220   
    
    
    SEGMENT ATTRIBUTES
    
        id tag      seg value
        -- ---      --- -----
         0 PHA_PAGE 1   1    
         1 PHA_PAGE 2   1    
         2 PHA_PAGE 3   1    
    
    
    GLOBAL SYMBOLS: SORTED ALPHABETICALLY BY Name 
    
    page  address   name                          
    ----  -------   ----                          
    0     000004cc  C$$EXIT                       
    2     00020000  CT_INTC                       
    abs   00024000  __PRU_CREG_BASE_PRU1_CTRL     
    abs   00002000  __PRU_CREG_BASE_PRU1_DMEM_0   
    abs   00000000  __PRU_CREG_BASE_PRU1_DMEM_1   
    abs   00026000  __PRU_CREG_BASE_PRU_CFG       
    abs   00026100  __PRU_CREG_BASE_PRU_CFG_0x100 
    abs   00030000  __PRU_CREG_BASE_PRU_ECAP      
    abs   0002e000  __PRU_CREG_BASE_PRU_IEP0      
    abs   0002e100  __PRU_CREG_BASE_PRU_IEP0_0x100
    abs   0002f000  __PRU_CREG_BASE_PRU_IEP1      
    abs   0002f100  __PRU_CREG_BASE_PRU_IEP1_0x100
    abs   00020000  __PRU_CREG_BASE_PRU_INTC      
    abs   00009000  __PRU_CREG_BASE_PRU_RAT1      
    abs   00010000  __PRU_CREG_BASE_PRU_SHAREDMEM 
    abs   00028000  __PRU_CREG_BASE_PRU_UART      
    abs   0002a000  __PRU_CREG_BASE_RSVD10        
    abs   00027000  __PRU_CREG_BASE_RSVD12        
    abs   0002c000  __PRU_CREG_BASE_RSVD13        
    abs   00024800  __PRU_CREG_BASE_RSVD14        
    abs   60000000  __PRU_CREG_BASE_RSVD15        
    abs   70000000  __PRU_CREG_BASE_RSVD16        
    abs   80000000  __PRU_CREG_BASE_RSVD17        
    abs   90000000  __PRU_CREG_BASE_RSVD18        
    abs   a0000000  __PRU_CREG_BASE_RSVD19        
    abs   b0000000  __PRU_CREG_BASE_RSVD20        
    abs   00032400  __PRU_CREG_BASE_RSVD21        
    abs   c0000000  __PRU_CREG_BASE_RSVD23        
    abs   00032000  __PRU_CREG_BASE_RSVD27        
    abs   d0000000  __PRU_CREG_BASE_RSVD29        
    abs   e0000000  __PRU_CREG_BASE_RSVD30        
    abs   f0000000  __PRU_CREG_BASE_RSVD31        
    abs   00033000  __PRU_CREG_BASE_RSVD9         
    abs   0000000b  __PRU_CREG_PRU1_CTRL          
    abs   00000019  __PRU_CREG_PRU1_DMEM_0        
    abs   00000018  __PRU_CREG_PRU1_DMEM_1        
    abs   00000004  __PRU_CREG_PRU_CFG            
    abs   00000005  __PRU_CREG_PRU_CFG_0x100      
    abs   00000003  __PRU_CREG_PRU_ECAP           
    abs   0000001a  __PRU_CREG_PRU_IEP0           
    abs   00000008  __PRU_CREG_PRU_IEP0_0x100     
    abs   00000001  __PRU_CREG_PRU_IEP1           
    abs   00000002  __PRU_CREG_PRU_IEP1_0x100     
    abs   00000000  __PRU_CREG_PRU_INTC           
    abs   00000016  __PRU_CREG_PRU_RAT1           
    abs   0000001c  __PRU_CREG_PRU_SHAREDMEM      
    abs   00000007  __PRU_CREG_PRU_UART           
    abs   0000000a  __PRU_CREG_RSVD10             
    abs   0000000c  __PRU_CREG_RSVD12             
    abs   0000000d  __PRU_CREG_RSVD13             
    abs   0000000e  __PRU_CREG_RSVD14             
    abs   0000000f  __PRU_CREG_RSVD15             
    abs   00000010  __PRU_CREG_RSVD16             
    abs   00000011  __PRU_CREG_RSVD17             
    abs   00000012  __PRU_CREG_RSVD18             
    abs   00000013  __PRU_CREG_RSVD19             
    abs   00000014  __PRU_CREG_RSVD20             
    abs   00000015  __PRU_CREG_RSVD21             
    abs   00000017  __PRU_CREG_RSVD23             
    abs   0000001b  __PRU_CREG_RSVD27             
    abs   0000001d  __PRU_CREG_RSVD29             
    abs   0000001e  __PRU_CREG_RSVD30             
    abs   0000001f  __PRU_CREG_RSVD31             
    abs   00000009  __PRU_CREG_RSVD9              
    1     000002f0  __TI_STACK_END                
    abs   00000100  __TI_STACK_SIZE               
    abs   ffffffff  __c_args__                    
    0     00000000  _c_int00_noinit_noargs        
    1     000001f0  _stack                        
    0     000004c4  abort                         
    0     000001d8  main                          
    0     00000468  memcpy                        
    0     00000000  my_irq_rsc                    
    1     00000000  payload                       
    0     00000414  pru_rpmsg_channel             
    0     00000298  pru_rpmsg_init                
    0     00000100  pru_rpmsg_receive             
    0     0000001c  pru_rpmsg_send                
    0     000003b8  pru_virtqueue_add_used_buf    
    0     000002f8  pru_virtqueue_get_avail_buf   
    0     00000358  pru_virtqueue_init            
    0     0000049c  pru_virtqueue_kick            
    1     000002f0  resourceTable                 
    
    
    GLOBAL SYMBOLS: SORTED BY Symbol Address 
    
    page  address   name                          
    ----  -------   ----                          
    0     00000000  _c_int00_noinit_noargs        
    0     00000000  my_irq_rsc                    
    0     0000001c  pru_rpmsg_send                
    0     00000100  pru_rpmsg_receive             
    0     000001d8  main                          
    0     00000298  pru_rpmsg_init                
    0     000002f8  pru_virtqueue_get_avail_buf   
    0     00000358  pru_virtqueue_init            
    0     000003b8  pru_virtqueue_add_used_buf    
    0     00000414  pru_rpmsg_channel             
    0     00000468  memcpy                        
    0     0000049c  pru_virtqueue_kick            
    0     000004c4  abort                         
    0     000004cc  C$$EXIT                       
    1     00000000  payload                       
    1     000001f0  _stack                        
    1     000002f0  __TI_STACK_END                
    1     000002f0  resourceTable                 
    2     00020000  CT_INTC                       
    abs   00000000  __PRU_CREG_BASE_PRU1_DMEM_1   
    abs   00000000  __PRU_CREG_PRU_INTC           
    abs   00000001  __PRU_CREG_PRU_IEP1           
    abs   00000002  __PRU_CREG_PRU_IEP1_0x100     
    abs   00000003  __PRU_CREG_PRU_ECAP           
    abs   00000004  __PRU_CREG_PRU_CFG            
    abs   00000005  __PRU_CREG_PRU_CFG_0x100      
    abs   00000007  __PRU_CREG_PRU_UART           
    abs   00000008  __PRU_CREG_PRU_IEP0_0x100     
    abs   00000009  __PRU_CREG_RSVD9              
    abs   0000000a  __PRU_CREG_RSVD10             
    abs   0000000b  __PRU_CREG_PRU1_CTRL          
    abs   0000000c  __PRU_CREG_RSVD12             
    abs   0000000d  __PRU_CREG_RSVD13             
    abs   0000000e  __PRU_CREG_RSVD14             
    abs   0000000f  __PRU_CREG_RSVD15             
    abs   00000010  __PRU_CREG_RSVD16             
    abs   00000011  __PRU_CREG_RSVD17             
    abs   00000012  __PRU_CREG_RSVD18             
    abs   00000013  __PRU_CREG_RSVD19             
    abs   00000014  __PRU_CREG_RSVD20             
    abs   00000015  __PRU_CREG_RSVD21             
    abs   00000016  __PRU_CREG_PRU_RAT1           
    abs   00000017  __PRU_CREG_RSVD23             
    abs   00000018  __PRU_CREG_PRU1_DMEM_1        
    abs   00000019  __PRU_CREG_PRU1_DMEM_0        
    abs   0000001a  __PRU_CREG_PRU_IEP0           
    abs   0000001b  __PRU_CREG_RSVD27             
    abs   0000001c  __PRU_CREG_PRU_SHAREDMEM      
    abs   0000001d  __PRU_CREG_RSVD29             
    abs   0000001e  __PRU_CREG_RSVD30             
    abs   0000001f  __PRU_CREG_RSVD31             
    abs   00000100  __TI_STACK_SIZE               
    abs   00002000  __PRU_CREG_BASE_PRU1_DMEM_0   
    abs   00009000  __PRU_CREG_BASE_PRU_RAT1      
    abs   00010000  __PRU_CREG_BASE_PRU_SHAREDMEM 
    abs   00020000  __PRU_CREG_BASE_PRU_INTC      
    abs   00024000  __PRU_CREG_BASE_PRU1_CTRL     
    abs   00024800  __PRU_CREG_BASE_RSVD14        
    abs   00026000  __PRU_CREG_BASE_PRU_CFG       
    abs   00026100  __PRU_CREG_BASE_PRU_CFG_0x100 
    abs   00027000  __PRU_CREG_BASE_RSVD12        
    abs   00028000  __PRU_CREG_BASE_PRU_UART      
    abs   0002a000  __PRU_CREG_BASE_RSVD10        
    abs   0002c000  __PRU_CREG_BASE_RSVD13        
    abs   0002e000  __PRU_CREG_BASE_PRU_IEP0      
    abs   0002e100  __PRU_CREG_BASE_PRU_IEP0_0x100
    abs   0002f000  __PRU_CREG_BASE_PRU_IEP1      
    abs   0002f100  __PRU_CREG_BASE_PRU_IEP1_0x100
    abs   00030000  __PRU_CREG_BASE_PRU_ECAP      
    abs   00032000  __PRU_CREG_BASE_RSVD27        
    abs   00032400  __PRU_CREG_BASE_RSVD21        
    abs   00033000  __PRU_CREG_BASE_RSVD9         
    abs   60000000  __PRU_CREG_BASE_RSVD15        
    abs   70000000  __PRU_CREG_BASE_RSVD16        
    abs   80000000  __PRU_CREG_BASE_RSVD17        
    abs   90000000  __PRU_CREG_BASE_RSVD18        
    abs   a0000000  __PRU_CREG_BASE_RSVD19        
    abs   b0000000  __PRU_CREG_BASE_RSVD20        
    abs   c0000000  __PRU_CREG_BASE_RSVD23        
    abs   d0000000  __PRU_CREG_BASE_RSVD29        
    abs   e0000000  __PRU_CREG_BASE_RSVD30        
    abs   f0000000  __PRU_CREG_BASE_RSVD31        
    abs   ffffffff  __c_args__                    
    
    [83 symbols]
    

  • I found the error message here at the CCS files area

     

  • Here are a image into the memory map alocations and the linker.cmd file:

    Theres some information at the address mentioned on the error message.

    This address value is for stack size of 0x200. For the default 0x100 stack size, the address value is  0x000002F0@Data_Memory

  • Hello Rafael,

    I spent my time today working on porting the AM335x UART example to AM62x instead of looking at this thread. I am going to try to get that working first so you have a "known good" template to work off of, and then I'll circle back to this thread.

    Feel free to ping the thread if I haven't replied here within another couple of business days.

    Regards,

    Nick

  • Hello Rafael,

    Summary

    This loading error is coming up because RPMsg code was not designed to be loaded by CCS - it has to be loaded by the Linux remoteproc driver. If there is a non-empty resource table in your project, you want to load the code from Linux.

    For more information about resource tables, refer to
    https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_09/exports/docs/common/PRU-ICSS/Resource_Tables.html

    For more information about using Linux to initialize the PRU, refer to the PRU Getting Started Labs:
    https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_09/exports/docs/common/PRU-ICSS/PRU-Getting-Started-Labs_Lab4.html 

    But WHY does Linux need to load the firmware for an RPMsg project?

    Even if you got the code to load from CCS, the resource table information is filled in by Linux, not the PRU or CCS. And since Linux was not the one to initialize the PRU core, Linux has no way of knowing that a resource table exists somewhere, and needs to be initialized.

    That means that even if you got the code to load from CCS, your program will always stall out here, since Linux will never initialize the VIRTIO data structures used for RPMsg communication, and then update the resource table:

    https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/examples/am62x/PRU_RPMsg_Echo_Interrupt0/main.c

    	/* Make sure the Linux drivers are ready for RPMsg communication */
    	status = &resourceTable.rpmsg_vdev.status;
    	while (!(*status & VIRTIO_CONFIG_S_DRIVER_OK));

    Regards,

    Nick

  • Can you please tellme the name of drivers that i need to activate to make this communication between PRU and MPU?

  • Hello Rafael,

    Please refer to this RPMsg Quick Start Guide for PRU:
    https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_09/exports/docs/linux/Foundational_Components/PRU-ICSS/RPMsg_Quick_Start_Guide.html

    It has been a couple years since I tested the steps on that page, so if you find anything that no longer applies please let us know here on the forums so we can get the document updated.

    Regards,

    Nick

  • Hello! I will test the implementation of RPMSG tomorrow morning, during my work day.

    I was looking a little at the structure of the RPMsg project here and I came across some things that were not easy to understand for me, and I would like to ask if you can clarify some doubts. Thanks!

    The codeprojectn question is this: ( https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/examples/am62x/PRU_RPMsg_Echo_Interrupt0 )

    So, about the resource table, if I understand correctly, the kernel-level rpmsg driver will establish communication from it, right? In this case, the memory error at the beginning of the program in this thread was due to the CCS itself not recognizing the sections in the linker (resource_table and pru_intc) and the communication between the driver, meaning that, during the memory check, it did not let the firmware pass to the devkit, correct?

    The structure of intc_map.h is what intrigued me, as I am already partially familiar with the fact that this section:

    ON INTC_MAP.H:

    #pragma DATA_SECTION(my_irq_rsc, ".pru_irq_map")
    #pragma RETAIN(my_irq_rsc)
    
    struct pru_irq_rsc my_irq_rsc  = {
    	0,			/* type = 0 */
    	1,			/* number of system events being mapped */
    	{
    		{17, 0, 0},	/* {sysevt, channel, host interrupt} */
    	},
    };
    

    ON LINKER.CMD:

    .pru_irq_map (COPY) :
    	{
    		*(.pru_irq_map)
    	}

    EXAMPLE ON .DTSI:

    &client_driver0 {
        interrupt-parent = <&icssg0_intc>;
         interrupts = <21 2 2>, <22 3 3>;
        interrupt-names = "interrupt_name1", "interrupt_name2";
    };

    However, I still don't quite understand why a new section is necessarily allocated within the linker and why it needs to be inserted manually, and how this connection between int_map - kernel works through this session. Does it provide a parameterization table to match the two situations?

    Also, there, in the intc_map.h interrupt vector, there are three numbers, which. How do I find these parameters for my specific target? I mean, I have the example below:

    < 17, 0, 0 >

    But how could I find other interruptions? And, furthermore, is this vector correct for the application or is it generic? Sorry for all the doubts, but this is a concept that remained cloudy in my mind.

    Thanks,

    Rafael V. Volkmer

  • Hello Rafael,

    Topics I will not discuss

    I am not going to be able to comment on the specifics of how CCS loads binaries, and what about the structure of the resource table & interrupt controller (INTC) map are causing issues for it. It does not matter, because if you are using RPMsg, you need to load the PRU cores from Linux anyway.

    You also do not need to know the mechanics of how the linker.cmd file & .pru_irq_map works when the Linux remoteproc driver is initializing the PRU - It should just work for you as long as you use the template we show in the PSSP projects.

    Let's talk about the resource table and the INTC mapping

    The way the PRU remoteproc driver works with resource tables & the INTC mapping is unique. The developer wrote it so that both the resource table AND the INTC mapping are optional for PRU projects that are loaded by the Linux remoteproc driver. This is different from all other remote cores.

    RESOURCE TABLE
    For every other remote core, the resource table is MANDATORY if you want to initialize the remote core with the Linux remoteproc driver. So if you want to initialize the M4F core, there NEEDS to be a resource table in the project. (note that you do NOT need a resource table for M4F projects if you are 1) using SBL boot instead of SPL boot, 2) initializing the M4F core during SBL boot instead of later during Linux boot, and 3) you do NOT need RPMsg communication between Linux and the M4F).

    For more information about M4F getting initialized by Linux, refer to the AM62x academy, multicore module, page "Application development on Remote Cores"
    https://dev.ti.com/tirex/explore/node?node=A__AVn3JGT9fqm0PbS.pegO-g__AM62-ACADEMY__uiYMDcq__LATEST 

    INTC MAP
    No other remote core has an INTC map. You can also configure the INTC from your PRU firmware, so you do not actually need an INTC map file if you are not using RPMsg communication between Linux and the PRU core. For more information, refer to https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_09/exports/docs/common/PRU-ICSS/INTC_Configuration.html

    Understanding the INTC settings 

    Please refer to the comments in the intc_map_0.h file:
    https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/examples/am62x/PRU_RPMsg_Echo_Interrupt0/intc_map_0.h

    LINUX devicetree side:

    /*
     * ======== PRU INTC Map ========
     *
     * Define the INTC mapping for interrupts going to the ICSS / ICSSG:
     * 	ICSS Host interrupts 0, 1
     * 	ICSSG Host interrupts 0, 1, 10-19
     *
     * Note that INTC interrupts going to the ARM Linux host should not be defined
     * in this file (ICSS/ICSSG Host interrupts 2-9).
     *
     * The INTC configuration for interrupts going to the ARM host should be defined
     * in the device tree node of the client driver, "interrupts" property.
     * See Documentation/devicetree/bindings/interrupt-controller/ti,pruss-intc.yaml
     * entry #interrupt-cells for more.

    Please refer to the file and section I referenced in your ti-linux-kernel folder.

    PRU FIRMWARE side:

    		{17, 0, 0},	/* {sysevt, channel, host interrupt} */

    For the system event, channel, and host interrupt information, please refer to the AM62x TRM, PRU chapter.

    Regards,

    Nick

  • At the RPMsg quik start guide (3.6.2.9. RPMsg Quick Start Guide — Processor SDK AM62x Documentation), dont show the Linux SDK for my target. Can you help-me, please?

  • Hello Rafael,

    Just use the AM62x Linux SDK that you are already using:
    https://www.ti.com/tool/download/PROCESSOR-SDK-LINUX-AM62X

    Regards,

    Nick

  • Hi! Can you please tell me why i have to use the pru drivers as modules? And, how these modules works? We're trying to activate the drivers from our own directory. How should I include these modules? Through specific files? I'm on a demand to try to make the image run with the drivers in "y". Could you help me understand this question?

     3.6.2.9. RPMsg Quick Start Guide — Processor SDK AM62x Documentation

  • Hello Rafael,

    That specific line was actually written before I started working for TI, right after SDK 2.0 was released (about 8 years ago). I am not sure why they had to enable the PRU as modules back then.

    It does look like in the default kernel config, all remoteproc & rpmsg driver are modules by default instead of built-in:

    #
    # Remoteproc drivers
    #
    CONFIG_REMOTEPROC=y
    # CONFIG_REMOTEPROC_CDEV is not set
    CONFIG_PRU_REMOTEPROC=m
    CONFIG_TI_K3_DSP_REMOTEPROC=m
    CONFIG_TI_K3_M4_REMOTEPROC=m
    CONFIG_TI_K3_R5_REMOTEPROC=m
    # end of Remoteproc drivers
    
    #
    # Rpmsg drivers
    #
    CONFIG_RPMSG=y
    CONFIG_RPMSG_CHAR=m
    CONFIG_RPMSG_CTRL=m
    CONFIG_RPMSG_NS=m
    # CONFIG_RPMSG_QCOM_GLINK_RPM is not set
    CONFIG_RPMSG_VIRTIO=m
    CONFIG_RPMSG_PRU=m
    # end of Rpmsg drivers
    

    I'll check with the current developer to see if he knows anything about it. Feel free to ping the thread if I haven't replied back in a couple of days.

    Regards,

    Nick

  • Hi! I'm trying to use the base rpmsg example available in PSSP 6.3.0 (PRU_RPMsg_Echo_Interrupt0), but, however, I send a message to the driver and nothing happens, in addition, when I go to cat, my execution freezes.

    My Pru Firmware file:

    I passed this .out file to SCP for the devkit via the eth0.

    My kernel-menuconfig:

    My linux terminal before start the remoteproc:

    My linux terminal after start the remoteproc:

    When i make the echo:

  • Hello Rafael,

    From the developer: 

    Our general suggestion is to have the Remoteproc & RPMsg drivers as modules. The drivers should work, even if the drivers are kernel built in. We just typically suggest building as modules, because with built-in drivers the kernel image gets bloated. With modules, only the needed modules are loaded at boot/runtime. I am not aware of a separate PRU requirement.

    Responding to your latest post: 

    It actually looks like RPMsg is behaving exactly as expected.

    1) After initializing the PRU firmware, /dev/rpmsg_pru30 appears

    2) When you echo a message to /dev/rpmsg_pru30, if the PRU had NOT echoed the message back, you would not have seen anything with cat /dev/rpmsg_pru30. So the fact that you DO see something tells me that the PRU firmware is running as expected

    3) It is expected that cat /dev/rpmsg_pru30 command stops there. Did you try doing Ctrl-C to continue typing into the terminal?

    Regards,

    Nick

  • It looks like you are already testing drivers as built-in vs modules. Once you feel comfortable saying whether or not built-in driver is working for you, please let me know. I'll give myself a reminder to circle back and update the RPMsg getting started page, hopefully sometime in the second half of the year.

    Regards,

    Nick

  • So, I was able to use both the uart code I made with my HAL and rpmsg separately, finally. Now I would like to know if there is any more practical way to test rpmsg latency with the RU. Could you point me to any? And if there's a system for it in linux itself.

    So, as I said in the message above, I was able to run the code directly inside linux, activating the drivers as "*" and not "m". Thank you very much for your attention

  • Hello Rafael,

    Building in the remoteproc and RPMsg drivers

    Great, thank you for verifying. I have created an internal ticket with specific parts of the PRU RPMsg quick start guide to update.

    Testing RPMsg latency

    Are you trying to calculate one-way latency, or is round-trip latency sufficient?

    Round-trip latency is much easier to calculate. For example, let's say you want to measure round-trip latency from the PRU side. You can use the PRU's CYCLE_COUNT register to count how long it takes to receive a response from Linux:
    https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/include/am62x/pru_ctrl.h

    (related note, it looks like the AM62x TRM is missing the CTRL registers. I've filed a bug against the TRM, in the meantime refer to AM335x TRM similar to for the PRU UART registers)

    Then your pseudocode might look like this:

    clear CYCLE_COUNT register
    enable cycle count register
    send the RPMsg message to Linux
    poll for a response from Linux
    receive the RPMsg response from Linux
    stop the cycle count counter
    calculate the total PRU clock cycles
    
    // repeat for a LOOOONG time
    // when dealing with huge datasets, I will often save data as histograms instead of recording
    every single datapoint
    e.g., instead of recording every single 100 us time, I'll have a single entry for
    each time: 1us, 2us, 100us, etc
    and then each time I see a 100us delay, I'll increment the 100us entry by one
    so at the end you can see how many times you got each delay without having megabytes or gigabytes of data

    Regards,

    Nick

  • Hi!

    So, in my application, in short, it captures a large pile of data at a high frequency and sends it to the processor, all of this quickly, hence the use of the PRU.

    I need the latency from serial reception until it reaches the MPU. I've already checked around 1us to 10us of round trip latency on the serial through a logic analyzer via the tx/rx pins, operating at around 4Mhz. Now, I need to know the time elapsed between starting the transmission of the PRU until it definitively reaches the MPU, so that I can align it with a unilateral UART test and see what I should adjust in a matter of time for the best efficiency of the system.

  • Hello again, could you tell me how I do the step by step to load the symbols into my ccs and do a step by step debugging step there while running my code through linux? I had been told that it was something related to load symbols, but what exactly does this symbol expect to receive? What file extension generated during make?

  • Hello Rafael,

    Any updates on the Linux driver?

    Before we spend too much more time developing and testing the PRU firmware: Did you ever take a look at using the Linux PRU_UART driver from AM335x with AM62x? How did those tests go?

    I suspect that it will be simpler, faster, and more deterministic to go Linux <---> UART hardware instead of Linux <---> PRU <---> UART hardware. So I would probably spend a couple hours trying out that before investing a lot more development time into the PRU code.

    How to debug by loading symbols 

    Please make sure that you have the PRU project loaded in CCS, and that you built the output binary from CCS.

    Next, have Linux load the binary into the PRU cores.

    From CCS, connect to the running board. Refer to https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_09/exports/docs/common/PRU-ICSS/PRU-Getting-Started-Labs_Lab4.html#initializing-the-pru-from-ccs as needed.

    Right click on the PRU core, select Connect Target

    Load symbols by Run -> Load -> Load Symbols 

    Regards,

    Nick

  • Hello! I'm taking a look at the PRU UART direct driver for Linux now. I managed to finish the application, in c, loading my .out from Linux itself, and it worked perfectly with the final code, with a small HAL for the PRU and adaptation of the RPMsg functions. I only have one more question, which is in relation to cycle_count. I didn't find the register in the AM62xx reference manual, do you know where it could be?

    I wanted to see this because I didn't understand exactly how he would return. It increments a decimal numeric value every tick, like int i ++? And if so, approximately how long would a PRU tick last? 100us?

    Thank you for your attention this past month, really. I don't have that much experience and development yet and I came across a complicated problem for me in my first request at the company. The support of the Texas team was essential for the completion of this stage. Thank you very much for your patience answering my questions.

  • Hello Rafael,

    How does the cycle counter work? 

    A PRU clock cycle lasts exactly as long as you program it - for AM62x, you can choose 3ns, (333MHz, note that this is 333,333,333.333Hz so the period is 3ns instead of 3.03 ns), 4ns (250MHz), 5ns (200MHz), and potentially a couple other options depending on the PRU clocking.

    I don't think you'll need this information: but if you want to modify the clock frequency of the PRU cores, the basic concepts are documented here:
    https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1049800/faq-pru_icssg-how-to-check-and-set-pru-core-frequency-in-linux

    ^ I wrote that information for PRU_ICSSG devices, so while the concepts are the same for AM62x, the exact details will be different

    Every clock cycle that the cycle counter is enabled, it will increment by 1. So to measure time, you set the counter to 0, start the counter, and then stop the counter and check how many clock cycles have passed.

    How to program the cycle counter register? 

    Take another look at the links in my previous response: 

    https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1336314/am625-pru-memory-error/5160887#5160887 

    Remember how we used the UART header file to directly read and write to registers and bitfields in the PRU_Hardware_UART example?
    https://git.ti.com/cgit/pru-software-support-package/pru-software-support-package/tree/examples/am62x/PRU_Hardware_UART/PRU_Hardware_UART.c

    You would do the same thing here, but with 
    CT_CTRL.

    Regards,

    Nick