Bug 105820 - [13 Regression] ICE in invert, at value-range.cc:1971
Summary: [13 Regression] ICE in invert, at value-range.cc:1971
Status: RESOLVED FIXED
Alias: None
Product: gcc
Classification: Unclassified
Component: tree-optimization (show other bugs)
Version: 13.0
: P3 normal
Target Milestone: 13.0
Assignee: Not yet assigned to anyone
URL:
Keywords: ice-checking, ice-on-valid-code
Depends on:
Blocks:
 
Reported: 2022-06-02 11:10 UTC by Arseny Solokha
Modified: 2022-10-17 13:41 UTC (History)
3 users (show)

See Also:
Host:
Target:
Build:
Known to work:
Known to fail:
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Arseny Solokha 2022-06-02 11:10:34 UTC
g++ 13.0.0 20220529 snapshot (g:58a40e76ebadce78639644cd3d56e42b68336927) ICEs when compiling the following testcase, reduced from gcc/testsuite/gcc.dg/tree-ssa/ssa-vrp-thread-1.c, w/ -O2 -fstrict-enums --param case-values-threshold=1:

typedef int basic_block;

enum gimple_code {};

struct omp_region {
  omp_region *outer;
  basic_block cont;
};

void
oof (void);

void
build_omp_regions_1 (omp_region *parent, basic_block bb, gimple_code code)
{
  if (code == 2)
    parent = parent->outer;
  else if (code != 0)
    parent->cont = bb;

  if (parent)
    oof ();
}

% g++-13.0.0 -O2 -fstrict-enums --param case-values-threshold=1 -c bx6eiilz.c
during GIMPLE pass: threadfull
bx6eiilz.c: In function 'void build_omp_regions_1(omp_region*, basic_block, gimple_code)':
bx6eiilz.c:14:1: internal compiler error: in invert, at value-range.cc:1971
   14 | build_omp_regions_1 (omp_region *parent, basic_block bb, gimple_code code)
      | ^~~~~~~~~~~~~~~~~~~
0x88b323 irange::invert()
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/value-range.cc:1971
0x1f574f2 gimple_outgoing_range::calc_switch_ranges(gswitch*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-edge.cc:148
0x1f57bbd gimple_outgoing_range::get_edge_range(irange&, gimple*, edge_def*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-edge.cc:106
0x1f57ef4 gimple_outgoing_range::edge_range_p(irange&, edge_def*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-edge.cc:212
0x1f61f7f gori_compute::outgoing_edge_range_p(irange&, edge_def*, tree_node*, range_query&)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-gori.cc:1255
0x1f54dc9 ranger_cache::edge_range(irange&, edge_def*, tree_node*, ranger_cache::rfd_mode)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-cache.cc:951
0x1f51ce4 gimple_ranger::range_on_edge(irange&, edge_def*, tree_node*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range.cc:240
0x1372f84 path_range_query::ssa_range_in_phi(irange&, gphi*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-path.cc:323
0x1372a35 path_range_query::range_defined_in_block(irange&, tree_node*, basic_block_def*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-path.cc:350
0x137318b path_range_query::compute_ranges_in_phis(basic_block_def*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-path.cc:393
0x13733d4 path_range_query::compute_ranges_in_block(basic_block_def*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-path.cc:442
0x13739a9 path_range_query::compute_ranges(vec<basic_block_def*, va_heap, vl_ptr> const&, bitmap_head const*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/gimple-range-path.cc:656
0x13f8e10 back_threader::find_taken_edge_cond(vec<basic_block_def*, va_heap, vl_ptr> const&, gcond*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:319
0x13f97ef back_threader::maybe_register_path()
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:232
0x13f9fac back_threader::find_paths_to_names(basic_block_def*, bitmap_head*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:419
0x13fa137 back_threader::resolve_phi(gphi*, bitmap_head*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:396
0x13fa137 back_threader::resolve_phi(gphi*, bitmap_head*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:356
0x13f9ef4 back_threader::find_paths_to_names(basic_block_def*, bitmap_head*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:444
0x13fa30a back_threader::find_paths(basic_block_def*, tree_node*)
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:493
0x13fa541 back_threader::thread_blocks()
	/var/tmp/portage/sys-devel/gcc-13.0.0_p20220529/work/gcc-13-20220529/gcc/tree-ssa-threadbackward.cc:901
Comment 1 Richard Biener 2022-06-02 12:18:57 UTC
#1  0x0000000001ced6a0 in irange::invert (this=0x7fffffff1f30)
    at /space/rguenther/src/gcc/gcc/value-range.cc:2166
2166      gcc_checking_assert (!undefined_p () && !varying_p ());

well, invert(undefined) = varying, invert(varying) = undefined - not sure
why we assert here.

(undefined is another name for 'empty')

I've wondered of several places checking for undefined/varying before
calling .invert () ...
Comment 2 Andrew Macleod 2022-06-02 13:05:30 UTC
Lets see try to remember....

it can be ambiguous.   The inversion of undefined is not necessarily expected to be varying in all circumstances..   Likewise, inverting varying is still varying in some circumstances and data flow. It  depends on how you are using it. 

Thus the onus is put on the caller to check for undefined or varying and do exactly what they expect it to do in their circumstance.  I probably should have documented it at the time.

Also you argued against undefined having a type, so there is no type to invert an undefined to varying with.
Comment 3 Aldy Hernandez 2022-06-03 05:30:35 UTC
Hmmm, all three of us had a conversation on this particular topic.  Initially I had coded it to so that VARYING / UNDEFINED were inverses of each other and y'all convinced me otherwise ;-).  I can't find the conversation though.
Comment 4 Andrew Macleod 2022-06-16 14:00:13 UTC
Well, thats not really the problem here. We are casting
  [irange] gimple_code [2, 2]
to a gimple_code, and getting:
  [irange] gimple_code VARYING

Couple of issues.. one, we shouldnt bother casting anything if the types are already the same...  but still.. the result is incorrect.

Tracing it down, it looks like during the casting process, we call:
operator_cast::inside_domain_p so see if a min == 2, max == 2, is inside the range of    [irange] gimple_code VARYING.

THe routine returns false because with strict enum on, we get the min and max of the domain from:

  wide_int domain_min = wi::to_wide (vrp_val_min (range.type ()));
  wide_int domain_max = wi::to_wide (vrp_val_max (range.type ()));,  which boils 

down to TYPE_MIN_VALUE (gimple_code) and TYPE_MAX_VALUE (gimple_code)

p range.type ()
$29 = (tree_node *) 0x7fffe9f77c78

(gdb) p print_generic_expr (stderr, $29, 0)
gimple_code

(gdb) p print_generic_expr (stderr, $29->type_non_common.minval, 0)
0
 
(gdb) p print_generic_expr (stderr, $29->type_non_common.maxval, 0)
1 

So the min value for the enum is set correctly to 0, but the max is set to 1... 
thus the routine determines that [2, 2] is not within the range of [0, 1] and returns varying..

It seems like the max value for the enum is not being set correctly?

If I check right at the point of the failure:
(gdb) frame 1

#1  0x0000000001c9c4fe in irange::invert (this=0x7fffffff1570) at /home/gcc/master/gcc/gcc/value-range.cc:2185
2185	  gcc_checking_assert (!undefined_p () && !varying_p ());
(gdb) p type()
$42 = (tree_node *) 0x7fffe9f77c78
(gdb) p print_generic_expr (stderr, type(), 0)
gimple_code
(gdb) p print_generic_expr (stderr, type()->type_non_common.maxval, 0)
1
Comment 5 Arseny Solokha 2022-10-17 11:24:13 UTC
I cannot reproduce this ICE w/ the current gcc 13.0.0 20221016 snapshot (g:6366e3e8847af98d4728d55951534769d034d02a).
Comment 6 Martin Liška 2022-10-17 12:14:02 UTC
Fixed with r13-3085-gae56d600d223e996.
Comment 7 Arseny Solokha 2022-10-17 12:38:04 UTC
I believe it won't hurt to add a testcase to the test suite.
Comment 8 Martin Liška 2022-10-17 12:42:59 UTC
(In reply to Arseny Solokha from comment #7)
> I believe it won't hurt to add a testcase to the test suite.

Sure, Aldy can you please do that?
Comment 9 GCC Commits 2022-10-17 13:41:15 UTC
The master branch has been updated by Aldy Hernandez <aldyh@gcc.gnu.org>:

https://gcc.gnu.org/g:01d7d459e433196b1faa4ee025a314266887fc59

commit r13-3336-g01d7d459e433196b1faa4ee025a314266887fc59
Author: Aldy Hernandez <aldyh@redhat.com>
Date:   Mon Oct 17 15:32:35 2022 +0200

    [PR tree-optimization/105820] Add test.
    
            PR tree-optimization/105820
    
    gcc/testsuite/ChangeLog:
    
            * g++.dg/tree-ssa/pr105820.c: New test.