Subject:
|
Re: [long] Interrupt programming, buggy code
|
Newsgroups:
|
lugnet.robotics.rcx
|
Date:
|
Tue, 2 Mar 2004 17:54:47 GMT
|
Viewed:
|
3426 times
|
| |
| |
Hi Benjamin,
When you declare your ISR as an interrupt_handler, GCC terminates the function
with an "rte" instead of an "rts". The ROM code that dispatches the interrupt
to your function is already doing the rte so your function should not. Here's
the ROM dispatch code:
04cc: mov.w r6,@-e7
04ce: mov.w @0xfda2:16,r6
04d2: jsr @r6
04d4: mov.w @r7+,r6
04d6: rte
Instead, you could remove the interrupt_handler attribute and preserve the
scratch registers like so:
void ocia_handler(void) {
__asm__ ("push r0");
__asm__ ("push r1");
__asm__ ("push r2");
__asm__ ("push r3");
FRT_TCSR &= ~bit3; /* clear output compare flag A */
count++;
debug_value(count);
__asm__ ("pop r3");
__asm__ ("pop r2");
__asm__ ("pop r1");
__asm__ ("pop r0");
}
Also, the C compiler that generated the ROM code uses a different calling
convention than GCC and r6 is trashed by the debug_value() call. GCC isn't
expecting this, so it may be prudent to wrap calls to debug_value() with a push
and pop of r6. It won't cause a problem in your current code because the ROM
dispatch code already preserves r6 for your ISR.
HTH,
Mark
In lugnet.robotics.rcx, Benjamin Sigonneau wrote:
> Hi all,
>
> I am currently programming the Lego RCX at low-level (plain C) using the
> GCC cross-compiler for Hitachi H8/300 and Kekoa Proudfoot's LibRCX. In
> fact, I'm designing exercises for students that learn micro-controller
> programming. Therefore, I don't even use the ROM routines (except those
> that deals with the lcd display).
>
> I managed to deal with motors and touch sensors using both the Hitachi
> Hardware Manual and Kekoa Proudfoot's "RCX Internals".
>
> I know want to program the H8/300 interrupts. I've managed to define an
> OCIA handler, but I'm afraid I've missed something since I can't get it
> to work right. This handler only increments a global and then displays
> its value on the LCD. That should be easy, but... When I run my program,
> the LCD displays 0, then 1, then 2, then 3, then... Then the RCX hangs,
> and I can't get anything from it. I have to remove the batteries and put
> them in again to "reboot" the crashed RCX.
>
> I just don't see what I'm doing wrong, so I'm asking if anybody has an
> idea. In case such gurus lie around here, I post my C code below.
>
> Thanks.
>
>
> /* My buggy code */
>
> int count;
>
> #define mask_it() asm ("orc #0x80, ccr");
> #define unmask_it() asm ("andc #0x7f, ccr");
>
> #define OCIA_HANDLER *( (volatile word *) 0xfda2)
>
> void ocia_handler(void) __attribute__ ((interrupt_handler));
> void ocia_handler(void) {
> FRT_TCSR &= ~bit3; /* clear output compare flag A */
> count++;
> debug_value(count);
> }
>
> int main (void) {
>
> count = 0;
>
> /* debug_value is just a call to ROM routine at 0x1ff2
> * that displays an integer */
> debug_value(count);
>
> OCIA_HANDLER = (word)ocia_handler; /* install OCIA handler */
>
> /* Timer clock selection: use div 32 clock */
> FRT_TCR |= bit1; /* CSK1 <- 1 */
> FRT_TCR &= ~bit0; /* CSK0 <- 0 */
>
> FRT_TCSR = bit0; /* Clear FRT on compare-match A */
> FRT_TOCR &= ~bit4; /* Compare timer to OCRA */
> FRT_OCRA = 50000; /* Interrupt every 100 ms */
> FRT_FRC = 0; /* Clear free running timer */
> FRT_TCSR &= ~bit3; /* Clear output compare flag A */
>
> /* Enable OCIA - see p. 117
> * ie an interrupt is generated when FRT == OCRA
> */
> FRT_TIER |= bit3;
>
> /* Unmask interrupts */
> unmask_it();
>
> while (!prgm_pressed()) {
> /* Wait for "pgrm"button to be pressed */
> }
>
> return 0;
> }
|
|
Message has 3 Replies: | | Re: [long] Interrupt programming, buggy code
|
| On Tue, 2 Mar 2004 17:54:47 GMT "Mark Riley" <markril@hotmail.com> wrote: Hi Mark, (...) [snip] (...) [snip] And that was it, indeed! Many to you, as well as Ralph and Kevin who tried to help me. There shouldn't be much trouble for me I think (if we (...) (21 years ago, 2-Mar-04, to lugnet.robotics.rcx)
|
Message is in Reply To:
| | [long] Interrupt programming, buggy code
|
| Hi all, I am currently programming the Lego RCX at low-level (plain C) using the GCC cross-compiler for Hitachi H8/300 and Kekoa Proudfoot's LibRCX. In fact, I'm designing exercises for students that learn micro-controller programming. Therefore, I (...) (21 years ago, 2-Mar-04, to lugnet.robotics.rcx)
|
7 Messages in This Thread:
- Entire Thread on One Page:
- Nested:
All | Brief | Compact | Dots
Linear:
All | Brief | Compact
This Message and its Replies on One Page:
- Nested:
All | Brief | Compact | Dots
Linear:
All | Brief | Compact
|
|
|
|