Weekly Progress Report Thread - PyPRUSS

Hello all. This is my progress report for WEEK 1. It has been quite a slow start for me. I fell ill last week and had to take two days off. I apologize to my mentors for not being active regarding the updates. I have completed most of the tasks planned for the week but I hope to be more active on the channel and provide daily updates on my work from now on.

Tasks Completed : (https://github.com/MuneebMohammed/pypruss)

  • Completed the remoteproc functions.

  • Completed the rpmsg functions.

  • Completed the PRU Memory access functions.

  • Tested the bindings using basic examples.
    Tasks planned for this week:

  • Complete the ddr memory functions.

  • Write C/C++ functions and use swig to generate pypruss-like bindings for other languages like nodejs, Go, etc.

  • Wrap up the work on remoteproc/rpmsg bindings to get started with the DMA project from next week.

Hello everyone. This is my progress report for WEEK 2.

Tasks Completed :

The project timeline is currently under review by the mentors. I will update the next week’s tasks as soon as it is finalized.

Note: The working repository for the project has been changed to https://github.com/MuneebMohammed/PRUSS-Bindings after merging the pypruss project with it.


Hello everyone. This is my progress report for WEEK 3. Been an eventful week.

Project Update: The PyPRUSS project as such is discontinued. Instead, the plan is to first write C++ bindings and use them to generate bindings (using swig) for other languages including python, among others.

Tasks completed during last week:

Hello everyone. This is my progress report for WEEK 4.

Tasks completed during last week:

Hello everyone. This is my progress report for WEEK 5. Could not put in sufficient hours this week (due to an annual festival - Eid). Will cover up the hours in the following week.

Tasks completed during last week:


Hello everyone. This is my progress report for WEEK 6. Last week was a really unproductive week. Couldn’t get much done as I was faced with multiple issues using DMA.

  1. I was working on transferring data to/from the PRU Data Memories with the EDMA controller configured as a slave using the DMA Engine API. I couldn’t get the transfers working. The dma channel is acquired and configured properly but the actual transfer doesn’t happen. The module which I was using was this - https://github.com/maciejjo/beaglebone-pru-dma/blob/master/wip/pru_dma_test/kmod/pru_dma_test.c and this was the dts I used.

Kernel log:

[    1.656951] edma 49000000.edma: TI EDMA DMA engine driver
[  543.116361] pru_dma_test: loading out-of-tree module taints kernel.
[  543.124268] pru_dma_test pru-dma-test: Start probe
[  543.124311] pru_dma_test pru-dma-test: Configure dma xfer
[  543.124355] pru_dma_test pru-dma-test: Map src buf
[  543.124373] pru_dma_test pru-dma-test: Perform transfer from 0x9a110590 to 0x4a300000
[  543.124391] pru_dma_test pru-dma-test: Submit xfer to pending queue
[  543.124402] pru_dma_test pru-dma-test: Issue pending transfer
[  548.143618] **edma 49000000.edma: dma_sync_wait: timeout!**
[  548.148935] pru_dma_test pru-dma-test: Probe complete

  1. The PRU DMA driver probe fails. After setting up the kernel with the DMA Driver patches and loading it, I get the following error on bootup -
[   27.109034] ti-pruss 4a300000.pruss: creating PRU cores and other child platform devices
[   27.109159] irq: no irq domain found for /ocp/pruss_soc_bus@4a326000/pruss@4a300000/intc@4a320000 !
[   27.192919] pru_dma 4a300000.pruss:pru_dma: **Unable to get PRUSS RAM.**
[   27.201309] remoteproc remoteproc1: 4a334000.pru0 is available
[   27.201427] pru-rproc 4a334000.pru0: PRU rproc node /ocp/pruss_soc_bus@4a326000/pruss@4a300000/pru@4a334000 probed successfully
[   27.202841] remoteproc remoteproc2: 4a338000.pru1 is available
[   27.202949] pru-rproc 4a338000.pru1: PRU rproc node /ocp/pruss_soc_bus@4a326000/pruss@4a300000/pru@4a338000 probed successfully
[   27.212016] pru_dma: **probe of 4a300000.pruss:pru_dma failed with error -16**

The DMA driver is an in-tree driver and it will be used by the patched pru_rproc driver during compilation (https://github.com/maciejjo/beaglebone-pru-dma/blob/be1b426c1ae9841e1cdc36ce294d6c10023f2049/kernel-patch/0001-Add-pru-dma-driver-to-Linux-tree.patch#L28)
It looks like the DMA driver is probed just before the remoteproc driver probe and it is unable to get the PRU memory regions.

I have worked on a kernel module to expose a sysfs interface for the DMA driver but couldn’t test it. I hope to resolve these issues and get on with the planned work as soon as possible.

Please provide suggestions/fixes for these issues if possible.


Hello everyone. This is my progress report for WEEK 7.

Last week it was decided to implement a version of LOG_printf() which will help debug PRU firmware code. The function will be on the PRU side and the end result should be that the kernel will print the formatted message to the kernel log. The advantage of this function will be that the string fomatting will be on the kernel side and PRU will be saved from this overhead. It was also suggested that the kernel should parse the ELF to get the strings and then the PRU will just pass the string by reference and also pass the runtime data.

Last week was mostly spent on discussing about the implementation of this function and there was no significant progress. I had to spent some time learning about the ELF format and thinking about the implementation of the function and couldn’t complete my goal. Once the implementation is finalised, I’ll update the report and get working on it with full speed.



For the string “optimization” you need to work with both the compiler and the linker. In GCC you should use the section attribute to tell the compiler to place a variable (array of chars in this case) into a non-default section:


#define print_rproc(STR)
do {
static const char __str[] attribute((section(".rproc_strings"))) = STR;
asm volatile ( “ldi32 r14, %[str_label]\n\t”
: [str_label] “i” ((int)__str)
: “r14”);
} while (0)


The inline assembly is what I would expect a simple “remoteproc print” implementation would look like. Load a constant integer address of the string into r14, and then halt the processor. You may extend the interface, e.g. load command ID into r14, string address into r15, printf arguments into r16-r28.

Then you have to inform linker where to place the new section. One method is to create a separate memory region for strings:


stringmem (r) : ORIGIN = 0x30000000, LENGTH = 8K



And then place there the sections created by compiler:



.rproc_strings (NOLOAD) : { *(.rproc_strings) } > stringmem


Your loader then could detect the new section by searching for non-executable flag and a base address 0x30000000.