https://gcc.gnu.org/bugzilla/show_bug.cgi?id=98282

Jakub Jelinek <jakub at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |rguenth at gcc dot gnu.org

--- Comment #5 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
So, the ICE is because compute_avail gets called twice on VIEW_CONVERT_EXPR
from NULL to decltype(nullptr):
stmt:
_7 = VIEW_CONVERT_EXPR<<<< Unknown tree: nullptr_type >>>>(0B);
rhs1:
 <view_convert_expr 0x7fffe9ddd0e0
    type <nullptr_type 0x7fffea1a3c78 decltype(nullptr) unsigned type_6 DI
        size <integer_cst 0x7fffea041eb8 constant 64>
        unit-size <integer_cst 0x7fffea041ed0 constant 8>
        align:64 warn_if_not_align:0 symtab:0 alias-set 14 canonical-type
0x7fffea1a3c78
        pointer_to_this <pointer_type 0x7fffea21db28> reference_to_this
<reference_type 0x7fffea1eb738>>
    constant
    arg:0 <integer_cst 0x7fffea1b0b28 type <pointer_type 0x7fffea1c3a80>
constant 0>
    pr98282.ii:19:13 start: pr98282.ii:19:13 finish: pr98282.ii:19:16>
TREE_TYPE (TREE_OPERAND (rhs1, 0)):
 <pointer_type 0x7fffea1c3a80
    type <integer_type 0x7fffea1c35e8 l sizes-gimplified type_6 SI
        size <integer_cst 0x7fffea062108 constant 32>
        unit-size <integer_cst 0x7fffea062120 constant 4>
        align:32 warn_if_not_align:0 symtab:0 alias-set -1 canonical-type
0x7fffea05f5e8 precision:32 min <integer_cst 0x7fffea0620c0 -2147483648> max
<integer_cst 0x7fffea0620d8 2147483647>
        pointer_to_this <pointer_type 0x7fffea1c3a80>>
    public unsigned DI
    size <integer_cst 0x7fffea041eb8 type <integer_type 0x7fffea05f0a8
bitsizetype> constant 64>
    unit-size <integer_cst 0x7fffea041ed0 type <integer_type 0x7fffea05f000
sizetype> constant 8>
    align:64 warn_if_not_align:0 symtab:0 alias-set -1 canonical-type
0x7fffea0679d8>
TYPE_CANONICAL (TREE_TYPE (TREE_OPERAND (rhs1, 0))):
 <pointer_type 0x7fffea0679d8
    type <integer_type 0x7fffea05f5e8 int sizes-gimplified public type_6 SI
        size <integer_cst 0x7fffea062108 constant 32>
        unit-size <integer_cst 0x7fffea062120 constant 4>
        align:32 warn_if_not_align:0 symtab:0 alias-set 10 canonical-type
0x7fffea05f5e8 precision:32 min <integer_cst 0x7fffea0620c0 -2147483648> max
<integer_cst 0x7fffea0620d8 2147483647>
        pointer_to_this <pointer_type 0x7fffea0679d8>>
    unsigned DI
    size <integer_cst 0x7fffea041eb8 type <integer_type 0x7fffea05f0a8
bitsizetype> constant 64>
    unit-size <integer_cst 0x7fffea041ed0 type <integer_type 0x7fffea05f000
sizetype> constant 8>
    align:64 warn_if_not_align:0 symtab:0 alias-set 4 canonical-type
0x7fffea0679d8>
The alias-set 4 above means get_alias_set on the VCE returns 4.

Second case:
stmt:
_8 = VIEW_CONVERT_EXPR<<<< Unknown tree: nullptr_type >>>>(0B);
rhs1:
 <view_convert_expr 0x7fffe9ddd120
    type <nullptr_type 0x7fffea1a3c78 decltype(nullptr) unsigned type_6 DI
        size <integer_cst 0x7fffea041eb8 constant 64>
        unit-size <integer_cst 0x7fffea041ed0 constant 8>
        align:64 warn_if_not_align:0 symtab:0 alias-set 14 canonical-type
0x7fffea1a3c78
        pointer_to_this <pointer_type 0x7fffea21db28> reference_to_this
<reference_type 0x7fffea1eb738>>
    constant
    arg:0 <integer_cst 0x7fffea1b09f0 type <pointer_type 0x7fffea1bf0a8 i>
constant 0>
    pr98282.ii:15:15 start: pr98282.ii:15:15 finish: pr98282.ii:15:15>
TREE_TYPE (TREE_OPERAND (rhs1, 0)):
 <pointer_type 0x7fffea1bf0a8 i
    type <record_type 0x7fffea1b5dc8 h sizes-gimplified addressable
needs-constructing cxx-odr-p type_5 type_6 BLK
        size <integer_cst 0x7fffea1d35b8 constant 96>
        unit-size <integer_cst 0x7fffea1d35d0 constant 12>
        align:32 warn_if_not_align:0 symtab:0 alias-set 17 canonical-type
0x7fffea1b5dc8
        fields <function_decl 0x7fffea213800 operator= type <method_type
0x7fffea212d20>
            addressable used nothrow public static weak autoinline decl_3
decl_5 QI defer-output pr98282.ii:60:8 align:16 warn_if_not_align:0 context
<record_type 0x7fffea1b5dc8 h> initial <block 0x7fffea1e3600> result
<result_decl 0x7fffea1fa438 D.3000>
            full-name "h& h::operator=(h&&)" chain <function_decl
0x7fffea213700 operator=>> context <translation_unit_decl 0x7fffea04e168
pr98282.ii>
        full-name "struct h"
        needs-constructor X() X(constX&) this=(X&) n_parents=0 use_template=0
interface-unknown
        pointer_to_this <pointer_type 0x7fffea1bf000> reference_to_this
<reference_type 0x7fffea2120a8> chain <type_decl 0x7fffea1be000 h>>
    public unsigned DI
    size <integer_cst 0x7fffea041eb8 type <integer_type 0x7fffea05f0a8
bitsizetype> constant 64>
    unit-size <integer_cst 0x7fffea041ed0 type <integer_type 0x7fffea05f000
sizetype> constant 8>
    align:64 warn_if_not_align:0 symtab:0 alias-set -1 canonical-type
0x7fffea1bf000>
TYPE_CANONICAL (TREE_TYPE (TREE_OPERAND (rhs1, 0))):
 <pointer_type 0x7fffea1bf000
    type <record_type 0x7fffea1b5dc8 h sizes-gimplified addressable
needs-constructing cxx-odr-p type_5 type_6 BLK
        size <integer_cst 0x7fffea1d35b8 constant 96>
        unit-size <integer_cst 0x7fffea1d35d0 constant 12>
        align:32 warn_if_not_align:0 symtab:0 alias-set 17 canonical-type
0x7fffea1b5dc8
        fields <function_decl 0x7fffea213800 operator= type <method_type
0x7fffea212d20>
            addressable used nothrow public static weak autoinline decl_3
decl_5 QI defer-output pr98282.ii:60:8 align:16 warn_if_not_align:0 context
<record_type 0x7fffea1b5dc8 h> initial <block 0x7fffea1e3600> result
<result_decl 0x7fffea1fa438 D.3000>
            full-name "h& h::operator=(h&&)" chain <function_decl
0x7fffea213700 operator=>> context <translation_unit_decl 0x7fffea04e168
pr98282.ii>
        full-name "struct h"
        needs-constructor X() X(constX&) this=(X&) n_parents=0 use_template=0
interface-unknown
        pointer_to_this <pointer_type 0x7fffea1bf000> reference_to_this
<reference_type 0x7fffea2120a8> chain <type_decl 0x7fffea1be000 h>>
    public unsigned type_6 DI
    size <integer_cst 0x7fffea041eb8 type <integer_type 0x7fffea05f0a8
bitsizetype> constant 64>
    unit-size <integer_cst 0x7fffea041ed0 type <integer_type 0x7fffea05f000
sizetype> constant 8>
    align:64 warn_if_not_align:0 symtab:0 alias-set 1 canonical-type
0x7fffea1bf000>

And the alias-set 1 means get_alias_set on the second VCE returns 1.

I think at least for the VCE of constant case (but VCE of SSA_NAME etc. would
as well) we shouldn't consider alias set at all.

So, one possible fix is:
--- gcc/tree-ssa-pre.c.jj       2020-11-30 10:48:31.000000000 +0100
+++ gcc/tree-ssa-pre.c  2020-12-15 10:51:51.061206572 +0100
@@ -4176,13 +4176,17 @@ compute_avail (void)
                             && ref2->opcode != MEM_REF
                             && ref2 != &operands[0])
                        --ref2;
-                     if ((ref1->opcode == TARGET_MEM_REF
-                          || ref1->opcode == MEM_REF)
-                         && (TYPE_ALIGN (ref1->type)
-                             > TYPE_ALIGN (ref2->type)))
-                       ref1->type
-                         = build_aligned_type (ref1->type,
-                                               TYPE_ALIGN (ref2->type));
+                     if (ref1->opcode == TARGET_MEM_REF
+                         || ref1->opcode == MEM_REF)
+                       {
+                         if (TYPE_ALIGN (ref1->type)
+                             > TYPE_ALIGN (ref2->type))
+                           ref1->type
+                             = build_aligned_type (ref1->type,
+                                                   TYPE_ALIGN (ref2->type));
+                       }
+                     else
+                       set = ref->set;
                      /* TBAA behavior is an obvious part so make sure
                         that the hashtable one covers this as well
                         by adjusting the ref alias set and its base.  */
i.e. ignore the alias set if there is no MEM_REF or TARGET_MEM_REF, after all,
the code below it relies on the alias sets to be equal except for MEM_REF or
TARGET_MEM_REF.

Another possibility would be for ao_ref_alias_set and ao_ref_base_alias_set to
return 0 if they aren't really memory reads, such as VCE of constant or VCE of
a SSA_NAME.

And yet another would be not to call ao_ref_alias_set at all in the
compute_avail code for such references, but do something different.

Reply via email to