This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Fix verify_type ICE during Ada bootstrap


On Mon, 30 Nov 2015, Jan Hubicka wrote:

> Hi,
> here is updated patch which bootstraps&regtestes, lto-bootstraps x86_64-linux and
> also works for Firefox. The basic pain is to identify which calls to get_alias_set
> are used to build alias sets themselves and thus must be made -fstrict-aliasing
> independent and which are used to drive queries to oracle and thus should follow
> -fstrict-aliasing.  Fortunately the sanity checking I added seems pretty effective
> to check bugs in this area: either we get ice in tree-streamer-out.c because alias
> set is 0 when it is not expected to be or we get an ice in record_component_aliases
> because alias set of component gets 0.
> 
> OK?

I think you are doing too many things in one patch.  I'm fine with
dropping the zero-alias-set streaming (but I'd rather not assert
as FE get_alias_set langhook may assign zero to random tree nodes).

I'm also fine with handling flag_strict_aliasing conservatively
during inlining - but the condition you placed on this handling
needs a comment.  I couldn't decipher it ;)

> +      if (dump_file)
> +     fprintf (dump_file, "Dropping flag_strict_aliasing on %s:%i\n",
> +              to->name (), to->order);

So I wonder if it makes sense to pessimize such inlining as well.

The two above should be enough to fix the correctness issue.

The parse_optimize_options hack looks indeed interesting, but we solved
the issue differently by

2014-11-27  Richard Biener  <rguenther@suse.de>

        PR middle-end/63704
        * alias.c (mems_in_disjoint_alias_sets_p): Remove assert
        and instead return false when !fstrict-aliasing.

So the hack can be removed as a separate commit after the first one
above.  This should make optimize("fno-strict-aliasing") work.


I don't really see why we need all the other changes and IMHO the
get_alias_set interface change is ugly and fragile.  And this doesn't
look like sth for stage3.

Thus please split the patch up.

Thanks,
Richard.

> Honza
> 
> 	* tree.c (free_lang_data): Pass true to get_alias_set.
> 	* tree-streamer-in.c (unpack_ts_type_common_value_fields): Do not stream
> 	alias set.
> 	* tree-ssa-alias.c (ao_ref_base_alias_set, ao_ref_alias_set): Pass true
> 	to get_alias_set; comment.
> 	(same_type_for_tbaa): Likewise.
> 	* alias.c (alias_set_subset_of, alias_sets_conflict_p): When strict
> 	aliasing is disabled, return true.
> 	(get_alias_set): New parameter strict.
> 	(new_alias_set): Always produce new alias set.
> 	(record_component_aliases): Pass true to get_alias_set.
> 	* alias.h (get_alias_set): New optional parameter STRICT.
> 	* lto-streamer-out.c (hash_tree): Do not hash alias set.
> 	* ipa-inline-transform.c (inline_call): Drop strict aliasing of
> 	caller if needed.
> 	* ipa-icf-gimple.c (func_checker::compatible_types_p): Pass true
> 	to get_alias_set.
> 	* tree-streamer-out.c (pack_ts_type_common_value_fields): Do not
> 	stream TYPE_ALIAS_SET; sanity check that alias set 0 at LTO time will
> 	match what frontneds does.
> 	* fold-const.c (operand_equal_p): Be cureful about TBAA info before
> 	inlining even with -fno-strict-aliasing.
> 	* gimple.c (gimple_get_alias_set): Pass true to get_alias_set.
> 
> 	* misc.c (gnat_get_alias_set): Pass true to get_alias_set.
> 	* utils.c (relate_alias_sets): Likewise.
> 	* trans.c (validate_unchecked_conversion): Likewise.
> 
> 	* lto-symtab.c (warn_type_compatibility_p): Pass true to get_alias_set.
> 	* lto.c (compare_tree_sccs_1): Do not ocmpare TYPE_ALIAS_SET.
> 
> 	* gcc.c-torture/execute/alias-1.c: New testcase.
> 	* gcc.dg/lto/alias-1_0.c: New testcase.
> 	* gcc.dg/lto/alias-1_1.c: New testcase.
> 
> 	* c-common.c (parse_optimize_options): Remove hack about
> 	flag_strict_aliasing.
> 	(convert_vector_to_pointer_for_subscript): Pass true to get_alias_set.
> 
> 	* cp-objcp-common.c (cxx_get_alias_set): Pass true to get_alias_set.
> 	
> 	* rtti.c (typeid_ok_p): Pass true to get_alias_set.
> Index: tree.c
> ===================================================================
> --- tree.c	(revision 231020)
> +++ tree.c	(working copy)
> @@ -5971,7 +5971,8 @@ free_lang_data (void)
>       while the slots are still in the way the frontends generated them.  */
>    for (i = 0; i < itk_none; ++i)
>      if (integer_types[i])
> -      TYPE_ALIAS_SET (integer_types[i]) = get_alias_set (integer_types[i]);
> +      TYPE_ALIAS_SET (integer_types[i]) = get_alias_set (integer_types[i],
> +							 true);
>  
>    /* Traverse the IL resetting language specific information for
>       operands, expressions, etc.  */
> Index: cp/rtti.c
> ===================================================================
> --- cp/rtti.c	(revision 231020)
> +++ cp/rtti.c	(working copy)
> @@ -300,10 +300,10 @@ typeid_ok_p (void)
>    /* Make sure abi::__type_info_pseudo has the same alias set
>       as std::type_info.  */
>    if (! TYPE_ALIAS_SET_KNOWN_P (pseudo_type_info))
> -    TYPE_ALIAS_SET (pseudo_type_info) = get_alias_set (type_info_type);
> +    TYPE_ALIAS_SET (pseudo_type_info) = get_alias_set (type_info_type, true);
>    else
>      gcc_assert (TYPE_ALIAS_SET (pseudo_type_info)
> -		== get_alias_set (type_info_type));
> +		== get_alias_set (type_info_type, true));
>  
>    return true;
>  }
> Index: cp/cp-objcp-common.c
> ===================================================================
> --- cp/cp-objcp-common.c	(revision 231020)
> +++ cp/cp-objcp-common.c	(working copy)
> @@ -32,7 +32,7 @@ cxx_get_alias_set (tree t)
>    if (IS_FAKE_BASE_TYPE (t))
>      /* The base variant of a type must be in the same alias set as the
>         complete type.  */
> -    return get_alias_set (TYPE_CONTEXT (t));
> +    return get_alias_set (TYPE_CONTEXT (t), true);
>  
>    /* Punt on PMFs until we canonicalize functions properly.  */
>    if (TYPE_PTRMEMFUNC_P (t)
> Index: tree-streamer-in.c
> ===================================================================
> --- tree-streamer-in.c	(revision 231020)
> +++ tree-streamer-in.c	(working copy)
> @@ -366,7 +366,6 @@ unpack_ts_type_common_value_fields (stru
>    TYPE_RESTRICT (expr) = (unsigned) bp_unpack_value (bp, 1);
>    TYPE_USER_ALIGN (expr) = (unsigned) bp_unpack_value (bp, 1);
>    TYPE_READONLY (expr) = (unsigned) bp_unpack_value (bp, 1);
> -  TYPE_ALIAS_SET (expr) = bp_unpack_value (bp, 1) ? 0 : -1;
>    if (RECORD_OR_UNION_TYPE_P (expr))
>      {
>        TYPE_TRANSPARENT_AGGR (expr) = (unsigned) bp_unpack_value (bp, 1);
> Index: tree-ssa-alias.c
> ===================================================================
> --- tree-ssa-alias.c	(revision 231020)
> +++ tree-ssa-alias.c	(working copy)
> @@ -563,7 +563,10 @@ ao_ref_base_alias_set (ao_ref *ref)
>    base_ref = ref->ref;
>    while (handled_component_p (base_ref))
>      base_ref = TREE_OPERAND (base_ref, 0);
> -  ref->base_alias_set = get_alias_set (base_ref);
> +  /* Do not return 0 in case of strict aliasing; this function is used at
> +     IPA level by ipa-icf-gimple.c.  It is job of caller to give up on
> +     using TBAA oracle when asked to not do so.  */
> +  ref->base_alias_set = get_alias_set (base_ref, true);
>    return ref->base_alias_set;
>  }
>  
> @@ -574,7 +577,10 @@ ao_ref_alias_set (ao_ref *ref)
>  {
>    if (ref->ref_alias_set != -1)
>      return ref->ref_alias_set;
> -  ref->ref_alias_set = get_alias_set (ref->ref);
> +  /* Do not return 0 in case of strict aliasing; this function is used at
> +     IPA level by ipa-icf-gimple.c.  It is job of caller to give up on
> +     using TBAA oracle when asked to not do so.  */
> +  ref->ref_alias_set = get_alias_set (ref->ref, true);
>    return ref->ref_alias_set;
>  }
>  
> @@ -668,7 +674,7 @@ same_type_for_tbaa (tree type1, tree typ
>       would mean that conversions between them are useless, whereas they are
>       not (e.g. type and subtypes can have different modes).  So, in the end,
>       they are only guaranteed to have the same alias set.  */
> -  if (get_alias_set (type1) == get_alias_set (type2))
> +  if (get_alias_set (type1, true) == get_alias_set (type2, true))
>      return -1;
>  
>    /* The types are known to be not equal.  */
> Index: alias.c
> ===================================================================
> --- alias.c	(revision 231020)
> +++ alias.c	(working copy)
> @@ -406,7 +406,7 @@ alias_set_subset_of (alias_set_type set1
>    alias_set_entry *ase2;
>  
>    /* Everything is a subset of the "aliases everything" set.  */
> -  if (set2 == 0)
> +  if (set2 == 0 || !flag_strict_aliasing)
>      return true;
>  
>    /* Check if set1 is a subset of set2.  */
> @@ -467,7 +467,7 @@ alias_sets_conflict_p (alias_set_type se
>    alias_set_entry *ase2;
>  
>    /* The easy case.  */
> -  if (alias_sets_must_conflict_p (set1, set2))
> +  if (!flag_strict_aliasing || alias_sets_must_conflict_p (set1, set2))
>      return 1;
>  
>    /* See if the first alias set is a subset of the second.  */
> @@ -809,17 +809,21 @@ init_alias_set_entry (alias_set_type set
>  }
>  
>  /* Return the alias set for T, which may be either a type or an
> -   expression.  Call language-specific routine for help, if needed.  */
> +   expression.  Call language-specific routine for help, if needed.
> +   If STRICT is true, ignore value of flag_strict_aliasing.  This is needed
> +   in cases we are in -fno-strict-aliasing region but still need to compute
> +   alias sets for some reason (this is used, for example, by rtti code to copy
> +   alias set from type to type).  */
>  
>  alias_set_type
> -get_alias_set (tree t)
> +get_alias_set (tree t, bool strict)
>  {
>    alias_set_type set;
>  
>    /* If we're not doing any alias analysis, just assume everything
>       aliases everything else.  Also return 0 if this or its type is
>       an error.  */
> -  if (! flag_strict_aliasing || t == error_mark_node
> +  if ((! flag_strict_aliasing && !strict)|| t == error_mark_node
>        || (! TYPE_P (t)
>  	  && (TREE_TYPE (t) == 0 || TREE_TYPE (t) == error_mark_node)))
>      return 0;
> @@ -898,7 +902,7 @@ get_alias_set (tree t)
>        /* For arrays with unknown size the conservative answer is the
>  	 alias set of the element type.  */
>        if (TREE_CODE (t) == ARRAY_TYPE)
> -	return get_alias_set (TREE_TYPE (t));
> +	return get_alias_set (TREE_TYPE (t), true);
>  
>        /* But return zero as a conservative answer for incomplete types.  */
>        return 0;
> @@ -920,7 +924,7 @@ get_alias_set (tree t)
>       normal usage.  And indeed lets vectors be treated more like an
>       array slice.  */
>    else if (TREE_CODE (t) == VECTOR_TYPE)
> -    set = get_alias_set (TREE_TYPE (t));
> +    set = get_alias_set (TREE_TYPE (t), true);
>  
>    /* Unless the language specifies otherwise, treat array types the
>       same as their components.  This avoids the asymmetry we get
> @@ -933,7 +937,7 @@ get_alias_set (tree t)
>    else if (TREE_CODE (t) == ARRAY_TYPE
>  	   && (!TYPE_NONALIASED_COMPONENT (t)
>  	       || TYPE_STRUCTURAL_EQUALITY_P (t)))
> -    set = get_alias_set (TREE_TYPE (t));
> +    set = get_alias_set (TREE_TYPE (t), true);
>  
>    /* From the former common C and C++ langhook implementation:
>  
> @@ -997,7 +1001,7 @@ get_alias_set (tree t)
>  	 (see record_component_aliases) and thus it is safe it to use it for
>  	 pointers to types with TYPE_STRUCTURAL_EQUALITY_P.  */
>        if (TREE_CODE (p) == VOID_TYPE || TYPE_STRUCTURAL_EQUALITY_P (p))
> -	set = get_alias_set (ptr_type_node);
> +	set = get_alias_set (ptr_type_node, true);
>        else
>  	{
>  	  /* Rebuild pointer type starting from canonical types using
> @@ -1085,15 +1089,10 @@ get_alias_set (tree t)
>  alias_set_type
>  new_alias_set (void)
>  {
> -  if (flag_strict_aliasing)
> -    {
> -      if (alias_sets == 0)
> -	vec_safe_push (alias_sets, (alias_set_entry *) NULL);
> -      vec_safe_push (alias_sets, (alias_set_entry *) NULL);
> -      return alias_sets->length () - 1;
> -    }
> -  else
> -    return 0;
> +  if (alias_sets == 0)
> +    vec_safe_push (alias_sets, (alias_set_entry *) NULL);
> +  vec_safe_push (alias_sets, (alias_set_entry *) NULL);
> +  return alias_sets->length () - 1;
>  }
>  
>  /* Indicate that things in SUBSET can alias things in SUPERSET, but that
> @@ -1169,7 +1168,7 @@ record_alias_subset (alias_set_type supe
>  void
>  record_component_aliases (tree type)
>  {
> -  alias_set_type superset = get_alias_set (type);
> +  alias_set_type superset = get_alias_set (type, true);
>    tree field;
>  
>    if (superset == 0)
> @@ -1215,16 +1214,17 @@ record_component_aliases (tree type)
>  		if (POINTER_TYPE_P (t))
>  		  t = ptr_type_node;
>  		else if (flag_checking)
> -		  gcc_checking_assert (get_alias_set (t)
> -				       == get_alias_set (TREE_TYPE (field)));
> +		  gcc_checking_assert (get_alias_set (t, true)
> +				       == get_alias_set (TREE_TYPE (field),
> +							 true));
>  	      }
>  
> -	    record_alias_subset (superset, get_alias_set (t));
> +	    record_alias_subset (superset, get_alias_set (t, true));
>  	  }
>        break;
>  
>      case COMPLEX_TYPE:
> -      record_alias_subset (superset, get_alias_set (TREE_TYPE (type)));
> +      record_alias_subset (superset, get_alias_set (TREE_TYPE (type), true));
>        break;
>  
>      /* VECTOR_TYPE and ARRAY_TYPE share the alias set with their
> Index: alias.h
> ===================================================================
> --- alias.h	(revision 231020)
> +++ alias.h	(working copy)
> @@ -21,7 +21,7 @@ along with GCC; see the file COPYING3.
>  #define GCC_ALIAS_H
>  
>  extern alias_set_type new_alias_set (void);
> -extern alias_set_type get_alias_set (tree);
> +extern alias_set_type get_alias_set (tree, bool strict = false);
>  extern alias_set_type get_deref_alias_set (tree);
>  extern alias_set_type get_varargs_alias_set (void);
>  extern alias_set_type get_frame_alias_set (void);
> Index: lto/lto-symtab.c
> ===================================================================
> --- lto/lto-symtab.c	(revision 231020)
> +++ lto/lto-symtab.c	(working copy)
> @@ -276,8 +276,8 @@ warn_type_compatibility_p (tree prevaili
>       we make ptr_type_node to TBAA compatible with every other type.  */
>    if (type_with_alias_set_p (type) && type_with_alias_set_p (prevailing_type))
>      {
> -      alias_set_type set1 = get_alias_set (type);
> -      alias_set_type set2 = get_alias_set (prevailing_type);
> +      alias_set_type set1 = get_alias_set (type, true);
> +      alias_set_type set2 = get_alias_set (prevailing_type, true);
>  
>        if (set1 && set2 && set1 != set2 
>            && (!POINTER_TYPE_P (type) || !POINTER_TYPE_P (prevailing_type)
> Index: lto/lto.c
> ===================================================================
> --- lto/lto.c	(revision 231020)
> +++ lto/lto.c	(working copy)
> @@ -1166,7 +1166,9 @@ compare_tree_sccs_1 (tree t1, tree t2, t
>        compare_values (TYPE_READONLY);
>        compare_values (TYPE_PRECISION);
>        compare_values (TYPE_ALIGN);
> -      compare_values (TYPE_ALIAS_SET);
> +      /* Do not compare TYPE_ALIAS_SET.  Doing so introduce ordering issues
> +         with calls to get_alias_set which may initialize it for streamed
> + 	 in types.  */
>      }
>  
>    /* We don't want to compare locations, so there is nothing do compare
> Index: testsuite/gcc.c-torture/execute/alias-1.c
> ===================================================================
> --- testsuite/gcc.c-torture/execute/alias-1.c	(revision 0)
> +++ testsuite/gcc.c-torture/execute/alias-1.c	(revision 0)
> @@ -0,0 +1,19 @@
> +int val;
> +
> +int *ptr = &val;
> +float *ptr2 = &val;
> +
> +__attribute__((optimize ("-fno-strict-aliasing")))
> +typepun ()
> +{
> +  *ptr2=0;
> +}
> +
> +main()
> +{
> +  *ptr=1;
> +  typepun ();
> +  if (*ptr)
> +    __builtin_abort ();
> +}
> +
> Index: testsuite/gcc.dg/lto/alias-1_0.c
> ===================================================================
> --- testsuite/gcc.dg/lto/alias-1_0.c	(revision 0)
> +++ testsuite/gcc.dg/lto/alias-1_0.c	(revision 0)
> @@ -0,0 +1,22 @@
> +/* { dg-lto-do run } */
> +/* { dg-lto-options { { -O2 -flto } } } */
> +int val;
> +
> +int *ptr = &val;
> +float *ptr2 = &val;
> +
> +extern void typefun(void);
> +
> +void link_error (void);
> +
> +int
> +main()
> +{ 
> +  *ptr=1;
> +  typefun ();
> +  if (*ptr)
> +    /*link_error ();*/
> +    __builtin_abort ();
> +  return 0;
> +}
> +
> Index: testsuite/gcc.dg/lto/alias-1_1.c
> ===================================================================
> --- testsuite/gcc.dg/lto/alias-1_1.c	(revision 0)
> +++ testsuite/gcc.dg/lto/alias-1_1.c	(revision 0)
> @@ -0,0 +1,8 @@
> +/* { dg-options "-fno-strict-aliasing" } */
> +extern float *ptr2;
> +void
> +__attribute__((optimize ("-fno-strict-aliasing")))
> +typefun ()
> +{ 
> +  *ptr2=0;
> +}
> Index: c-family/c-common.c
> ===================================================================
> --- c-family/c-common.c	(revision 231048)
> +++ c-family/c-common.c	(working copy)
> @@ -9988,7 +9988,6 @@ parse_optimize_options (tree args, bool
>    bool ret = true;
>    unsigned opt_argc;
>    unsigned i;
> -  int saved_flag_strict_aliasing;
>    const char **opt_argv;
>    struct cl_decoded_option *decoded_options;
>    unsigned int decoded_options_count;
> @@ -10081,8 +10080,6 @@ parse_optimize_options (tree args, bool
>    for (i = 1; i < opt_argc; i++)
>      opt_argv[i] = (*optimize_args)[i];
>  
> -  saved_flag_strict_aliasing = flag_strict_aliasing;
> -
>    /* Now parse the options.  */
>    decode_cmdline_options_to_array_default_mask (opt_argc, opt_argv,
>  						&decoded_options,
> @@ -10093,9 +10090,6 @@ parse_optimize_options (tree args, bool
>  
>    targetm.override_options_after_change();
>  
> -  /* Don't allow changing -fstrict-aliasing.  */
> -  flag_strict_aliasing = saved_flag_strict_aliasing;
> -
>    optimize_args->truncate (0);
>    return ret;
>  }
> @@ -12930,8 +12924,8 @@ convert_vector_to_pointer_for_subscript
>  	  /* If the original vector isn't declared may_alias and it
>  	     isn't a bare vector look if the subscripting would
>  	     alias the vector we subscript, and if not, force ref-all.  */
> -	  alias_set_type vecset = get_alias_set (*vecp);
> -	  alias_set_type sset = get_alias_set (type);
> +	  alias_set_type vecset = get_alias_set (*vecp, true);
> +	  alias_set_type sset = get_alias_set (type, true);
>  	  if (!alias_sets_must_conflict_p (sset, vecset)
>  	      && !alias_set_subset_of (sset, vecset))
>  	    ref_all = true;
> Index: lto-streamer-out.c
> ===================================================================
> --- lto-streamer-out.c	(revision 231020)
> +++ lto-streamer-out.c	(working copy)
> @@ -1109,10 +1109,6 @@ hash_tree (struct streamer_tree_cache_d
>        hstate.commit_flag ();
>        hstate.add_int (TYPE_PRECISION (t));
>        hstate.add_int (TYPE_ALIGN (t));
> -      hstate.add_int ((TYPE_ALIAS_SET (t) == 0
> -					 || (!in_lto_p
> -					     && get_alias_set (t) == 0))
> -					? 0 : -1);
>      }
>  
>    if (CODE_CONTAINS_STRUCT (code, TS_TRANSLATION_UNIT_DECL))
> Index: ipa-inline-transform.c
> ===================================================================
> --- ipa-inline-transform.c	(revision 231020)
> +++ ipa-inline-transform.c	(working copy)
> @@ -322,6 +322,23 @@ inline_call (struct cgraph_edge *e, bool
>    if (DECL_FUNCTION_PERSONALITY (callee->decl))
>      DECL_FUNCTION_PERSONALITY (to->decl)
>        = DECL_FUNCTION_PERSONALITY (callee->decl);
> +  if (!opt_for_fn (callee->decl, flag_strict_aliasing)
> +      && opt_for_fn (to->decl, flag_strict_aliasing)
> +      && (!callee->merged
> +	  || lookup_attribute ("optimization", DECL_ATTRIBUTES (e->caller->decl))
> +	  || lookup_attribute ("optimization", DECL_ATTRIBUTES (callee->decl))))
> +    {
> +      struct gcc_options opts = global_options;
> +      cl_optimization_restore (&opts,
> +	 TREE_OPTIMIZATION (DECL_FUNCTION_SPECIFIC_OPTIMIZATION (to->decl)));
> +      opts.x_flag_strict_aliasing = false;
> +      if (dump_file)
> +	fprintf (dump_file, "Dropping flag_strict_aliasing on %s:%i\n",
> +		 to->name (), to->order);
> +      build_optimization_node (&opts);
> +      DECL_FUNCTION_SPECIFIC_OPTIMIZATION (to->decl)
> +	 = build_optimization_node (&opts);
> +    }
>  
>    /* If aliases are involved, redirect edge to the actual destination and
>       possibly remove the aliases.  */
> Index: ipa-icf-gimple.c
> ===================================================================
> --- ipa-icf-gimple.c	(revision 231020)
> +++ ipa-icf-gimple.c	(working copy)
> @@ -241,7 +241,7 @@ func_checker::compatible_types_p (tree t
>       For time being just avoid calling get_alias_set on types that are not
>       having alias sets defined at all.  */
>    if (type_with_alias_set_p (t1) && type_with_alias_set_p (t2)
> -      && get_alias_set (t1) != get_alias_set (t2))
> +      && get_alias_set (t1, true) != get_alias_set (t2, true))
>      return return_false_with_msg ("alias sets are different");
>  
>    return true;
> Index: tree-streamer-out.c
> ===================================================================
> --- tree-streamer-out.c	(revision 231020)
> +++ tree-streamer-out.c	(working copy)
> @@ -317,13 +321,18 @@ pack_ts_type_common_value_fields (struct
>    bp_pack_value (bp, TYPE_RESTRICT (expr), 1);
>    bp_pack_value (bp, TYPE_USER_ALIGN (expr), 1);
>    bp_pack_value (bp, TYPE_READONLY (expr), 1);
> -  /* Make sure to preserve the fact whether the frontend would assign
> -     alias-set zero to this type.  Do that only for main variants, because
> -     type variants alias sets are never computed.
> -     FIXME:  This does not work for pre-streamed builtin types.  */
> -  bp_pack_value (bp, (TYPE_ALIAS_SET (expr) == 0
> -		      || (!in_lto_p && TYPE_MAIN_VARIANT (expr) == expr
> -			  && get_alias_set (expr) == 0)), 1);
> +  /* We used to stream TYPE_ALIAS_SET == 0 information to let frontends mark
> +     types that are opaque for TBAA.  This however did not work as intended,
> +     becuase TYPE_ALIAS_SET == 0 was regularly lost in type merging.
> +
> +     Instead now double check that all aliaset set 0 types will be alias set
> +     0 in LTO world, too.  */
> +  gcc_checking_assert (!type_with_alias_set_p (expr)
> +		       || !canonical_type_used_p (expr)
> +		       || TYPE_ALIAS_SET (expr) != 0
> +		       || expr == char_type_node
> +		       || expr == signed_char_type_node
> +		       || expr == unsigned_char_type_node);
>    if (RECORD_OR_UNION_TYPE_P (expr))
>      {
>        bp_pack_value (bp, TYPE_TRANSPARENT_AGGR (expr), 1);
> Index: fold-const.c
> ===================================================================
> --- fold-const.c	(revision 231020)
> +++ fold-const.c	(working copy)
> @@ -2987,7 +2987,7 @@ operand_equal_p (const_tree arg0, const_
>  					   flags)))
>  		return 0;
>  	      /* Verify that accesses are TBAA compatible.  */
> -	      if (flag_strict_aliasing
> +	      if ((flag_strict_aliasing || !cfun->after_inlining)
>  		  && (!alias_ptr_types_compatible_p
>  		        (TREE_TYPE (TREE_OPERAND (arg0, 1)),
>  		         TREE_TYPE (TREE_OPERAND (arg1, 1)))
> Index: ada/gcc-interface/misc.c
> ===================================================================
> --- ada/gcc-interface/misc.c	(revision 231020)
> +++ ada/gcc-interface/misc.c	(working copy)
> @@ -592,13 +592,14 @@ gnat_get_alias_set (tree type)
>  {
>    /* If this is a padding type, use the type of the first field.  */
>    if (TYPE_IS_PADDING_P (type))
> -    return get_alias_set (TREE_TYPE (TYPE_FIELDS (type)));
> +    return get_alias_set (TREE_TYPE (TYPE_FIELDS (type)), true);
>  
>    /* If the type is an unconstrained array, use the type of the
>       self-referential array we make.  */
>    else if (TREE_CODE (type) == UNCONSTRAINED_ARRAY_TYPE)
>      return
> -      get_alias_set (TREE_TYPE (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (type)))));
> +      get_alias_set (TREE_TYPE (TREE_TYPE (TYPE_FIELDS (TREE_TYPE (type)))),
> +		     true);
>  
>    /* If the type can alias any other types, return the alias set 0.  */
>    else if (TYPE_P (type) && TYPE_UNIVERSAL_ALIASING_P (type))
> Index: ada/gcc-interface/utils.c
> ===================================================================
> --- ada/gcc-interface/utils.c	(revision 231020)
> +++ ada/gcc-interface/utils.c	(working copy)
> @@ -1520,14 +1520,14 @@ relate_alias_sets (tree gnu_new_type, tr
>  		      && TYPE_NONALIASED_COMPONENT (gnu_new_type)
>  			 != TYPE_NONALIASED_COMPONENT (gnu_old_type)));
>  
> -      TYPE_ALIAS_SET (gnu_new_type) = get_alias_set (gnu_old_type);
> +      TYPE_ALIAS_SET (gnu_new_type) = get_alias_set (gnu_old_type, true);
>        break;
>  
>      case ALIAS_SET_SUBSET:
>      case ALIAS_SET_SUPERSET:
>        {
> -	alias_set_type old_set = get_alias_set (gnu_old_type);
> -	alias_set_type new_set = get_alias_set (gnu_new_type);
> +	alias_set_type old_set = get_alias_set (gnu_old_type, true);
> +	alias_set_type new_set = get_alias_set (gnu_new_type, true);
>  
>  	/* Do nothing if the alias sets conflict.  This ensures that we
>  	   never call record_alias_subset several times for the same pair
> Index: ada/gcc-interface/trans.c
> ===================================================================
> --- ada/gcc-interface/trans.c	(revision 231020)
> +++ ada/gcc-interface/trans.c	(working copy)
> @@ -9702,11 +9702,13 @@ validate_unchecked_conversion (Node_Id g
>  				   ? TREE_TYPE (gnu_source_type)
>  				   : NULL_TREE;
>        tree gnu_target_desig_type = TREE_TYPE (gnu_target_type);
> -      alias_set_type target_alias_set = get_alias_set (gnu_target_desig_type);
> +      alias_set_type target_alias_set = get_alias_set (gnu_target_desig_type,
> +						       true);
>  
>        if (target_alias_set != 0
>  	  && (!POINTER_TYPE_P (gnu_source_type)
> -	      || !alias_sets_conflict_p (get_alias_set (gnu_source_desig_type),
> +	      || !alias_sets_conflict_p (get_alias_set (gnu_source_desig_type,
> +							true),
>  					 target_alias_set)))
>  	{
>  	  post_error_ne ("?possible aliasing problem for type&",
> @@ -9728,11 +9730,13 @@ validate_unchecked_conversion (Node_Id g
>  	  : NULL_TREE;
>        tree gnu_target_desig_type
>  	= TREE_TYPE (TREE_TYPE (TYPE_FIELDS (gnu_target_type)));
> -      alias_set_type target_alias_set = get_alias_set (gnu_target_desig_type);
> +      alias_set_type target_alias_set = get_alias_set (gnu_target_desig_type,
> +						       true);
>  
>        if (target_alias_set != 0
>  	  && (!TYPE_IS_FAT_POINTER_P (gnu_source_type)
> -	      || !alias_sets_conflict_p (get_alias_set (gnu_source_desig_type),
> +	      || !alias_sets_conflict_p (get_alias_set (gnu_source_desig_type,
> +							true),
>  					 target_alias_set)))
>  	{
>  	  post_error_ne ("?possible aliasing problem for type&",
> Index: gimple.c
> ===================================================================
> --- gimple.c	(revision 231020)
> +++ gimple.c	(working copy)
> @@ -2408,7 +2408,7 @@ gimple_get_alias_set (tree t)
>  
>        /* t1 == t can happen for boolean nodes which are always unsigned.  */
>        if (t1 != t)
> -	return get_alias_set (t1);
> +	return get_alias_set (t1, true);
>      }
>  
>    return -1;
> 
> 

-- 
Richard Biener <rguenther@suse.de>
SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]