On Thu, 11 Dec 2014, Marek Polacek wrote:

> On Wed, Dec 10, 2014 at 08:11:02PM +0100, Marc Glisse wrote:
> > >+inline tree
> > >+any_integral_type_check (tree __t, const char *__f, int __l, const char 
> > >*__g)
> > >+{
> > >+  if (!(INTEGRAL_TYPE_P (__t)
> > >+  || ((TREE_CODE (__t) == COMPLEX_TYPE
> > >+       || VECTOR_TYPE_P (__t))
> > >+      && INTEGRAL_TYPE_P (TREE_TYPE (__t)))))
> > >+    tree_check_failed (__t, __f, __l, __g, BOOLEAN_TYPE, ENUMERAL_TYPE,
> > >+                 INTEGER_TYPE, 0);
> > >+  return __t;
> > >+}
> > 
> > Is there a particular reason why you are avoiding ANY_INTEGRAL_TYPE_P in
> > any_integral_type_check?
> 
> No, I'm just blind ;).  Changed in the following, thanks for looking
> into this!
> 
> Bootstrapped/regtested on x86_64-linux, ok for trunk?

Ok.

Thanks,
Richard.

> 2014-12-11  Marek Polacek  <pola...@redhat.com>
> 
>       * fold-const.c (fold_negate_expr): Add ANY_INTEGRAL_TYPE_P check.
>       (extract_muldiv_1): Likewise.
>       (maybe_canonicalize_comparison_1): Likewise.
>       (fold_comparison): Likewise.
>       (tree_binary_nonnegative_warnv_p): Likewise.
>       (tree_binary_nonzero_warnv_p): Likewise.
>       * gimple-ssa-strength-reduction.c (legal_cast_p_1): Likewise.
>       * tree-scalar-evolution.c (simple_iv): Likewise.
>       (scev_const_prop): Likewise.
>       * tree-ssa-loop-niter.c (expand_simple_operations): Likewise.
>       * tree-vect-generic.c (expand_vector_operation): Likewise.
>       * tree.h (ANY_INTEGRAL_TYPE_CHECK): Define.
>       (ANY_INTEGRAL_TYPE_P): Define.
>       (TYPE_OVERFLOW_WRAPS, TYPE_OVERFLOW_UNDEFINED, TYPE_OVERFLOW_TRAPS):
>       Add ANY_INTEGRAL_TYPE_CHECK.
>       (any_integral_type_check): New function.
> 
> diff --git gcc/fold-const.c gcc/fold-const.c
> index 0d947ae..7b68bea 100644
> --- gcc/fold-const.c
> +++ gcc/fold-const.c
> @@ -558,7 +558,8 @@ fold_negate_expr (location_t loc, tree t)
>      case INTEGER_CST:
>        tem = fold_negate_const (t, type);
>        if (TREE_OVERFLOW (tem) == TREE_OVERFLOW (t)
> -       || (!TYPE_OVERFLOW_TRAPS (type)
> +       || (ANY_INTEGRAL_TYPE_P (type)
> +           && !TYPE_OVERFLOW_TRAPS (type)
>             && TYPE_OVERFLOW_WRAPS (type))
>         || (flag_sanitize & SANITIZE_SI_OVERFLOW) == 0)
>       return tem;
> @@ -5951,7 +5952,8 @@ extract_muldiv_1 (tree t, tree c, enum tree_code code, 
> tree wide_type,
>          || EXPRESSION_CLASS_P (op0))
>         /* ... and has wrapping overflow, and its type is smaller
>            than ctype, then we cannot pass through as widening.  */
> -       && ((TYPE_OVERFLOW_WRAPS (TREE_TYPE (op0))
> +       && (((ANY_INTEGRAL_TYPE_P (TREE_TYPE (op0))
> +             && TYPE_OVERFLOW_WRAPS (TREE_TYPE (op0)))
>              && (TYPE_PRECISION (ctype)
>                  > TYPE_PRECISION (TREE_TYPE (op0))))
>             /* ... or this is a truncation (t is narrower than op0),
> @@ -5966,7 +5968,8 @@ extract_muldiv_1 (tree t, tree c, enum tree_code code, 
> tree wide_type,
>             /* ... or has undefined overflow while the converted to
>                type has not, we cannot do the operation in the inner type
>                as that would introduce undefined overflow.  */
> -           || (TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (op0))
> +           || ((ANY_INTEGRAL_TYPE_P (TREE_TYPE (op0))
> +                && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (op0)))
>                 && !TYPE_OVERFLOW_UNDEFINED (type))))
>       break;
>  
> @@ -8497,7 +8500,8 @@ maybe_canonicalize_comparison_1 (location_t loc, enum 
> tree_code code, tree type,
>  
>    /* Match A +- CST code arg1 and CST code arg1.  We can change the
>       first form only if overflow is undefined.  */
> -  if (!((TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))
> +  if (!(((ANY_INTEGRAL_TYPE_P (TREE_TYPE (arg0))
> +       && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0)))
>        /* In principle pointers also have undefined overflow behavior,
>           but that causes problems elsewhere.  */
>        && !POINTER_TYPE_P (TREE_TYPE (arg0))
> @@ -8712,7 +8716,9 @@ fold_comparison (location_t loc, enum tree_code code, 
> tree type,
>  
>    /* Transform comparisons of the form X +- C1 CMP C2 to X CMP C2 -+ C1.  */
>    if ((TREE_CODE (arg0) == PLUS_EXPR || TREE_CODE (arg0) == MINUS_EXPR)
> -      && (equality_code || TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0)))
> +      && (equality_code
> +       || (ANY_INTEGRAL_TYPE_P (TREE_TYPE (arg0))
> +           && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))))
>        && TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST
>        && !TREE_OVERFLOW (TREE_OPERAND (arg0, 1))
>        && TREE_CODE (arg1) == INTEGER_CST
> @@ -9031,7 +9037,8 @@ fold_comparison (location_t loc, enum tree_code code, 
> tree type,
>       X CMP Y +- C2 +- C1 for signed X, Y.  This is valid if
>       the resulting offset is smaller in absolute value than the
>       original one and has the same sign.  */
> -  if (TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))
> +  if (ANY_INTEGRAL_TYPE_P (TREE_TYPE (arg0))
> +      && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))
>        && (TREE_CODE (arg0) == PLUS_EXPR || TREE_CODE (arg0) == MINUS_EXPR)
>        && (TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST
>         && !TREE_OVERFLOW (TREE_OPERAND (arg0, 1)))
> @@ -9085,7 +9092,8 @@ fold_comparison (location_t loc, enum tree_code code, 
> tree type,
>       signed arithmetic case.  That form is created by the compiler
>       often enough for folding it to be of value.  One example is in
>       computing loop trip counts after Operator Strength Reduction.  */
> -  if (TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))
> +  if (ANY_INTEGRAL_TYPE_P (TREE_TYPE (arg0))
> +      && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0))
>        && TREE_CODE (arg0) == MULT_EXPR
>        && (TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST
>            && !TREE_OVERFLOW (TREE_OPERAND (arg0, 1)))
> @@ -14733,7 +14741,8 @@ tree_binary_nonnegative_warnv_p (enum tree_code code, 
> tree type, tree op0,
>             || (tree_expr_nonnegative_warnv_p (op0, strict_overflow_p)
>                 && tree_expr_nonnegative_warnv_p (op1, strict_overflow_p)))
>           {
> -           if (TYPE_OVERFLOW_UNDEFINED (type))
> +           if (ANY_INTEGRAL_TYPE_P (type)
> +               && TYPE_OVERFLOW_UNDEFINED (type))
>               *strict_overflow_p = true;
>             return true;
>           }
> @@ -15205,7 +15214,7 @@ tree_binary_nonzero_warnv_p (enum tree_code code,
>      {
>      case POINTER_PLUS_EXPR:
>      case PLUS_EXPR:
> -      if (TYPE_OVERFLOW_UNDEFINED (type))
> +      if (ANY_INTEGRAL_TYPE_P (type) && TYPE_OVERFLOW_UNDEFINED (type))
>       {
>         /* With the presence of negative values it is hard
>            to say something.  */
> diff --git gcc/gimple-ssa-strength-reduction.c 
> gcc/gimple-ssa-strength-reduction.c
> index 547327c..945075c 100644
> --- gcc/gimple-ssa-strength-reduction.c
> +++ gcc/gimple-ssa-strength-reduction.c
> @@ -1487,8 +1487,8 @@ legal_cast_p_1 (tree lhs, tree rhs)
>    rhs_type = TREE_TYPE (rhs);
>    lhs_size = TYPE_PRECISION (lhs_type);
>    rhs_size = TYPE_PRECISION (rhs_type);
> -  lhs_wraps = TYPE_OVERFLOW_WRAPS (lhs_type);
> -  rhs_wraps = TYPE_OVERFLOW_WRAPS (rhs_type);
> +  lhs_wraps = ANY_INTEGRAL_TYPE_P (lhs_type) && TYPE_OVERFLOW_WRAPS 
> (lhs_type);
> +  rhs_wraps = ANY_INTEGRAL_TYPE_P (rhs_type) && TYPE_OVERFLOW_WRAPS 
> (rhs_type);
>  
>    if (lhs_size < rhs_size
>        || (rhs_wraps && !lhs_wraps)
> diff --git gcc/tree-scalar-evolution.c gcc/tree-scalar-evolution.c
> index 5183cb8..7c69814 100644
> --- gcc/tree-scalar-evolution.c
> +++ gcc/tree-scalar-evolution.c
> @@ -3267,7 +3267,8 @@ simple_iv (struct loop *wrto_loop, struct loop 
> *use_loop, tree op,
>    if (tree_contains_chrecs (iv->base, NULL))
>      return false;
>  
> -  iv->no_overflow = !folded_casts && TYPE_OVERFLOW_UNDEFINED (type);
> +  iv->no_overflow = (!folded_casts && ANY_INTEGRAL_TYPE_P (type)
> +                  && TYPE_OVERFLOW_UNDEFINED (type));
>  
>    return true;
>  }
> @@ -3490,7 +3491,8 @@ scev_const_prop (void)
>         /* If def's type has undefined overflow and there were folded
>            casts, rewrite all stmts added for def into arithmetics
>            with defined overflow behavior.  */
> -       if (folded_casts && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (def)))
> +       if (folded_casts && ANY_INTEGRAL_TYPE_P (TREE_TYPE (def))
> +           && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (def)))
>           {
>             gimple_seq stmts;
>             gimple_stmt_iterator gsi2;
> diff --git gcc/tree-ssa-loop-niter.c gcc/tree-ssa-loop-niter.c
> index d17227f..359d03d 100644
> --- gcc/tree-ssa-loop-niter.c
> +++ gcc/tree-ssa-loop-niter.c
> @@ -1642,7 +1642,8 @@ expand_simple_operations (tree expr)
>  
>      case PLUS_EXPR:
>      case MINUS_EXPR:
> -      if (TYPE_OVERFLOW_TRAPS (TREE_TYPE (expr)))
> +      if (ANY_INTEGRAL_TYPE_P (TREE_TYPE (expr))
> +       && TYPE_OVERFLOW_TRAPS (TREE_TYPE (expr)))
>       return expr;
>        /* Fallthru.  */
>      case POINTER_PLUS_EXPR:
> diff --git gcc/tree-vect-generic.c gcc/tree-vect-generic.c
> index a8a8ecd..de09ff0 100644
> --- gcc/tree-vect-generic.c
> +++ gcc/tree-vect-generic.c
> @@ -926,14 +926,14 @@ expand_vector_operation (gimple_stmt_iterator *gsi, 
> tree type, tree compute_type
>        {
>        case PLUS_EXPR:
>        case MINUS_EXPR:
> -        if (!TYPE_OVERFLOW_TRAPS (type))
> +        if (ANY_INTEGRAL_TYPE_P (type) && !TYPE_OVERFLOW_TRAPS (type))
>         return expand_vector_addition (gsi, do_binop, do_plus_minus, type,
>                                        gimple_assign_rhs1 (assign),
>                                        gimple_assign_rhs2 (assign), code);
>       break;
>  
>        case NEGATE_EXPR:
> -        if (!TYPE_OVERFLOW_TRAPS (type))
> +        if (ANY_INTEGRAL_TYPE_P (type) && !TYPE_OVERFLOW_TRAPS (type))
>            return expand_vector_addition (gsi, do_unop, do_negate, type,
>                                        gimple_assign_rhs1 (assign),
>                                        NULL_TREE, code);
> diff --git gcc/tree.h gcc/tree.h
> index 45214d6..c8a91dd 100644
> --- gcc/tree.h
> +++ gcc/tree.h
> @@ -283,6 +283,10 @@ along with GCC; see the file COPYING3.  If not see
>  #define NON_TYPE_CHECK(T) \
>  (non_type_check ((T), __FILE__, __LINE__, __FUNCTION__))
>  
> +/* These checks have to be special cased.  */
> +#define ANY_INTEGRAL_TYPE_CHECK(T) \
> +(any_integral_type_check ((T), __FILE__, __LINE__, __FUNCTION__))
> +
>  #define TREE_INT_CST_ELT_CHECK(T, I) \
>  (*tree_int_cst_elt_check ((T), (I), __FILE__, __LINE__, __FUNCTION__))
>  
> @@ -388,6 +392,7 @@ extern void omp_clause_range_check_failed (const_tree, 
> const char *, int,
>  #define OMP_CLAUSE_ELT_CHECK(T, i)           ((T)->omp_clause.ops[i])
>  #define OMP_CLAUSE_RANGE_CHECK(T, CODE1, CODE2)      (T)
>  #define OMP_CLAUSE_SUBCODE_CHECK(T, CODE)    (T)
> +#define ANY_INTEGRAL_TYPE_CHECK(T)           (T)
>  
>  #define TREE_CHAIN(NODE) ((NODE)->common.chain)
>  #define TREE_TYPE(NODE) ((NODE)->typed.type)
> @@ -482,6 +487,15 @@ extern void omp_clause_range_check_failed (const_tree, 
> const char *, int,
>     || TREE_CODE (TYPE) == BOOLEAN_TYPE \
>     || TREE_CODE (TYPE) == INTEGER_TYPE)
>  
> +/* Nonzero if TYPE represents an integral type, including complex
> +   and vector integer types.  */
> +
> +#define ANY_INTEGRAL_TYPE_P(TYPE)            \
> +  (INTEGRAL_TYPE_P (TYPE)                    \
> +   || ((TREE_CODE (TYPE) == COMPLEX_TYPE     \
> +        || VECTOR_TYPE_P (TYPE))             \
> +       && INTEGRAL_TYPE_P (TREE_TYPE (TYPE))))
> +
>  /* Nonzero if TYPE represents a non-saturating fixed-point type.  */
>  
>  #define NON_SAT_FIXED_POINT_TYPE_P(TYPE) \
> @@ -771,7 +785,7 @@ extern void omp_clause_range_check_failed (const_tree, 
> const char *, int,
>  /* True if overflow wraps around for the given integral type.  That
>     is, TYPE_MAX + 1 == TYPE_MIN.  */
>  #define TYPE_OVERFLOW_WRAPS(TYPE) \
> -  (TYPE_UNSIGNED (TYPE) || flag_wrapv)
> +  (ANY_INTEGRAL_TYPE_CHECK(TYPE)->base.u.bits.unsigned_flag || flag_wrapv)
>  
>  /* True if overflow is undefined for the given integral type.  We may
>     optimize on the assumption that values in the type never overflow.
> @@ -781,13 +795,14 @@ extern void omp_clause_range_check_failed (const_tree, 
> const char *, int,
>     it will be appropriate to issue the warning immediately, and in
>     other cases it will be appropriate to simply set a flag and let the
>     caller decide whether a warning is appropriate or not.  */
> -#define TYPE_OVERFLOW_UNDEFINED(TYPE) \
> -  (!TYPE_UNSIGNED (TYPE) && !flag_wrapv && !flag_trapv && 
> flag_strict_overflow)
> +#define TYPE_OVERFLOW_UNDEFINED(TYPE)                                \
> +  (!ANY_INTEGRAL_TYPE_CHECK(TYPE)->base.u.bits.unsigned_flag \
> +   && !flag_wrapv && !flag_trapv && flag_strict_overflow)
>  
>  /* True if overflow for the given integral type should issue a
>     trap.  */
>  #define TYPE_OVERFLOW_TRAPS(TYPE) \
> -  (!TYPE_UNSIGNED (TYPE) && flag_trapv)
> +  (!ANY_INTEGRAL_TYPE_CHECK(TYPE)->base.u.bits.unsigned_flag && flag_trapv)
>  
>  /* True if an overflow is to be preserved for sanitization.  */
>  #define TYPE_OVERFLOW_SANITIZED(TYPE)                        \
> @@ -2990,6 +3005,17 @@ omp_clause_elt_check (tree __t, int __i,
>    return &__t->omp_clause.ops[__i];
>  }
>  
> +/* These checks have to be special cased.  */
> +
> +inline tree
> +any_integral_type_check (tree __t, const char *__f, int __l, const char *__g)
> +{
> +  if (!ANY_INTEGRAL_TYPE_P (__t))
> +    tree_check_failed (__t, __f, __l, __g, BOOLEAN_TYPE, ENUMERAL_TYPE,
> +                    INTEGER_TYPE, 0);
> +  return __t;
> +}
> +
>  inline const_tree
>  tree_check (const_tree __t, const char *__f, int __l, const char *__g,
>           tree_code __c)
> @@ -3197,6 +3223,16 @@ omp_clause_elt_check (const_tree __t, int __i,
>    return CONST_CAST (const_tree *, &__t->omp_clause.ops[__i]);
>  }
>  
> +inline const_tree
> +any_integral_type_check (const_tree __t, const char *__f, int __l,
> +                      const char *__g)
> +{
> +  if (!ANY_INTEGRAL_TYPE_P (__t))
> +    tree_check_failed (__t, __f, __l, __g, BOOLEAN_TYPE, ENUMERAL_TYPE,
> +                    INTEGER_TYPE, 0);
> +  return __t;
> +}
> +
>  #endif
>  
>  /* Compute the number of operands in an expression node NODE.  For
> 
>       Marek
> 
> 

-- 
Richard Biener <rguent...@suse.de>
SUSE LINUX GmbH, GF: Jeff Hawn, Jennifer Guild, Felix Imendoerffer, HRB 21284
(AG Nuernberg)
Maxfeldstrasse 5, 90409 Nuernberg, Germany

Reply via email to