Hi,
I would like to transfer high data rates from PRU to my userspace C-program. Therefore I need a buffer which is larger than the 12kB of shared ram. I tried using cmicalis example which he mentioned here: https://groups.google.com/d/msg/beagleboard/iqo3csrF93E/tIzWhN0CB9QJ
My problem:
After writing something to the DDR by the PRU, it takes too long time until I can read out this value in my C-program. The time variies from nearly 0 up to 5s.
I set up a little example based on cmicalis code to show the problem. I basicly write a value from my C-program to the PRU dataram and measure how long it takes until the PRU has written this value to the DDR. The PRU is doing this in an endless loop, it should take only a few cycles.
This is the output of my example:
`
set: 0; data: 0; ddr: 0; time: 0ms
set: 1; data: 1; ddr: 1; time: 2167ms
set: 2; data: 2; ddr: 2; time: 0ms
set: 3; data: 3; ddr: 3; time: 0ms
set: 4; data: 4; ddr: 4; time: 439ms
set: 5; data: 5; ddr: 5; time: 425ms
set: 6; data: 6; ddr: 6; time: 546ms
set: 7; data: 7; ddr: 7; time: 0ms
`
As you can see, the time ist variing very much.
The important parts of my example are these:
`
while(info.pru_params->run_flag) {
timer = 0;
info.pru_params->counterIn = counter;
while(ddr[0] != counter) {
usleep(1000);
timer++;
}
printf(“set: %2u; data:%2u; ddr:%2u; time: %4ums\n”, counter, info.pru_params->counterOut, ddr[0], timer);
fflush(stdout);
counter++;
usleep(1000);
}
`
PRU:
`
MAIN_LOOP:
LBBO r0, ADDR_PRURAM, OFFSET(AppParams.CounterIn), 4 //load value
SBBO r0, ADDR_DDR, 0, 4 //write value to DDR
SBBO r0, ADDR_PRURAM, OFFSET(AppParams.CounterOut), 4 //write value to dataram
// Check to see if the host is still running
LBBO r0, ADDR_PRURAM, OFFSET(AppParams.RunFlag), 4
// If not, jump to exit
QBEQ EXIT, r0, 0
// Do the loop again
JMP MAIN_LOOP
`
The full programs can be found here: https://github.com/nils-z/am335x_pru_package/tree/master/pru_sw/example_apps/ddr_access_timing
If I check the time how long it takes to write to the dataram, it is always very short, as I expect it. The problem occurs only when using the DDR.
Has anyone an explanation for this behaviour? Perhaps it is a problem with some kind of cache, how could I get around this? I’d like to implement a ring buffer but it would have to be very large if it has to take data of several seconds.
Thanks, Nils