https://gcc.gnu.org/bugzilla/show_bug.cgi?id=91291
--- Comment #2 from Richard Biener <rguenth at gcc dot gnu.org> ---
Ah, we do not eliminate
# VUSE <.MEM_8>
reg.0_2 = reg;
because this is a hard-register load (we know reg.0_2 is constant 1). So
we end up making the constant 1 (value) available via the leader reg.0_2.
Note it doesn't really work here as the comment says
/* See PR43491. Do not replace a global register variable when
it is a the RHS of an assignment. Do replace local register
variables since gcc does not guarantee a local variable will
be allocated in register.
??? The fix isn't effective here. This should instead
be ensured by not value-numbering them the same but treating
them like volatiles? */
&& !(gimple_assign_single_p (stmt)
&& (TREE_CODE (gimple_assign_rhs1 (stmt)) == VAR_DECL
&& DECL_HARD_REGISTER (gimple_assign_rhs1 (stmt))
&& is_global_var (gimple_assign_rhs1 (stmt)))))
uses of reg.0_2 will still be replaced with '1':
Value numbering stmt = reg = 1B;
RHS 1B simplified to 1B
No store match
Value numbering store reg to 1B
Setting value number of .MEM_8 to .MEM_8 (changed)
Value numbering stmt = reg.0_2 = reg;
Setting value number of reg.0_2 to 1B (changed)
Value numbering stmt = if (reg.0_2 == 0B)
marking known outgoing edge 3 -> 5 executable
Removing unexecutable edge from if (reg.0_2 == 0B)
...
<bb 3> :
foo:
reg = 1B;
reg.0_2 = reg;
reg = &foo;
goto <bb 3>; [INV]
so the only thing this achieved is leaving a dead load around
in this case.
Anyways, easy to fix.