This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

LPC2378 ISR Problem

Hello Everybody. I tried since days to make my program jumping to ISR. But i still stuck with this problem. I think i already did the right programm and the right start-up file after searching in Internet. At the moment i don't know anymore what to do.

I want that my program jumps to ISR, if a rising edge or a falling edge occurs on my capture port.

I could watch the timer counter and the timer interrupt flag in the debugger but it doesn't jump to ISR. The Flag of my I_BIT is 0 in the beginning.[CPSR = 0x6000005F].So IRQ is enable!! When i give a rising edge signal on my capture-ports, the CPSR Register still contains: CPSR = 0x6000005F.

Sorry for my bad english and Thank you for any helps :-) The Main Programm is in the next message.

My Start-Up:


/* Stack Sizes */
.set  UND_STACK_SIZE, 0x00000004                /* stack for "undefined instruction" interrupts is 4 bytes  */
.set  ABT_STACK_SIZE, 0x00000004                /* stack for "abort" interrupts is 4 bytes                  */
.set  FIQ_STACK_SIZE, 0x00000004                /* stack for "FIQ" interrupts  is 4 bytes                             */
.set  IRQ_STACK_SIZE, 0X00000004                /* stack for "IRQ" normal interrupts is 4 bytes                       */
.set  SVC_STACK_SIZE, 0x00000004                /* stack for "SVC" supervisor mode is 4 bytes                                 */



/* Standard definitions of Mode bits and Interrupt (I & F) flags in PSRs (program status registers) */
.set  MODE_USR, 0x10                            /* Normal User Mode                                                                             */
.set  MODE_FIQ, 0x11                            /* FIQ Processing Fast Interrupts Mode                                          */
.set  MODE_IRQ, 0x12                            /* IRQ Processing Standard Interrupts Mode                                      */
.set  MODE_SVC, 0x13                            /* Supervisor Processing Software Interrupts Mode                       */
.set  MODE_ABT, 0x17                            /* Abort Processing memory Faults Mode                                          */
.set  MODE_UND, 0x1B                            /* Undefined Processing Undefined Instructions Mode             */
.set  MODE_SYS, 0x1F                            /* System Running Priviledged Operating System Tasks  Mode      */

.set  I_BIT, 0x80                               /* when I bit is set, IRQ is disabled (program status registers) */
.set  F_BIT, 0x40                               /* when F bit is set, FIQ is disabled (program status registers) */


.text
.arm

.global Reset_Handler
.global _startup
.func   _startup

_startup:

# Exception Vectors

_vectors:       ldr     PC, Reset_Addr
                ldr     PC, Undef_Addr
                ldr     PC, SWI_Addr
                ldr     PC, PAbt_Addr
                ldr     PC, DAbt_Addr
                nop                                                     /* Reserved Vector (holds Philips ISP checksum) */
                ldr     PC, [PC,#-0x120]        /* see page 71 of "Insiders Guide to the Philips ARM7-Based Microcontrollers" by Trevor Martin  */
                ldr     PC, FIQ_Addr

Reset_Addr:     .word   Reset_Handler           /* defined in this module below  */
Undef_Addr:     .word   UNDEF_Routine           /* defined in main.c  */
SWI_Addr:       .word   SWI_Routine                     /* defined in main.c  */
PAbt_Addr:      .word   UNDEF_Routine           /* defined in main.c  */
DAbt_Addr:      .word   UNDEF_Routine           /* defined in main.c  */
IRQ_Addr:       .word   IRQ_Routine                     /* defined in main.c  */
FIQ_Addr:       .word   FIQ_Routine                     /* defined in main.c  */
                .word   0                                       /* rounds the vectors and ISR addresses to 64 bytes total  */


# Reset Handler

Reset_Handler:

                                /* Setup a stack for each mode - note that this only sets up a usable stack
                                for User mode.   Also each mode is setup with interrupts initially disabled. */

                        ldr   r0, =_stack_end
                        msr   CPSR_c, #MODE_UND|I_BIT|F_BIT     /* Undefined Instruction Mode  */
                        mov   sp, r0
                        sub   r0, r0, #UND_STACK_SIZE
                        msr   CPSR_c, #MODE_ABT|I_BIT|F_BIT     /* Abort Mode */
                        mov   sp, r0
                        sub   r0, r0, #ABT_STACK_SIZE
                        msr   CPSR_c, #MODE_FIQ|I_BIT|F_BIT     /* FIQ Mode */
                        mov   sp, r0
                                sub   r0, r0, #FIQ_STACK_SIZE
                        msr   CPSR_c, #MODE_IRQ|I_BIT|F_BIT     /* IRQ Mode */
                        mov   sp, r0
                        sub   r0, r0, #IRQ_STACK_SIZE
                        msr   CPSR_c, #MODE_SVC|I_BIT|F_BIT     /* Supervisor Mode */
                        mov   sp, r0
                        sub   r0, r0, #SVC_STACK_SIZE
                        msr   CPSR_c, #MODE_SYS|I_BIT|F_BIT     /* User Mode */
                        mov   sp, r0

                                /* copy .data section (Copy from ROM to RAM) */
                ldr     R1, =_etext
                ldr     R2, =_data
                ldr     R3, =_edata
1:                      cmp     R2, R3
                ldrlo   R0, [R1], #4
                strlo   R0, [R2], #4
                blo     1b

                                /* Clear .bss section (Zero init)  */
                mov     R0, #0
                ldr     R1, =_bss_start
                ldr     R2, =_bss_end
2:                              cmp     R1, R2
                strlo   R0, [R1], #4
                blo     2b

                                /* Enter the C code  */
                b       main

.endfunc
.end

.

Parents
  • My Main Program:

    .
    void Initialize(void);
    void feed(void);
    
    void IRQ_Routine (void)   __attribute__ ((interrupt("IRQ")));
    void FIQ_Routine (void)   __attribute__ ((interrupt("FIQ")));
    void SWI_Routine (void)   __attribute__ ((interrupt("SWI")));
    void UNDEF_Routine (void) __attribute__ ((interrupt("UNDEF")));
    unsigned enableIRQ(void);
    unsigned disableIRQ(void);
    #define IRQ_MASK 0x00000080
    #include "LPC2378.h"
    
    int     main (void) {
    
            int             i;                                                                              // loop counter (stack variable)
    
            InitMAM();
    
            //InitClock();
    
            SCS |= 0x01;
    
            // Initialize the system
            Initialize();
    
            // LPC-P2378
    
            FIO0DIR |= 1<<21; // P0.21 - power up the SD/MMC
            FIO0CLR |= 1<<21; // off
            PINSEL3 = 0x00300000;
            TIMER0_IR = 0xff;                                                                       /* Reset all interrupts */
            TIMER0_TCR = 0x02;
            TIMER0_CCR = 0x0007;
    
            VICVectAddr4 = (unsigned)IRQ_Routine;                   /* Set interrupt vector in 0 */
            VICVectPriority4 = 0x0000000004;                                /* Use it for Timer 0 Interrupt */
            VICIntEnable = 0x00000010;                                              /* Enable Timer0 interrupt */
            TIMER0_TCR = 0x01;                                                                      /* Start timer */
            enableIRQ();
    
    
                    /* Start timer */
    
            // endless loop to toggle the two leds
            while (1)
                    {
                            i=1;
    
                    }
    }
    
    
    
    
    /*  Stubs for various interrupts (may be replaced later)  */
    /*  ----------------------------------------------------  */
    
    void IRQ_Routine (void)
    {
            int x;
            x= T0CRO;
            T0IR = 0x00000001;                                              /* Reset interrupt */
            VICAddress = 0x00000000;
    }
    
    
    
    void FIQ_Routine (void)  {
            while (1) ;
    }
    
    
    void SWI_Routine (void)  {
            while (1) ;
    }
    
    
    void UNDEF_Routine (void) {
            while (1) ;
    }
    
    
    
    
    static inline unsigned asm_get_cpsr(void)
    {
      unsigned long retval;
      asm volatile (" mrs  %0, cpsr" : "=r" (retval) : /* no inputs */  );
      return retval;
    }
    
    static inline void asm_set_cpsr(unsigned val)
    {
      asm volatile (" msr  cpsr, %0" : /* no outputs */ : "r" (val)  );
    }
    
    unsigned enableIRQ(void)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr(_cpsr & ~IRQ_MASK);
      return _cpsr;
    }
    
    unsigned disableIRQ(void)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr(_cpsr | IRQ_MASK);
      return _cpsr;
    }
    
    unsigned restoreIRQ(unsigned oldCPSR)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr((_cpsr & ~IRQ_MASK) | (oldCPSR & IRQ_MASK));
      return _cpsr;
    }
    
    

    .

Reply
  • My Main Program:

    .
    void Initialize(void);
    void feed(void);
    
    void IRQ_Routine (void)   __attribute__ ((interrupt("IRQ")));
    void FIQ_Routine (void)   __attribute__ ((interrupt("FIQ")));
    void SWI_Routine (void)   __attribute__ ((interrupt("SWI")));
    void UNDEF_Routine (void) __attribute__ ((interrupt("UNDEF")));
    unsigned enableIRQ(void);
    unsigned disableIRQ(void);
    #define IRQ_MASK 0x00000080
    #include "LPC2378.h"
    
    int     main (void) {
    
            int             i;                                                                              // loop counter (stack variable)
    
            InitMAM();
    
            //InitClock();
    
            SCS |= 0x01;
    
            // Initialize the system
            Initialize();
    
            // LPC-P2378
    
            FIO0DIR |= 1<<21; // P0.21 - power up the SD/MMC
            FIO0CLR |= 1<<21; // off
            PINSEL3 = 0x00300000;
            TIMER0_IR = 0xff;                                                                       /* Reset all interrupts */
            TIMER0_TCR = 0x02;
            TIMER0_CCR = 0x0007;
    
            VICVectAddr4 = (unsigned)IRQ_Routine;                   /* Set interrupt vector in 0 */
            VICVectPriority4 = 0x0000000004;                                /* Use it for Timer 0 Interrupt */
            VICIntEnable = 0x00000010;                                              /* Enable Timer0 interrupt */
            TIMER0_TCR = 0x01;                                                                      /* Start timer */
            enableIRQ();
    
    
                    /* Start timer */
    
            // endless loop to toggle the two leds
            while (1)
                    {
                            i=1;
    
                    }
    }
    
    
    
    
    /*  Stubs for various interrupts (may be replaced later)  */
    /*  ----------------------------------------------------  */
    
    void IRQ_Routine (void)
    {
            int x;
            x= T0CRO;
            T0IR = 0x00000001;                                              /* Reset interrupt */
            VICAddress = 0x00000000;
    }
    
    
    
    void FIQ_Routine (void)  {
            while (1) ;
    }
    
    
    void SWI_Routine (void)  {
            while (1) ;
    }
    
    
    void UNDEF_Routine (void) {
            while (1) ;
    }
    
    
    
    
    static inline unsigned asm_get_cpsr(void)
    {
      unsigned long retval;
      asm volatile (" mrs  %0, cpsr" : "=r" (retval) : /* no inputs */  );
      return retval;
    }
    
    static inline void asm_set_cpsr(unsigned val)
    {
      asm volatile (" msr  cpsr, %0" : /* no outputs */ : "r" (val)  );
    }
    
    unsigned enableIRQ(void)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr(_cpsr & ~IRQ_MASK);
      return _cpsr;
    }
    
    unsigned disableIRQ(void)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr(_cpsr | IRQ_MASK);
      return _cpsr;
    }
    
    unsigned restoreIRQ(unsigned oldCPSR)
    {
      unsigned _cpsr;
    
      _cpsr = asm_get_cpsr();
      asm_set_cpsr((_cpsr & ~IRQ_MASK) | (oldCPSR & IRQ_MASK));
      return _cpsr;
    }
    
    

    .

Children
  • Forget about changes to the startup file. Use the default one you can add to your project when you start a new one.
    You need to read the user manual of the processor and connect the ISR to an pin that can function as an external interrupt source. You have not done so as far as I can see. Usually there are predefined pins - again, checkout your user manual.

  • This code applies to the LPC2478:

    // init GPIO 2.30 interrupt for quick power failure handling
    
    IO2_INT_EN_F |= (1<<30) ;
    
    if (install_irq(EINT3_INT, (void *)gpio_handler, IRQ_HIGHEST_PRIORITY) == 0)
    {
         gp_software_event(e_critical, ERR_FAILED_TO_INSTALL_ISR, __current_pc(), EINT3_INT ) ;
    }
    

    and then

    __irq void gpio_handler(void)
    {
        if ( (IO2_INT_STAT_F >> 30) & 1) // has a power failure occurred?
        {
            // power failure detected
    
            ...
        }
    
        // acknowledge interrupt
        VICVectAddr = 0 ;
        IO2_INT_CLR = (1<<30) ;
    }