[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [avr-libc-dev] Re: gcc's avr implementation does not appear to be in
From: |
Marek Michalkiewicz |
Subject: |
Re: [avr-libc-dev] Re: gcc's avr implementation does not appear to be interrupt safe! |
Date: |
Wed, 19 Jan 2005 19:56:10 +0100 |
User-agent: |
Mutt/1.5.6+20040907i |
On Wed, Jan 19, 2005 at 11:07:50AM -0700, E. Weddington wrote:
> Paul Schlie wrote:
>
> >Hey guys, just to give you a heads up, as there are routines implemented
> >in both avr.c and avr.md that temporarily utilize r1 without disabling
> >interrupts around these sections;
> >
> Please provide examples (functions, line numbers, etc.) of what you mean.
Yes, this happens a few times - for example, MUL instructions return
their result in r1:r0. But interrupts are not a problem here, because
interrupt/signal prologue saves r1 on stack and then clears it (and
epilogue restores it before returning to the main program).
> >The only reasonable solution to this problem that I see is to remove the
> >presumption that r1 == 0, and let the complier allocate what ever values it
> >deems necessary to generate efficient code; as otherwise the requirement to
> >block interrupts around these otherwise critical sections doesn't seem like
> >a good idea, as it's neither efficient code-wise, or helpful minimizing
> >interrupt latencies. (the compiler will tend to allocate and maintain any
> >frequently required value, the avr port should likely just let the compiler
> >do it's job).
The use of fixed registers r0 and r1 (__tmp_reg__ and __zero_reg__)
dates back to the beginning of avr-gcc (a few years ago). One big
problem with changing this is with restrictions on movM patterns:
Therefore, when given such a pair of operands, the pattern must
generate RTL which needs no reloading and needs no temporary
registers--no registers other than the operands. [...]
In some cases (loading constants to lower 16 registers not allowed
for "ldi") r31 is used as an extra temporary register, but it is
saved in __tmp_reg__ first, and GCC knows nothing about this.
Yes, this is a hack, but the alternative is to load the constant
with "lds" - a waste of RAM (usually more valuable than flash).
> >(now that I think of it, to my vague recollection, I recall that stack
> >pointer manipulation may also not be interrupt save, but haven't checked
> >the code yet)
If you check it, you will see that interrupts are disabled around
any stack pointer changes. SREG is restored (possibly re-enabling
interrupts, if enabled before) between changing SPH and SPL, but
enabling interrupts takes effect only after the next instruction.
There is a -mtiny-stack option for cases where the stack fits within
one 256-byte page (SPH never changes or simply doesn't exist), and
also -mno-interrupts for code that runs with interrupts disabled.
> And next time please post to a mailing list, preferrably avr-libc-dev
> (which I've CC'd) where the GCC maintainers (or at least one of them) is
> listening in.
Not very actively recently - but yes, I'm still alive :)
Marek