Daniel Jacobowitz <[EMAIL PROTECTED]> writes:
> On Fri, Jun 16, 2006 at 02:12:29PM -0700, Ian Lance Taylor wrote:
> > The computation of the address of x was moved outside the
> > conditional--that is, both the rdhwr and the addu moved. You'll have
> > to figure out why. gcc shouldn't move instructions outside of a
> > conditional unless they are cheap and don't trap. This instruction
> > doesn't trap, but it's not cheap.
>
> What metric gets used for this - rtx_cost?
I'm not sure, because I'm not sure what is hoisting the instruction.
I tried recreating this, but I couldn't. I get this:
foo:
.frame $sp,0,$31 # vars= 0, regs= 0/0, args= 0, gp= 0
.mask 0x00000000,0
.fmask 0x00000000,0
.set noreorder
.cpload $25
.set reorder
.set noreorder
.set nomacro
beq $4,$0,$L7
.set push
.set mips32r2
rdhwr $3,$29
.set pop
.set macro
.set reorder
lw $2,%gottprel(x)($28)
addu $2,$2,$3
lw $2,0($2)
j $31
$L7:
.set noreorder
.set nomacro
j $31
move $2,$0
.set macro
.set reorder
This of course is not ideal, since it unconditionally executes the
rdhwr instruction. But it is not the same as what the OP reported.
This case happens because reorg.c ignores the cost of the instruction
in fill_slots_from_thread. I believe that reorg.c should not move an
expensive instruction which is only conditionally executed into a
delay slot. That is probably a bug.
We can see a similar case with this:
int foo(int arg, int x)
{
if (arg)
return x * x;
return 0;
}
which yields this:
foo:
.frame $sp,0,$31 # vars= 0, regs= 0/0, args= 0, gp= 0
.mask 0x00000000,0
.fmask 0x00000000,0
.set noreorder
.cpload $25
.set reorder
.set noreorder
.set nomacro
beq $4,$0,$L7
mult $5,$5
.set macro
.set reorder
mflo $2
j $31
$L7:
.set noreorder
.set nomacro
j $31
move $2,$0
.set macro
.set reorder
which executes the "mult" instruction unconditionally which is
probably not desirable since it will tie up the multiplication
pipeline.
Ian