https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109238
Richard Biener <rguenth at gcc dot gnu.org> changed: What |Removed |Added ---------------------------------------------------------------------------- CC| |amacleod at redhat dot com --- Comment #3 from Richard Biener <rguenth at gcc dot gnu.org> --- For the given CFG where dominated_by_p (CDI_DOMINATORS, gimple_bb (use_stmt), gimple_bb (stmt)); and we have <bb 28> [local count: 428124]: c_24 = realloc (p_17, 18446744073709551615); if (c_24 != 0B) goto <bb 29>; [99.96%] else goto <bb 33>; [0.04%] .. on the 28->33 edge intermediate blocks, including a CFG cycle ... <bb 36> [local count: 171]: p_31 = realloc (p_17, 0); but range_of_expr (vr, c_24, use_stmt) doesn't give us [0,0], instead we get VARYING. It looks like we go range_of_stmt of the c_24 def and then m_cache.block_range has a VARYING entry range as well and then we're done. 176 range_of_expr(c_24) at stmt p_31 = realloc (p_17, 0); 177 range_on_entry (c_24) to BB 36 178 range_of_stmt (c_24) at stmt c_24 = realloc (p_17, 18446744073709551615); GLOBAL : UPDATE cache for c_24 in BB 28 : successors : : No updates! TRUE : (178) range_of_stmt (c_24) [irange] unsigned char * VARYING c_24 : CACHE: BB 36 DOM query for c_24, found [irange] unsigned char * VARYING at BB28 179 GORI outgoing_edge for c_24 on edge 28->33 180 GORI compute op 1 (c_24) at if (c_24 != 0B) GORI LHS =[irange] _Bool [0, 0] NONZERO 0x0 GORI Computes c_24 = [irange] unsigned char * [0, 0] NONZERO 0x0 intersect Known range : [irange] unsigned char * VARYING GORI TRUE : (180) produces (c_24) [irange] unsigned char * [0, 0] NONZERO 0x0 GORI TRUE : (179) outgoing_edge (c_24) [irange] unsigned char * [0, 0] NONZERO 0x0 CACHE: BB 32 DOM query for c_24, found [irange] unsigned char * VARYING at BB28 CACHE: Range for DOM returns : [irange] unsigned char * VARYING CACHE: Range for DOM returns : [irange] unsigned char * VARYING Filled from dominator! : [irange] unsigned char * VARYING TRUE : (177) range_on_entry (c_24) [irange] unsigned char * VARYING TRUE : (176) range_of_expr (c_24) [irange] unsigned char * VARYING 181 range_of_expr(c_24) at stmt _27 = p_17 + _26; 182 range_on_entry (c_24) to BB 30 183 range_of_stmt (c_24) at stmt c_24 = realloc (p_17, 18446744073709551615); TRUE : (183) cached (c_24) [irange] unsigned char * VARYING c_24 : CACHE: BB 30 DOM query for c_24, found [irange] unsigned char * VARYING at BB33 CACHE: Range for DOM returns : [irange] unsigned char * VARYING Filled from dominator! : [irange] unsigned char * VARYING TRUE : (182) range_on_entry (c_24) [irange] unsigned char * VARYING ... (not sure where relevant dumps stop). A reduced testcase like the following doesn't exhibit this issue - the range is successfully computed as [0,0] there. So to me this looks like a ranger issue? Andrew? #include <stdlib.h> int do_test(void *p) { unsigned char *c = realloc (p, -1); if (c != 0) abort (); c = p; int ok = 1; for (int i = 0; i < 16; i++) { if (c[i] != 0xff) ok = 0; } if (!ok) abort (); p = realloc (p, 0); if (p != NULL) abort (); return ok; }