attach a patch
implementing this. It seems to work in basic testing; libgcc compiles,
the test case and the larger code that it comes from now works
correctly. Code generation may be a bit worse from having only 2/3
pointer register pairs to work with, but it will at least be correct.
2) Split apart HImode from Pmode on AVR. The current code in
avr_hard_regno_mode_ok() seems to be written on the assumption that
this is the case since it talks about only allowing Pmode.
I'm not sure how to do this without bloating avr.md a lot.
3) Try to fix the framepointer situation so that it gets correctly
accounted for and you can't accidentally write over half of it
if you use half the register at the wrong time. Sounds like the
right thing to do. Sounds a project I'd have no idea how to start.
4) Make the code in resolve_shift_zext() and anywhere else use
(strict_lower_part ) when it doesn't want the upper part to be
overwritten. Again, sounds like the right thing to do. I tried to do
this, was beyond my GCC hacking skills. Also, I suspect that it might
have gigantic unexpected consequences on generated code
on various platforms.
5) Try to split apart 'HARD_REGNO_MODE_OK' into two concepts:
- Whether it's OK to allocate registers in this mode
- Whether it's OK to read and write this register as a subreg
of a larger register.
The second check could then be used in simplify_subreg_regno()
and the push_reload() optimization. I don't think GCC really
needs the extra complexity.
For comparison, With the attached patch the body of the function is the
much more reasonable:
===
rcall func1
mov r15,r24
rcall func1
mov r17,r15
ldi r16,lo8(0)
add r16,r24
adc r17,__zero_reg__
ldi r24,hi8(257)
cpi r16,lo8(257)
cpc r17,r24
brge .L1
rcall func1
mov r24,r16
mov r25,r17
rcall funct2
===
--
Summary: avr miscompilations related to frame pointer registers
Product: gcc
Version: 4.5.1
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: target
AssignedTo: unassigned at gcc dot gnu dot org
ReportedBy: otaylor at redhat dot com
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=45291