Alternate stack pointer for interrupt handlers?

Go To Last Post
15 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

is there a way to let GCC generate signal handler code that uses an alternate stack pointer? The function attribute sp_switch would do what I want but it is ignore for AVR targets.

Is there another way?

Thanks,
Markus

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Why do you want to do that ?

1) Studio 4.18 build 716 (SP3)
2) WinAvr 20100110
3) PN, all on Doze XP... For Now
A) Avr Dragon ver. 1
B) Avr MKII ISP, 2009 model
C) MKII JTAGICE ver. 1

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MegaTorr wrote:
is there a way to let GCC generate signal handler code that uses an alternate stack pointer? The function attribute sp_switch would do what I want but it is ignore for AVR targets.
You'll have to implement it on your own, either as function attribute in your private avr-gcc port or by means of application software in your OS scheduler.

Function attributes implemented for SH won't work for AVR, of course.

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Obviously I would like to avoid running my own gcc port ;).

What would help me a lot is if I can get gcc to generate an ISR prologue/epilogue for a regular function (saving of r0/r1, SREG, r18-r27, r30/r31) depending on those registers being accessed.

If I declare a regular function with a signal (or interrupt) attribute gcc complains that an interrupt handler is misnamed. And if I don't give it the attribute signal then gcc doesn't save those registers.

Can I change this behaviour?
Or inject a piece of custom assmebler code into the prologue/epilogue?

Thanks,
Markus

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Or, can I get gcc to store the interrupt vector table somewhere else and I provide an interrupt table with proxy calls?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MegaTorr wrote:
What would help me a lot is if I can get gcc to generate an ISR prologue/epilogue for a regular function (saving of r0/r1, SREG, r18-r27, r30/r31) depending on those registers being accessed.

If I declare a regular function with a signal (or interrupt) attribute gcc complains that an interrupt handler is misnamed. And if I don't give it the attribute signal then gcc doesn't save those registers.

Maybe what you are looking for is simply ISR macro provided here?

http://nongnu.org/avr-libc/user-...

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks for the link. The only option I see would be declaring each ISR as naked, at which point I would have to manually generate the prologue/epilogue for each ISR (which is a pain since I don't know which registers gcc will use) or use the brute-force approach and save all of them - regardless of usage.

Is that really my only option?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

It's already hard for me to grasp what you really want and what's in "your opinion":

MegaTorr wrote:
What would help me a lot is if I can get gcc to generate an ISR prologue/epilogue for a regular function (saving of r0/r1, SREG, r18-r27, r30/r31) depending on those registers being accessed.
You want everything like an ISR with the following exception: If, say, R28 is used by the C code that register should *not* be saved/restored?

If you are concerned about the warning when "ordinary" function is attributed signal/interrupt, then write

static void __attribute__ ((signal, used))
__vector_foo (void)
{
}

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

cool, that did the trick!

would you also happen to have an idea how I get gcc to issue a 'ret' instead of a 'reti' as part of the epilogue?

Thanks a lot,
Markus

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MegaTorr wrote:
would you also happen to have an idea how I get gcc to issue a 'ret' instead of a 'reti' as part of the epilogue?
Not without hack, for example
asm (".macro reti\nret\n.endm\n");

static void __attribute__ ((signal,used))
__vector_foo (void)
{
}

and compile with -fno-toplevel-reorder and no code after __vector_foo. You may expect strange results if variable in static storage is named "reti".

But if you think you need that *really* maybe you have a design flaw and discussing the anatomy of your code is indicated.

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
   .global foo_vector
foo_vector:
   push R16
   in R16, SPL
   sts oldSPL, R16
   in R16, SPH
   sts oldSPH, R16
   ldi R16, newSPL
   out SPL, R16
   ldi R16, newSPH
   out SPH, R16
   call foo_vector_c
   cli ;  will be executed immediately after reti
   ... ; an exercise for the reader
   pop R16
   reti

Of course, we still don't know why you want a different stack pointer.
The utility, if any, is not obvious.
It does add rather a lot of cycles.

Iluvatar is the better part of Valar.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

My crystal ball says this is an attempt to reduce individual task's stack usage for a multitasking system.

Which in itself is a dubious (even if popular) concept for an 8-bitter, IMHO.

JW

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Context:

This is an experiment in multitasking and I'm not sure yet where it will end up. If I run multiple tasks with their own stack space, then each one of them has to accommodate for interrupt stack space...

I've been playing with protothreads and similar single stack concepts, so this seemed to be the next logical step.

Michael,

Quote:

   call foo_vector_c
   cli ;  will be executed immediately after reti
   ... ; an exercise for the reader 


thanks a lot, I had forgotten that the AVR executes a single instruction while interrupts are still disabled after reti and cli. So there is no race left.

Have fun,
Markus

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MegaTorr wrote:
I had forgotten that the AVR executes a single instruction while interrupts are still disabled
This wors too for Xmega? SEI has no latency, so setting I flag by hand (OUT SREG, Rn) or by RETI probably works similar.

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Correction: The instructions to turn on interrupts are reti and sei.

I don't know about the xmega - never used one.

Have fun,
Markus