------- Comment #2 from kkojima at gcc dot gnu dot org  2009-09-30 02:00 -------
It seems that the difference occurs at combine pass.  With -g,
two insns

(insn 104 102 106 12 xxx.c:127 (set (reg:SI 207 [ stmt_4->gsbase.code ])
        (zero_extend:SI (reg:QI 219 [ stmt_4->gsbase.code ]))) 156
{*zero_extendqisi2_compact} (expr_list:REG_DEAD (reg:QI 219 [
stmt_4->gsbase.code ])
        (expr_list:REG_EQUAL (zero_extend:SI (mem/s/j:QI (reg/v/f:SI 161 [ stmt
]) [0 stmt_4->gsbase.code+0 S1 A32]))
            (nil))))

(insn 106 104 107 12 xxx.c:127 (set (reg:SI 147 t)
        (eq:SI (reg:SI 207 [ stmt_4->gsbase.code ])
            (const_int 6 [0x6]))) 1 {cmpeqsi_t} (expr_list:REG_DEAD (reg:SI 207
[ stmt_4->gsbase.code ])
        (nil)))

are successfully combined:

Trying 104 -> 106:
Successfully matched this instruction:
(set (reg:SI 147 t)
    (eq:SI (subreg:SI (reg:QI 219 [ stmt_4->gsbase.code ]) 0)
        (const_int 6 [0x6])))

but without -g, the corresponding two insns

(insn 89 87 91 12 xxx.c:127 (set (reg:SI 207 [ stmt_4->gsbase.code ])
        (zero_extend:SI (reg:QI 219 [ stmt_4->gsbase.code ]))) 156
{*zero_extendqisi2_compact} (expr_list:REG_DEAD (reg:QI 219 [
stmt_4->gsbase.code ])
        (expr_list:REG_EQUAL (zero_extend:SI (mem/s/j:QI (reg/v/f:SI 161 [ stmt
]) [0 stmt_4->gsbase.code+0 S1 A32]))
            (nil))))

(insn 91 89 92 12 xxx.c:127 (set (reg:SI 147 t)
        (eq:SI (reg:SI 207 [ stmt_4->gsbase.code ])
            (const_int 6 [0x6]))) 1 {cmpeqsi_t} (expr_list:REG_DEAD (reg:SI 207
[ stmt_4->gsbase.code ])
        (nil)))

are filed to be combined:

Trying 89 -> 91:
Failed to match this instruction:
(set (reg:SI 147 t)
    (eq:SI (reg:QI 219 [ stmt_4->gsbase.code ])
        (const_int 6 [0x6])))

I've traced what is going on in try_combine for these 2 cases and
found the combine.c:get_last_value returns (clobber (const_int 0))
without -g but (mem/s/j:QI (reg/v/f:SI 161)) with -g for
(reg:QI 219 [ stmt_4->gsbase.code ]).
Without -g, get_last_value_validate replaces the original *loc
(mem/s/j:QI (reg/v/f:SI 161)) with (clobber (const_int 0)) by

  /* If this is a memory reference, make sure that there were
     no stores after it that might have clobbered the value.  We don't
     have alias info, so we assume any store invalidates it.  */
  else if (MEM_P (x) && !MEM_READONLY_P (x)
           && DF_INSN_LUID (insn) <= mem_last_set)
    {
      if (replace)
        *loc = gen_rtx_CLOBBER (GET_MODE (x), const0_rtx);
      return replace;
    }

where insn is

(insn 21 20 22 4 xxx.c:135 (set (reg:QI 219 [ stmt_4->gsbase.code ])
        (mem/s/j:QI (reg/v/f:SI 161 [ stmt ]) [0 stmt_4->gsbase.code+0 S1
A32]))

both DF_INSN_LUID (insn) and mem_last_set are 0 here.
This mem_last_set is set to 0 at

0x0869b923 in record_dead_and_set_regs_1 (dest=0xb7fb0fb4, setter=0xb7fb0fc0, 
    data=0xb7fb80d8) at ../../LOCAL/trunk/gcc/combine.c:11823
11823       mem_last_set = DF_INSN_LUID (record_dead_insn);
(gdb) call debug_rtx(record_dead_insn)
(insn 87 86 89 12 xxx.c:152 (set (mem/s:SI (reg/v/f:SI 166 [ rhs ]) [0
rhs_27->exp.locus+0 S4 A32])
        (reg:SI 168 [ D.2312 ])) 175 {movsi_ie} (expr_list:REG_DEAD (reg:SI 168
[ D.2312 ])
        (nil)))

With -g, mem_last_set is set to 1 at the same situation with insn

(insn 88 87 89 11 xxx.c:146 (set (reg:HI 201 [ rhs_27->base.code ])
        (mem/s/j:HI (reg/v/f:SI 166 [ rhs ]) [0 rhs_27->base.code+0 S2 A32]))
187 {movhi_i} (nil))

because there is an insn just before insn 88 for debug:

(insn 87 86 88 11 xxx.c:146 (set (reg/f:SI 199)
        (symbol_ref:SI ("tree_code_type") [flags 0x40] <var_decl 0xb7efb228
tree_code_type>)) 175 {movsi_ie} (nil))

which doesn't appear without -g.

It looks that DF_INSN_LUID can be unique only in each basic blocks
here and the above code of get_last_value_validate compares DF_INSN_LUID
of insns at different basic blocks.


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=41511

Reply via email to