Beaglebone 4.4.27-ti-r63 and uio_pruss; program ran in 3.8 not running in 4.4 pru, help appreciated

Hi All :slight_smile:

I have a program which ran with Beaglebone black, 3.8; I am updating the system to Beaglebone 4.4.27-ti-r63 and getting segmentation fault.
Seems like the overlay is not loading, even when loaded manually.

If you have a working configuration for Beaglebone 4.4.x and uio_pruss please also post, as any help would be greatly appreciated

On fresh reboot
lsmod | grep uio
uio_pdrv_genirq 3923 0
uio 10524 1 uio_pdrv_genirq

echo ‘EBB-PRU-MIC’ > /sys/devices/platform/bone_capemgr/slots
-bash: echo: write error: File exists

modprobe uio_pruss

lsmod | grep uio
uio_pruss 5504 0
uio_pdrv_genirq 3923 0
uio 10524 2 uio_pruss,uio_pdrv_genirq

compiled program is Segmentation fault

So issues seem to be;

  1. cannot load my overlay "EBB-PRU-MIC"
  2. PRU seems to be running
  3. Other ?

If you have any ideas please let me know, as I am kinda lost where to go. Attached source code.

Much Appreciated
MB

→ EBB-PRU-MIC-00A0.dts
/* Device Tree Overlay for enabling the pins that are used in the Chapter 25

  • directory for copyright and GNU GPLv3 license information.
    */
    /dts-v1/;
    /plugin/;

/ {
compatible = “ti,beaglebone”, “ti,beaglebone-black”;

part-number = “EBB-PRU-MIC”;
version = “00A0”;

/* This overlay uses the following resources */
exclusive-use =
“P8.46”, “P8.45” , “pru1”;

fragment@0 {
target = <&am33xx_pinmux>;
overlay {

pru_pru_pins: pinmux_pru_pru_pins { // The PRU pin modes
pinctrl-single,pins = <
// See Table 6-7, no pull up/down resistors enabled
// This is for PRU1, the sample clock – debug only
0x0a4 0x36 // SAMP P8_46 pr1_pru1_pru_r31_1, MODE5 | INPUT | PULL UP
0x0a0 0x36 // SAMP P8_46 pr1_pru1_pru_r31_0, MODE5 | INPUT | PULL UP

;
};
};
};

fragment@1 { // Enable the PRUSS
target = <&pruss>;
overlay {
status = “okay”;
pinctrl-names = “default”;
pinctrl-0 = <&pru_pru_pins>;
};
};

};

→ timedelay.p compiled with pasm -b timedelay.p ; chmod +x timedelay.bin
// This is a nearly-minimal PRU program. It delays for five seconds, then
// notifies the host that it has completed, then halts the PRU.
//
// The idea is to have a program that does something you can see from user
// space, without doing anything complicated like playing with IO pins,
// DDR or shared memory.
//
// Try adjusting the DELAYCOUNT value and re-running the test; you should
// be able to convince yourself that the program is actually doing something.

.origin 0 // offset of the start of the code in PRU memory
.entrypoint START // program entry point, used by debugger only

// To signal the host that we’re done, we set bit 5 in our R31
// simultaneously with putting the number of the signal we want
// into R31 bits 0-3. See 5.2.2.2 in AM335x PRU-ICSS Reference Guide.

#define PRU0_R31_VEC_VALID 32;
#define PRU_EVTOUT_0 3
#define PRU_EVTOUT_1 4
#define PRU1_ARM_INTERRUPT 20

#define DELAY_SECONDS 2 // adjust this to experiment
#define CLOCK 200000000 // PRU is always clocked at 200MHz
#define CLOCKS_PER_LOOP 2 // loop contains two instructions, one clock each
#define DELAYCOUNT DELAY_SECONDS * CLOCK / CLOCKS_PER_LOOP

START:

// initialize loop counter
MOV r1, DELAYCOUNT
// wait for specified period of time
DELAY:
SUB r1, r1, 1 // decrement loop counter
QBNE DELAY, r1, 0 // repeat loop unless zero
// tell host we’re done
mov r31.b0, PRU1_ARM_INTERRUPT+16

MOV r1, DELAYCOUNT
// wait for specified period of time
DELAY2:
SUB r1, r1, 1 // decrement loop counter
QBNE DELAY2, r1, 0 // repeat loop unless zero
// tell host we’re done
mov r31.b0, PRU1_ARM_INTERRUPT+16

// initialize loop counter
MOV r1, DELAYCOUNT
// wait for specified period of time
DELAY1:
SUB r1, r1, 1 // decrement loop counter
QBNE DELAY1, r1, 0 // repeat loop unless zero

// tell host we’re done, then halt
mov r31.b0, PRU1_ARM_INTERRUPT+16 //int1
mov r31.b0, PRU1_ARM_INTERRUPT+15 //int0

HALT

–>main c ; program meant to flash on board LED’s
//********
#include <stdio.h>
#include <stdlib.h>
#include <prussdrv.h>
#include <pruss_intc_mapping.h>
#include <pthread.h>
#include <unistd.h>

#include
#include
#include

using namespace std;

#define LED0_PATH “/sys/class/leds/beaglebone:green:usr0”
#define LED1_PATH “/sys/class/leds/beaglebone:green:usr1”
#define LED2_PATH “/sys/class/leds/beaglebone:green:usr2”
#define LED3_PATH “/sys/class/leds/beaglebone:green:usr3”

#define PRU_NUM 1

static void *PRU1DataMemory;
static unsigned int *PRU1DataMemory_int;

void removeTrigger(){
// remove the trigger from the LED
std::fstream fs;
fs.open( LED0_PATH “/trigger”, std::fstream::out);
fs << “none”;
fs.close();
fs.open (LED0_PATH “/brightness”, std::fstream::out);
fs << “0”;
fs.close();

fs.open( LED1_PATH “/trigger”, std::fstream::out);
fs << “none”;
fs.close();
fs.open (LED1_PATH “/brightness”, std::fstream::out);
fs << “0”;
fs.close();

fs.open( LED2_PATH “/trigger”, std::fstream::out);
fs << “none”;
fs.close();
fs.open (LED2_PATH “/brightness”, std::fstream::out);
fs << “0”;
fs.close();

fs.open( LED3_PATH “/trigger”, std::fstream::out);
fs << “none”;
fs.close();
fs.open (LED3_PATH “/brightness”, std::fstream::out);
fs << “0”;
fs.close();
}

void *threadFunction(void *value){
do {
std::fstream fs1;
int notimes = prussdrv_pru_wait_event (PRU_EVTOUT_1);
cout << "PRU event 1 " << notimes << endl << flush ;

fs1.open (LED1_PATH “/brightness”, std::fstream::out);
fs1 << “1”;
fs1.close();

sleep(3);
prussdrv_pru_clear_event (PRU_EVTOUT_1, PRU1_ARM_INTERRUPT);
} while (1);
}

int main (void)
{
if(getuid()!=0){
printf(“You must run this program as root. Exiting.\n”);
exit(EXIT_FAILURE);
}
pthread_t thread;
tpruss_intc_initdata pruss_intc_initdata = PRUSS_INTC_INITDATA;

std::fstream fs;

removeTrigger();
cout << “All LED’s off for 3 second” << endl;
sleep(3); //1 sec delay all LEDS off

// select whether it is on, off or flash
fs.open (LED0_PATH “/brightness”, std::fstream::out);
fs << “1”;
fs.close();

// Allocate and initialize memory
prussdrv_init ();
prussdrv_open (PRU_EVTOUT_0);
prussdrv_open (PRU_EVTOUT_1);

// Map PRU’s INTC
prussdrv_pruintc_init(&pruss_intc_initdata);

// Copy data to PRU memory - different way
prussdrv_map_prumem(PRUSS0_PRU1_DATARAM, &PRU1DataMemory);
PRU1DataMemory_int = (unsigned int *) PRU1DataMemory;
// Use the first 4 bytes for the number of samples
*PRU1DataMemory_int = 500;
// Use the second 4 bytes for the sample delay in ms
*(PRU1DataMemory_int+1) = 100; // 2 milli seconds between samples

// Load and execute binary on PRU
prussdrv_exec_program (PRU_NUM, “./timedelay.bin”);

fs.open (LED2_PATH “/brightness”, std::fstream::out);
fs << “1”;
fs.close();

if(pthread_create(&thread, NULL, &threadFunction, NULL)){
printf(“Failed to create thread!”);
}
int n = prussdrv_pru_wait_event (PRU_EVTOUT_0);
printf(“PRU program completed, event number %d.\n”, n);

// distance in inches = time (ms) / 148 according to datasheet
/* Disable PRU and close memory mappings */
prussdrv_pru_disable(PRU_NUM);
prussdrv_exit ();
fs.open (LED3_PATH “/brightness”, std::fstream::out);
fs << “1”;
fs.close();

return EXIT_SUCCESS;
}

The issue was eclipse; during the upgrade to windows 10 all the paths got lost and … big head ache; got to work on “old” 3.8 bone 70 version example is running fine; will try 4.4 next couple of days

part of solution was to compile on the BB, hope helps someone in future