EmbeddedRelated.com
Forums

external interrupt edge sensitive don't work

Started by Unknown March 17, 2005
Hello ,

I use an LPC2210 and I would use two external interrupt in edge sensitive but it doesn't work.

My hardware is : the same signal is connect to P0.15(EINT2) in falling edge sensitive , and P0.16(EINT0) in rising edge sensitive.

My code is :

#define REG(addr) (*(volatile _uint32 *)(addr))
#define REGSetBit(addr, mask) (*(volatile _uint32 *)(addr) |= mask)
#define REGClrBit(addr, mask) (*(volatile _uint32 *)(addr) &= (~mask))

void EINT0Interrupt(void) __attribute__ ((interrupt));
void EINT1Interrupt(void) __attribute__ ((interrupt));
void EINT2Interrupt(void) __attribute__ ((interrupt));
void EINT3Interrupt(void) __attribute__ ((interrupt));

void InterruptEnable(_uint8 IntChannel)
{
REG(VICIntEnable) = (1 << IntChannel);
} void InitIntVectors(void)
{
REG(VICIntSelect) = 0; // set all interrupts as IRQs
REG(VICDefVectAddr) = (_uint32)DefaultInterrupt; // set ISR for non-vectored IRQs
// Init Watchdog Interrupt Function
REG(VICVectAddr0) = (_uint32)WatchdogInterrupt; // set interrupt vector in 0
REG(VICVectCntl0) = VICIrqChWDT | VICVectEnable; // use it for Watchdog Interrupt
// Init Timer0 Interrupt Function
REG(VICVectAddr1) = (_uint32)Timer0Interrupt; // set interrupt vector in 1
REG(VICVectCntl1) = VICIrqChTimer0 | VICVectEnable; // use it for Timer 0 Interrupt
// Init Timer1 Interrupt Function
REG(VICVectAddr2) = (_uint32)Timer1Interrupt; // set interrupt vector in 2
REG(VICVectCntl2) = VICIrqChTimer1 | VICVectEnable; // use it for Timer 1 Interrupt
// Init Uart0 Interrupt Function
REG(VICVectAddr3) = (_uint32)Uart0Interrupt; // set interrupt vector in 3
REG(VICVectCntl3) = VICIrqChUart0 | VICVectEnable; // use it for Uart 0 Interrupt
// Init Uart1 Interrupt Function
REG(VICVectAddr4) = (_uint32)Uart1Interrupt; // set interrupt vector in 4
REG(VICVectCntl4) = VICIrqChUart1 | VICVectEnable; // use it for Uart 1 Interrupt
// Init PWM0 Interrupt Function
REG(VICVectAddr5) = (_uint32)PWM0Interrupt; // set interrupt vector in 5
REG(VICVectCntl5) = VICIrqChPWM0 | VICVectEnable; // use it for PWM0 Interrupt
// Init I2C Interrupt Function
REG(VICVectAddr6) = (_uint32)I2CInterrupt; // set interrupt vector in 6
REG(VICVectCntl6) = VICIrqChI2C | VICVectEnable; // use it for I2C Interrupt
// Init SPI0 Interrupt Function
REG(VICVectAddr7) = (_uint32)SPI0Interrupt; // set interrupt vector in 7
REG(VICVectCntl7) = VICIrqChSPI0 | VICVectEnable; // use it for SPI0 Interrupt
// Init SPI1 Interrupt Function
REG(VICVectAddr8) = (_uint32)SPI1Interrupt; // set interrupt vector in 8
REG(VICVectCntl8) = VICIrqChSPI1 | VICVectEnable; // use it for SPI1 Interrupt
// Init PLL Interrupt Function
REG(VICVectAddr9) = (_uint32)PLLInterrupt; // set interrupt vector in 9
REG(VICVectCntl9) = VICIrqChPLL | VICVectEnable; // use it for PLL Interrupt
// Init RTC Interrupt Function
REG(VICVectAddr10) = (_uint32)RTCInterrupt; // set interrupt vector in 10
REG(VICVectCntl10) = VICIrqChRTC | VICVectEnable; // use it for RTC Interrupt
// Init EINT0 Interrupt Function
REG(VICVectAddr11) = (_uint32)EINT0Interrupt; // set interrupt vector in 11
REG(VICVectCntl11) = VICIrqChEINT0 | VICVectEnable; // use it for EINT0 Interrupt
// Init EINT1 Interrupt Function
REG(VICVectAddr12) = (_uint32)EINT1Interrupt; // set interrupt vector in 12
REG(VICVectCntl12) = VICIrqChEINT1 | VICVectEnable; // use it for EINT1 Interrupt
// Init EINT2 Interrupt Function
REG(VICVectAddr13) = (_uint32)EINT2Interrupt; // set interrupt vector in 13
REG(VICVectCntl13) = VICIrqChEINT2 | VICVectEnable; // use it for EINT2 Interrupt
// Init EINT3 Interrupt Function
REG(VICVectAddr14) = (_uint32)EINT3Interrupt; // set interrupt vector in 14
REG(VICVectCntl14) = VICIrqChEINT3 | VICVectEnable; // use it for EINT3 Interrupt
// Init AD Interrupt Function
REG(VICVectAddr15) = (_uint32)ADInterrupt; // set interrupt vector in 15
REG(VICVectCntl15) = VICIrqChAD | VICVectEnable; // use it for AD Interrupt
} void EINT0Interrupt(void)
{
_uint8 i;
dLed.f->Set(LEDGREEN);
for(i=0;i<10;i++){};
dLed.f->Set(LEDRED);

REG(EXTINT) = EXTINT0;
// Acknowledge interrupt
REG(VICVectAddr) = 0;
} void EINT2Interrupt(void)
{
_uint8 i;
dLed.f->Set(LEDRED);
for(i=0;i<10;i++){};
dLed.f->Set(LEDGREEN);

REG(EXTINT) = EXTINT2;
// Acknowledge interrupt
REG(VICVectAddr) = 0;
} main(void) {
InitIntVectors();

// P0.15 et P0.16 is setting as EINT2 and EINT0

{
_uint32 vpbdiv = REG(SYSCON_VPBDIV);
vpbdiv = REG(SYSCON_VPBDIV); // 2210 Errata VPBDIV.1 work-aroud
REG(SYSCON_VPBDIV) = 0; // 2210 Errata EXTINT.1 work-aroud
// Configure irq on rising edge
REGSetBit(EXTMODE, EXTINT0); // edge sensitive
REGSetBit(EXTPOLAR, EXTINT0);// edge positive
REG(EXTINT) = EXTINT0; // clear interrupt flag
// Configure irq on falling edge
REGSetBit(EXTMODE, EXTINT2); // edge sensitive
REGClrBit(EXTPOLAR, EXTINT2);// edge negative
REG(EXTINT) = EXTINT2; // clear interrupt flag
REG(SYSCON_VPBDIV) = vpbdiv; // 2210 Errata EXTINT.1 work-aroud

InterruptEnable(VICIrqChEINT2); // enable interrupt
InterruptEnable(VICIrqChEINT0); // enable interrupt // Driver SFB : only edge negative needed
}

while(1){};
} AND THE RESULT IS :

signal in P0.15/16 : ___ _______
|__________| |______--------
_ _ _ _ _ _____ _ _
Led level (high level is for green) : ____| |_| |_| |_| |_| |_| |_| |_| |_------

INSTEAD OF

signal in P0.15/16 : ___ _______
|__________| |______--------
_________ _____
Led level (high level is for green) : _____| |______| ------ if I doesn't active EINT2 it work well in falling edge .... I dont understand why IRQ is always active even when there's no edge .... thanks for advance for any idea why the code don't work.

and sorry for my very bad english.

Sebastien.



Re: external interrupt edge sensitive don't work

An Engineer's Guide to the LPC2100 Series


Hallo Sebastien

I didn't study your code because I'm not sure that it is the same
for the LPC210x (which I know) as for the LPC22xx (which I don't
know). However I did note this sentence towards the end which
reminded me of an experince I had:

"I dont understand why IRQ is always active even when there's no
edge ...."

These are my ideas

1. The interrupts are basically level sensitive and not specifically
falling edge sensitive.

2. If an interrupt routine is called due to the iRQ line going low
and doesn't do an action to cause the IRQ line to go high again [eg.
reading a register from an external peripheral device] it can NOT
clear the interrupt. It will reenter the IRQ routine as soon as it
leaves it.
[Detail: It is not possible to clear an interrup by using the
following code if the IRQ line stays low {EXTINT_bit.EINT2 = 1}
beacsue the level sensitive interrupt simply causes it to be set
again]

3. I wanted to have an interrupt on an input sensor and adopted the
following code (which I call "one-shot" interrupt code) - example
for IRQ2.

A: Prepare the "one shot" interrupt
__disable_int();
LPC210xInitExternalInterrupt2(fnEint2Interrupt);
PINSEL0_bit.P0_15=0x2; // Set pin function to EINT2
EXTINT_bit.EINT2 = 1; // try to clear any pending interrupt
__enable_int();

void LPC210xInitExternalInterrupt2(void(*eint2_func)())
{
eint2_function = eint2_func; // Setup eint2 callback function.
VICIntSelect &= ~VIC_EINT2_bit; // IRQ on external int 2.
VICVectAddr4 = (unsigned int)&ExternalInterrupt2;
VICVectCntl4 = 0x20 | VIC_EINT2; // Enable vector interrupt.
VICIntEnable = VIC_EINT2_bit; // Enable EINT 2 interrupt.
}

B: When the IRQ occurs:

static void ExternalInterrupt2() // IRQ 2 interrupt routine
{
PINSEL0_bit.P0_15=0; // Set pin function to normal input.
(*eint2_function)(); // Execute interrupt callback function.
EXTINT_bit.EINT2 = 1; // Reset external interrupt flag.
}

You will see that the first thing which the IRQ routine does is to
set the IRQ line back to normal input. This allows the IRQ flag to
be reset even if the IRQ line remains low - hence the "One-shot"
property.

C: If another interrupt is required A: can be performed again.
Note that if the IRQ line is already at a low level the IRQ routine
will immediately be entered.

Maybe this was not exactly your problem but it may help.

Avec mes meilleurs salutations

Mark Butcher

www.mjbc.ch


Hello,

first, thanks for your answers.

>I didn't study your code because I'm not sure that it is the same
>for the LPC210x (which I know) as for the LPC22xx (which I don't
>know). However I did note this sentence towards the end which
>reminded me of an experince I had:


I use the same user manual that the 210x serie. >"I dont understand why IRQ is always active even when there's no
>edge ...."

>These are my ideas

>1. The interrupts are basically level sensitive and not specifically
>falling edge sensitive.


Why are they register for select edge sensitive if they work only in level sensitive ??? (EXTPOLAR register)




> I use the same user manual that the 210x serie.
>
> Why are they register for select edge sensitive if they work only
in level sensitive ??? (EXTPOLAR register)
>


Hallo Sastien

In my user manual (LPC2106/2105/2104 USER MANUAL) there is no
EXTPOLAR register so this must be specific to another processor type.

Regards

Mark Butcher



sorry it's the UM_LPC21XX_LPC22XX_2.pdf manual

and my problem concern just the EINT0 interrupt, I can't setting it without reason. (always low level sensitive)

Sebastien
----- Original Message -----
From: Mark Butcher
To:
Sent: Saturday, March 19, 2005 1:57 AM
Subject: [lpc2000] Re: external interrupt edge sensitive don't work

> I use the same user manual that the 210x serie.
>
> Why are they register for select edge sensitive if they work only
in level sensitive ??? (EXTPOLAR register)
>


Hallo Sastien

In my user manual (LPC2106/2105/2104 USER MANUAL) there is no
EXTPOLAR register so this must be specific to another processor type.

Regards

Mark Butcher
------
Yahoo! Groups Links

a.. To



I have the same problem, impossible to put 1 in EXTPOLAR and EXTMODE
for EINT0 (no problem for 1 to 3). I program all the recomendations
from philips :
Before writing to the EXTMODE and EXTPOLAR registers,
1> Write 0x0 to VPBDIV
2> Then write the desired value to EXTMODE or EXTPOLAR register.
3> Then write the same value to VPBDIV ( additional step)
4> Restore the VPBDIV to the previously saved value or simply write
to the register again with the desired value.

I test on 2 LPC2294 the same, so now i use IT capture 0 timer 1
instead of EINT0 for my quad external uart! --- In lpc2000@lpc2..., Sastien MARION (UMM)
<s.marion@u...> wrote:
>
> sorry it's the UM_LPC21XX_LPC22XX_2.pdf manual
>
> and my problem concern just the EINT0 interrupt, I can't setting it
without reason. (always low level sensitive)
>
> Sebastien
> ----- Original Message -----
> From: Mark Butcher
> To: lpc2000@lpc2...
> Sent: Saturday, March 19, 2005 1:57 AM
> Subject: [lpc2000] Re: external interrupt edge sensitive don't
work
>
> > I use the same user manual that the 210x serie.
> >
> > Why are they register for select edge sensitive if they work
only
> in level sensitive ??? (EXTPOLAR register)
> > Hallo Sastien
>
> In my user manual (LPC2106/2105/2104 USER MANUAL) there is no
> EXTPOLAR register so this must be specific to another processor
type.
>
> Regards
>
> Mark Butcher >
> --------------------------------
----------
> Yahoo! Groups Links
>
> a.. To >
>



jbhoudry wrote:
>
> I have the same problem, impossible to put 1 in EXTPOLAR and EXTMODE
> for EINT0 (no problem for 1 to 3). I program all the recomendations
> from philips :
> Before writing to the EXTMODE and EXTPOLAR registers,
> 1> Write 0x0 to VPBDIV
> 2> Then write the desired value to EXTMODE or EXTPOLAR register.
> 3> Then write the same value to VPBDIV ( additional step)
> 4> Restore the VPBDIV to the previously saved value or simply write
> to the register again with the desired value.
>
> I test on 2 LPC2294 the same, so now i use IT capture 0 timer 1

Could Philips urgently confirm or not this EINT0 edge problem exists on
a LPC2124 ?

Just about to change a layout to use EINT0 in edge sensitive mode
(wasn't using it at all before) to WAKEup out of sleep mode, so I'm not
in a position to test this till it's all too late !!

--
Cheers,
Bruce
-------------------------------
/\\\/\\\/\\\ / / Bruce Paterson
/ \\\ \\\ \\\ / / Senior Design Engineer
/ /\\\/\\\/\\\/ / 8 Anzed Court, Mulgrave, Vic, 3170
/ / \\\ \\\ \\\ / PO Box 4112, Mulgrave, Vic, 3170, Australia
/ / \\\/\\\ \\\/ Ph: +61 3 8561 4232 Fax: +61 3 9560 9055
Tele-IP Ltd. Email: bruce@bruc... Icq: #32015991
WWW: http://www.tele-ip.com VK3TJN
-------------------------------



Bruce,

I tried debugging the below code using the Keil MicroVision3
debugger.

/* Configuring EXTMODE and EXTPOLAR */
VPBDIV=0x0;
EXTMODE=0x1;
VPBDIV=0x1;

VPBDIV=0x0;
EXTPOLAR=0x1;
VPBDIV=0x1;

VPBDIV=0x0;

It works fine on my end. Please dont single-step through these
instructions. You need to place a breakpoint at the instruction
following

VPBDIV=0x0;

When this breakpoint is hit, on the Memory Window of the debugger,
EXTMODE and EXTPOLAR should reflect 0x1

Best Regards,
Philips_apps

--- In lpc2000@lpc2..., Bruce Paterson <bruce@t...> wrote:
> jbhoudry wrote:
> >
> > I have the same problem, impossible to put 1 in EXTPOLAR and
EXTMODE
> > for EINT0 (no problem for 1 to 3). I program all the
recomendations
> > from philips :
> > Before writing to the EXTMODE and EXTPOLAR registers,
> > 1> Write 0x0 to VPBDIV
> > 2> Then write the desired value to EXTMODE or EXTPOLAR register.
> > 3> Then write the same value to VPBDIV ( additional step)
> > 4> Restore the VPBDIV to the previously saved value or simply
write
> > to the register again with the desired value.
> >
> > I test on 2 LPC2294 the same, so now i use IT capture 0 timer 1
>
> Could Philips urgently confirm or not this EINT0 edge problem
exists on
> a LPC2124 ?
>
> Just about to change a layout to use EINT0 in edge sensitive mode
> (wasn't using it at all before) to WAKEup out of sleep mode, so I'm
not
> in a position to test this till it's all too late !!
>
> --
> Cheers,
> Bruce
> -------------------------------
> /\\\/\\\/\\\ / / Bruce Paterson
> / \\\ \\\ \\\ / / Senior Design Engineer
> / /\\\/\\\/\\\/ / 8 Anzed Court, Mulgrave, Vic, 3170
> / / \\\ \\\ \\\ / PO Box 4112, Mulgrave, Vic, 3170, Australia
> / / \\\/\\\ \\\/ Ph: +61 3 8561 4232 Fax: +61 3 9560 9055
> Tele-IP Ltd. Email: bruce@t... Icq: #32015991
> WWW: http://www.tele-ip.com VK3TJN
> -------------------------------



hi,

I make the same things with pathfinder and EXTMODE are correct BUT without effect on the behaviour of EINT0 always on low level detection mode ....

I note that EXTMODE and EXTPOLAR never chane the behaviour of EINT0 !!! (same code with EINT2 work very fine)

Regards,
Sastien ----- Original Message -----
From: philips_apps
To: lpc2000@lpc2...
Sent: Thursday, March 31, 2005 11:58 PM
Subject: [lpc2000] Re: external interrupt edge sensitive don't work
Bruce,

I tried debugging the below code using the Keil MicroVision3
debugger.

/* Configuring EXTMODE and EXTPOLAR */
VPBDIV=0x0;
EXTMODE=0x1;
VPBDIV=0x1;

VPBDIV=0x0;
EXTPOLAR=0x1;
VPBDIV=0x1;

VPBDIV=0x0;

It works fine on my end. Please dont single-step through these
instructions. You need to place a breakpoint at the instruction
following

VPBDIV=0x0;

When this breakpoint is hit, on the Memory Window of the debugger,
EXTMODE and EXTPOLAR should reflect 0x1

Best Regards,
Philips_apps

--- In lpc2000@lpc2..., Bruce Paterson <bruce@t...> wrote:
> jbhoudry wrote:
> >
> > I have the same problem, impossible to put 1 in EXTPOLAR and
EXTMODE
> > for EINT0 (no problem for 1 to 3). I program all the
recomendations
> > from philips :
> > Before writing to the EXTMODE and EXTPOLAR registers,
> > 1> Write 0x0 to VPBDIV
> > 2> Then write the desired value to EXTMODE or EXTPOLAR register.
> > 3> Then write the same value to VPBDIV ( additional step)
> > 4> Restore the VPBDIV to the previously saved value or simply
write
> > to the register again with the desired value.
> >
> > I test on 2 LPC2294 the same, so now i use IT capture 0 timer 1
>
> Could Philips urgently confirm or not this EINT0 edge problem
exists on
> a LPC2124 ?
>
> Just about to change a layout to use EINT0 in edge sensitive mode
> (wasn't using it at all before) to WAKEup out of sleep mode, so I'm
not
> in a position to test this till it's all too late !!
>
> --
> Cheers,
> Bruce
> -------------------------------
> /\\\/\\\/\\\ / / Bruce Paterson
> / \\\ \\\ \\\ / / Senior Design Engineer
> / /\\\/\\\/\\\/ / 8 Anzed Court, Mulgrave, Vic, 3170
> / / \\\ \\\ \\\ / PO Box 4112, Mulgrave, Vic, 3170, Australia
> / / \\\/\\\ \\\/ Ph: +61 3 8561 4232 Fax: +61 3 9560 9055
> Tele-IP Ltd. Email: bruce@t... Icq: #32015991
> WWW: http://www.tele-ip.com VK3TJN
> -------------------------------


------
Yahoo! Groups Links

a.. To



I make the same things, whith Phytec board LPC2294, Isystem Ione and
Iar compiler, work fine for EINT1-3 and always 0 for EINT0!

Regards,
JBH

--- In lpc2000@lpc2..., Sastien MARION (UMM)
<s.marion@u...> wrote:
> hi,
>
> I make the same things with pathfinder and EXTMODE are correct
BUT without effect on the behaviour of EINT0 always on low level
detection mode ....
>
> I note that EXTMODE and EXTPOLAR never chane the behaviour of
EINT0 !!! (same code with EINT2 work very fine)
>
> Regards,
> Sastien > ----- Original Message -----
> From: philips_apps
> To: lpc2000@lpc2...
> Sent: Thursday, March 31, 2005 11:58 PM
> Subject: [lpc2000] Re: external interrupt edge sensitive don't
work
> Bruce,
>
> I tried debugging the below code using the Keil MicroVision3
> debugger.
>
> /* Configuring EXTMODE and EXTPOLAR */
> VPBDIV=0x0;
> EXTMODE=0x1;
> VPBDIV=0x1;
>
> VPBDIV=0x0;
> EXTPOLAR=0x1;
> VPBDIV=0x1;
>
> VPBDIV=0x0;
>
> It works fine on my end. Please dont single-step through these
> instructions. You need to place a breakpoint at the instruction
> following
>
> VPBDIV=0x0;
>
> When this breakpoint is hit, on the Memory Window of the
debugger,
> EXTMODE and EXTPOLAR should reflect 0x1
>
> Best Regards,
> Philips_apps
>
> --- In lpc2000@lpc2..., Bruce Paterson <bruce@t...> wrote:
> > jbhoudry wrote:
> > >
> > > I have the same problem, impossible to put 1 in EXTPOLAR and
> EXTMODE
> > > for EINT0 (no problem for 1 to 3). I program all the
> recomendations
> > > from philips :
> > > Before writing to the EXTMODE and EXTPOLAR registers,
> > > 1> Write 0x0 to VPBDIV
> > > 2> Then write the desired value to EXTMODE or EXTPOLAR
register.
> > > 3> Then write the same value to VPBDIV ( additional step)
> > > 4> Restore the VPBDIV to the previously saved value or simply
> write
> > > to the register again with the desired value.
> > >
> > > I test on 2 LPC2294 the same, so now i use IT capture 0 timer
1
> >
> > Could Philips urgently confirm or not this EINT0 edge problem
> exists on
> > a LPC2124 ?
> >
> > Just about to change a layout to use EINT0 in edge sensitive
mode
> > (wasn't using it at all before) to WAKEup out of sleep mode, so
I'm
> not
> > in a position to test this till it's all too late !!
> >
> > --
> > Cheers,
> > Bruce
> > ----------------------------
---
> > /\\\/\\\/\\\ / / Bruce Paterson
> > / \\\ \\\ \\\ / / Senior Design Engineer
> > / /\\\/\\\/\\\/ / 8 Anzed Court, Mulgrave, Vic, 3170
> > / / \\\ \\\ \\\ / PO Box 4112, Mulgrave, Vic, 3170,
Australia
> > / / \\\/\\\ \\\/ Ph: +61 3 8561 4232 Fax: +61 3 9560
9055
> > Tele-IP Ltd. Email: bruce@t... Icq: #32015991
> > WWW: http://www.tele-ip.com
VK3TJN
> > ----------------------------
---
>
>
> --------------------------------
----------
> Yahoo! Groups Links
>
> a.. To >
>