On 08/14/2018 01:32 PM, Paul Koning wrote:
> I'm trying to convert the pdp11 target to use LRA.
>
> A lot of it "just works". But one of the test suite files fails in a way
> that I can't figure out at all. I'm hoping for some help or hints to track
> down the cause and come up with a fix.
>
> The failing program is testsuite/gcc.c-torture/compile/ifreg.c:
>
> union foo
> {
> float f;
> int i;
> };
>
> foo (int a, float c)
> {
> union foo b;
> b.i = a;
> return b.f + c;
> }
>
> When compiled in LRA mode, I get this:
>
> during RTL pass: reload
> dump file: ifreg.c.274r.reload
> ../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c: In function ‘foo’:
> ../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c:12:1: internal compiler
> error: Max. number of generated reload insns per insn is achieved (90)
>
> I fiddled a bit with the mov<mode> patterns, for example disabling the
> patterns that work on multi-word values (SI and DI mode, since pdp11 word is
> HImode). That doesn't fix (or create) the failure, though the specific insns
> change as a result.
>
> What I see going in to reload (from the "ira" dump file) is:
>
> (note 5 1 2 2 [bb 2] NOTE_INSN_BASIC_BLOCK)
> (note 2 5 4 2 NOTE_INSN_DELETED)
> (note 4 2 22 2 NOTE_INSN_FUNCTION_BEG)
> (insn 22 4 18 2 (clobber (reg/v:DI 26 [ b ]))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 -1
> (nil))
> (insn 18 22 19 2 (set (subreg:HI (reg/v:DI 26 [ b ]) 0)
> (const_int 0 [0]))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> (insn 19 18 20 2 (set (subreg:HI (reg/v:DI 26 [ b ]) 2)
> (const_int 0 [0]))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> ...
>
> Reload shows this:
>
> (note 5 1 2 2 [bb 2] NOTE_INSN_BASIC_BLOCK)
> (note 2 5 4 2 NOTE_INSN_DELETED)
> (note 4 2 22 2 NOTE_INSN_FUNCTION_BEG)
> (insn 22 4 18 2 (clobber (reg/v:DI 26 [ b ]))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 -1
> (nil))
> (insn 18 22 25 2 (set (reg:HI 32)
> (const_int 0 [0]))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> (insn 25 18 26 2 (set (reg:HI 33)
> (reg:HI 32))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> (insn 26 25 27 2 (set (reg:HI 34)
> (reg:HI 33))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> (insn 27 26 28 2 (set (reg:HI 35)
> (reg:HI 34))
> "../../gcc/gcc/testsuite/gcc.c-torture/compile/ifreg.c":10 21 {movhi}
> (nil))
> ... with insns that do nothing, like the one above, repeating until it gives
> up.
>
> At the top of the dump file where LRA is reporting what it's doing, I see
> this:
>
> ********** Local #1: **********
>
> Spilling non-eliminable hard regs: 6
> New elimination table:
> Can eliminate 15 to 6 (offset=10, prev_offset=0)
> Can eliminate 15 to 5 (offset=4, prev_offset=0)
> Can eliminate 14 to 6 (offset=8, prev_offset=0)
> Can eliminate 14 to 5 (offset=0, prev_offset=0)
> 0 Non input pseudo reload: reject++
> alt=0,overall=7,losers=1,rld_nregs=1
> 0 Non input pseudo reload: reject++
> alt=1,overall=7,losers=1,rld_nregs=1
> alt=2: Bad operand -- refuse
> alt=3: Bad operand -- refuse
> Choosing alt 0 in insn 18: (0) =rR (1) rRN {movhi}
We've selected alternative 0 for insn 18. I believe that's the rRN ->
=rR alternative.
> Creating newreg=32, assigning class GENERAL_REGS to r32
The insn did not match its constraints. So some kind of reload is
needed. We allocate a new reload register r32.
> 18: r32:HI=0
> Inserting insn reload after:
And we try to initialize r32 to 0. Which of course needs another reload.
I suspect LRA is somehow missing that the operand could live in memory.
Jeff