[Bug c++/58377] spurious "may be used uninitialized" warning with -Og
davidxl at google dot com
gcc-bugzilla@gcc.gnu.org
Tue Sep 10 20:23:00 GMT 2013
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=58377
--- Comment #9 from davidxl at google dot com ---
(In reply to Richard Biener from comment #5)
> Confirmed with the C++ FE, works with the C FE. Does not warn on trunk (for
> no good reason I think, the reason seems to be presence of loop structure
> and thus some extra BBs).
>
> Difference:
>
> trunk:
>
> [WORKLIST]: add to initial list: out_2 = PHI <out_8(D)(2), out_1(8)>
> [CHECK]: examining phi: out_2 = PHI <out_8(D)(2), out_1(8)>
>
> Use in stmt out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> is guarded by :
> if (pop_first_bucket.2_10 != 0)
>
> [CHECK] Found def edge 0 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
>
> [CHECK] Found def edge 1 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> Operand defs of phi out_2 = PHI <out_8(D)(2), out_1(8)>
> is guarded by :
> if (out_12 != 0)
> [CHECK]: Found unguarded use: out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> [WORKLIST]: Update worklist with phi: out_1 = PHI <out_12(4), out_12(5),
> out_2(3)>
> [CHECK]: examining phi: out_1 = PHI <out_12(4), out_12(5), out_2(3)>
>
> Use in stmt out_2 = PHI <out_8(D)(2), out_1(8)>
> is guarded by :
> (.NOT.) if (iftmp.1_3 != 0)
>
> [CHECK] Found def edge 0 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
>
> [CHECK] Found def edge 1 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> Operand defs of phi out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> is guarded by :
> if (pop_first_bucket.2_10 != 0)
> (.AND.)
> if (out_12 != 0)
> (.OR.)
> if (pop_first_bucket.2_10 != 0)
> (.AND.)
> (.NOT.) if (out_12 != 0)
>
> Normalized to
> Operand defs of phi out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> is guarded by :
> if (pop_first_bucket.2_10 != 0)
> ...
>
> vs. 4.8 branch:
>
> [WORKLIST]: add to initial list: out_2 = PHI <out_8(D)(2), out_1(6)>
> [CHECK]: examining phi: out_2 = PHI <out_8(D)(2), out_1(6)>
>
> Use in stmt out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> is guarded by :
> if (pop_first_bucket.2_10 != 0)
>
> [CHECK] Found def edge 0 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
>
> [CHECK] Found def edge 1 in out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> Operand defs of phi out_2 = PHI <out_8(D)(2), out_1(6)>
> is guarded by :
> if (out_12 != 0)
> [CHECK]: Found unguarded use: out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> [WORKLIST]: Update worklist with phi: out_1 = PHI <out_12(4), out_12(5),
> out_2(3)>
> [CHECK]: examining phi: out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> [CHECK]: Found unguarded use: out_2 = PHI <out_8(D)(2), out_1(6)>
> [CHECK]: Found unguarded use: _4 = PHI <out_1(6), 0(7)>
> [WORKLIST]: Update worklist with phi: _4 = PHI <out_1(6), 0(7)>
> [CHECK]: examining phi: _4 = PHI <out_1(6), 0(7)>
> [CHECK]: Found unguarded use: return _4;
>
> The IL difference is that we have
>
> <bb 6>:
> # out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> # iftmp.1_3 = PHI <1(4), 0(5), 0(3)>
> if (iftmp.1_3 != 0)
> goto <bb 7>;
> else
> goto <bb 8>;
>
> <bb 7>:
> out_13 = out_1;
> goto <bb 10>;
> ...
> <bb 10>:
> # _4 = PHI <out_13(7), 0(9)>
> return _4;
>
> which doesn't warn vs.
>
> <bb 6>:
> # out_1 = PHI <out_12(4), out_12(5), out_2(3)>
> # iftmp.1_3 = PHI <1(4), 0(5), 0(3)>
> if (iftmp.1_3 != 0)
> goto <bb 8>;
> else
> goto <bb 7>;
> ...
> <bb 8>:
> # _4 = PHI <out_1(6), 0(7)>
> return _4;
>
> which does. The issue seems to be that the analysis doesn't consider
> the PHI uses in
>
> if (iftmp.1_3 != 0)
> goto <bb 8>;
> else
> goto <bb 7>;
>
> <bb 7>:
> # out_2 = PHI <out_8(D)(2), out_1(6)>
>
> guarded by anything (the out_1 use is guarded by iftmp.1_3 == 0).
>
> David - the code does
>
> if (gimple_code (use_stmt) == GIMPLE_PHI)
> use_bb = gimple_phi_arg_edge (use_stmt,
> PHI_ARG_INDEX_FROM_USE (use_p))->src;
> else
> use_bb = gimple_bb (use_stmt);
>
> if (is_use_properly_guarded (use_stmt,
> use_bb,
> ...
>
> so it chooses the source block (as approximation?).
>
> Splitting all edges results in us no longer warning here and:
>
> Use in stmt out_2 = PHI <out_8(D)(15), out_1(16)>
> is guarded by :
> (.NOT.) if (iftmp.1_3 != 0)
>
> Can you see to fix that please? Thanks.
Your analysis is correct -- the use is indeed guarded. I forgot why I chose to
use the phi arg's source BB. Will take a look.
David
More information about the Gcc-bugs
mailing list