Quantcast
Channel: Processors
Viewing all articles
Browse latest Browse all 123557

Forum Post: C6747 PRUSS Interrupts

$
0
0

Hi,

I've been trying to configure PRUSS Interrupts via timer Event. I used the "PRU_timer0interrupt" example from the SPRC940 Developement Package. Without modifying the code the interrupt runs successfully.

I want to configure an continious timer interrupt, so I had to modify some code lines. Additionally I added 3 code Lines in the Interrupt Routine to trigger some DSP GPIOs Outputs:

.origin 0
.entrypoint TIMER0INTERRUPT
#include "PRU_timer0Interrupt.hp"
//
// Macro definitions
//

TIMER0INTERRUPT:
    // Initialize pointer to INTC registers
    MOV32     regOffset, 0x00000000
    // Clear SYS_EVT
    MOV32     r31, 0x00000000
    
    // Global enable of all host interrupts
    LDI       regVal.w0, 0x0001
    SBCO      regVal, CONST_PRUSSINTC, GER_OFFSET, 2

    // Enable host interrupt 0
    MOV32     regVal, (0x00000000 | HOST_NUM)
    SBCO      regVal, CONST_PRUSSINTC, HIESR_OFFSET, 4

    // Map channel 0 to host 0
    LDI       regOffset.w0, INTC_HOSTMAP_REGS_OFFSET
    ADD       regOffset.w0, regOffset.w0, HOST_NUM
    LDI       regVal.w0, CHN_NUM
    SBCO      regVal, CONST_PRUSSINTC, regOffset.w0, 1

    // Map Timer 0 interrupt to channel 0
    LDI       regOffset.w0, INTC_CHNMAP_REGS_OFFSET
    ADD       regOffset, regOffset, SYS_EVT
    LDI       regVal.b0, CHN_NUM
    SBCO      regVal.b0, CONST_PRUSSINTC, regOffset.w0, 1

    // Set the polarity registers
    MOV32     regPointer, (INTC_REGS_BASE + INTC_SYS_INT_REGS_OFFSET)
    MOV32     regVal, 0xFFFFFFFF
    SBBO      regVal, regPointer, 0x00, 4
    SBBO      regVal, regPointer, 0x04, 4

    // Set the type registers
    MOV32     regVal, 0x1C000000
    SBBO      regVal, regPointer, 0x80, 4
    LDI       regVal.w2, #0x0000
    SBBO      regVal, regPointer, 0x84, 4

    // Make sure the Timer 0 system interrupt is cleared
    MOV32     regVal, (0x00000000 | SYS_EVT)
    SBCO      regVal, CONST_PRUSSINTC, SICR_OFFSET, 4

    // Enable Timer 0 system interrupt
    SBCO      regVal, CONST_PRUSSINTC, EISR_OFFSET, 4

CORE_LOOP:
    // Poll for receipt of interrupt on host 0
    QBBS      EVENT_HANDLER, eventStatus, #30
    JMP       CORE_LOOP

EVENT_HANDLER:
    // Initialize pointer to priority index register location in the INTC
    LDI       regOffset.w0, INTC_HOSTINTPRIO_REGS_OFFSET

    // Retrieve interrupt number from the INTC registers
    LBCO      jumpOffset, CONST_PRUSSINTC, regOffset.w0, 4
    AND       jumpOffset.b0, jumpOffset.b0, PT_MASK

    // Jump to the timer interrupt ISR
    QBEQ      TIMER64P0_EVENTOUT12, jumpOffset.b0, 3
    JMP       CORE_LOOP                                                                                 (original:   JMP       DONE)

TIMER64P0_EVENTOUT12:
    // Clear the status of the timer interrupt
    MOV32     regVal, (0x00000000 | SYS_EVT)
    SBCO      regVal, CONST_PRUSSINTC, SICR_OFFSET, 4
    SBBO    r5, r10, 0, 4                                                                                   (added Code Lines which triggers GPIO Pins)
    XOR    r5, r6, r5
    XOR     r6, r7, r6
   JMP       CORE_LOOP                                                                                 (original: nothing)

DONE:
    MOV32     regVal, 0x00000000
    SBCO      regVal, CONST_PRUDRAM, 0x00, 4
    HALT
So I only modifier 2 lines that let the code jump back to the poll for receipt interrupts.
The timer is set up that he generates 12 kHz interrupts. So the GPIO Pins should be triggered with the same Frequency. But they are triggered with nearly 3MHz. So it seems like the PRUSS jumps every time into the interrupt routine. But the Interrupt Status is cleared every time in the "SICR" register. So I don't really understand why the Interrupts occur every time.
I tried to program the PRUSS manually with the help of the wiki article: processors.wiki.ti.com/index.php/PRU_Interrupt_Controller
There the interrupt checking is described a little different than it is coded in the example of the developement package.
In the wiki article the interrupt checking and clearing should be done via the "SECR" register.
So I wrote my one code (yellow lines):

.origin 0
.entrypoint TIMER0INTERRUPT
#include "PRU_timer0Interrupt.hp"
//
// Macro definitions
//

TIMER0INTERRUPT:
    // Initialize pointer to INTC registers
    MOV32     regOffset, 0x00000000
    // Clear SYS_EVT
    MOV32     r31, 0x00000000
    
    // Global enable of all host interrupts
    LDI       regVal.w0, 0x0001
    SBCO      regVal, CONST_PRUSSINTC, GER_OFFSET, 2

    // Enable host interrupt 0
    MOV32     regVal, (0x00000000 | HOST_NUM)
    SBCO      regVal, CONST_PRUSSINTC, HIESR_OFFSET, 4

    // Map channel 0 to host 0
    LDI       regOffset.w0, INTC_HOSTMAP_REGS_OFFSET
    ADD       regOffset.w0, regOffset.w0, HOST_NUM
    LDI       regVal.w0, CHN_NUM
    SBCO      regVal, CONST_PRUSSINTC, regOffset.w0, 1

    // Map Timer 0 interrupt to channel 0
    LDI       regOffset.w0, INTC_CHNMAP_REGS_OFFSET
    ADD       regOffset, regOffset, SYS_EVT
    LDI       regVal.b0, CHN_NUM
    SBCO      regVal.b0, CONST_PRUSSINTC, regOffset.w0, 1

    // Set the polarity registers
    MOV32     regPointer, (INTC_REGS_BASE + INTC_SYS_INT_REGS_OFFSET)
    MOV32     regVal, 0xFFFFFFFF
    SBBO      regVal, regPointer, 0x00, 4
    SBBO      regVal, regPointer, 0x04, 4

    // Set the type registers
    MOV32     regVal, 0x1C000000
    SBBO      regVal, regPointer, 0x80, 4
    LDI       regVal.w2, #0x0000
    SBBO      regVal, regPointer, 0x84, 4

    // Make sure the Timer 0 system interrupt is cleared
    MOV32     regVal, (0x00000000 | SYS_EVT)
    SBCO      regVal, CONST_PRUSSINTC, SICR_OFFSET, 4

    // Enable Timer 0 system interrupt
    SBCO      regVal, CONST_PRUSSINTC, EISR_OFFSET, 4

CORE_LOOP:
MOV32    regOffset, SECR1_OFFSET                                         
LBCO     r4, CONST_PRUSSINTC, regOffset, 4                               // Load Status from SECR1 Register
QBBS      EVENT_HANDLER, r4, 3                                                     // If bit 3 is set -> jump to interrupt routine
JMP           CORE_LOOP

EVENT_HANDLER:
 // Clear the status of the timer interrupt
MOV32     regVal, 0x00000008                                                           
SBCO       regVal, CONST_PRUSSINTC, regOffset, 4                    // by writing 1 at bit 3 the timer interrupt status is deleted
SBBO       r5, r10, 0, 4
XOR          r5, r6, r5
XOR          r6, r7, r6
JMP           CORE_LOOP
But unfortunatelly the result is the same. The GPIOs are triggered with every loop.



Viewing all articles
Browse latest Browse all 123557

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>