[PR c/84293] Unexpected strict-alias warning
authorNathan Sidwell <nathan@acm.org>
Fri, 9 Feb 2018 19:31:10 +0000 (19:31 +0000)
committerNathan Sidwell <nathan@gcc.gnu.org>
Fri, 9 Feb 2018 19:31:10 +0000 (19:31 +0000)
https://gcc.gnu.org/ml/gcc-patches/2018-02/msg00510.html
PR c/84293
gcc/c/
* c-typeck.c (build_indirect_ref, build_c_cast): Pass expr location
to strict_aliasing_warning.

gcc/c-family/
* c-common.h (strict_aliasing_warning): Drop OTYPE arg, insert LOC
arg.
* c-warn.c (strict_aliasing_warning): Drop OTYPE arg, require LOC
arg.  Adjust.

gcc/cp/
* typeck.c (cp_build_indirect_ref_1, build_reinterpret_cast_1):
Pass expr location to strict_aliasing_warning.

gcc/testsuite/
* c-c++-common/pr84293.h: New.
* c-c++-common/pr84293.c: New.

From-SVN: r257539

gcc/c-family/ChangeLog
gcc/c-family/c-common.h
gcc/c-family/c-warn.c
gcc/c/ChangeLog
gcc/c/c-typeck.c
gcc/cp/ChangeLog
gcc/cp/typeck.c
gcc/testsuite/ChangeLog
gcc/testsuite/c-c++-common/pr84293.c [new file with mode: 0644]
gcc/testsuite/c-c++-common/pr84293.h [new file with mode: 0644]

index 2378181..1f536d1 100644 (file)
@@ -1,3 +1,11 @@
+2018-02-09  Nathan Sidwell  <nathan@acm.org>
+
+       PR c/84293
+       * c-common.h (strict_aliasing_warning): Drop OTYPE arg, insert LOC
+       arg.
+       * c-warn.c (strict_aliasing_warning): Drop OTYPE arg, require LOC
+       arg.  Adjust.
+
 2018-02-09  Martin Sebor  <msebor@redhat.com>
 
        PR lto/84212
index 775d468..95bb0fd 100644 (file)
@@ -1260,7 +1260,7 @@ extern void warn_tautological_cmp (location_t, enum tree_code, tree, tree);
 extern void warn_logical_not_parentheses (location_t, enum tree_code, tree,
                                          tree);
 extern bool warn_if_unused_value (const_tree, location_t);
-extern bool strict_aliasing_warning (tree, tree, tree);
+extern bool strict_aliasing_warning (location_t, tree, tree);
 extern void sizeof_pointer_memaccess_warning (location_t *, tree,
                                              vec<tree, va_gc> *, tree *,
                                              bool (*) (tree, tree));
index 7d87c45..f3fb62c 100644 (file)
@@ -599,17 +599,21 @@ warn_if_unused_value (const_tree exp, location_t locus)
     }
 }
 
-/* Print a warning about casts that might indicate violation
-   of strict aliasing rules if -Wstrict-aliasing is used and
-   strict aliasing mode is in effect. OTYPE is the original
-   TREE_TYPE of EXPR, and TYPE the type we're casting to. */
+/* Print a warning about casts that might indicate violation of strict
+   aliasing rules if -Wstrict-aliasing is used and strict aliasing
+   mode is in effect.  LOC is the location of the expression being
+   cast, EXPR might be from inside it.  TYPE is the type we're casting
+   to.  */
 
 bool
-strict_aliasing_warning (tree otype, tree type, tree expr)
+strict_aliasing_warning (location_t loc, tree type, tree expr)
 {
+  if (loc == UNKNOWN_LOCATION)
+    loc = input_location;
+
   /* Strip pointer conversion chains and get to the correct original type.  */
   STRIP_NOPS (expr);
-  otype = TREE_TYPE (expr);
+  tree otype = TREE_TYPE (expr);
 
   if (!(flag_strict_aliasing
        && POINTER_TYPE_P (type)
@@ -628,8 +632,9 @@ strict_aliasing_warning (tree otype, tree type, tree expr)
         if the cast breaks type based aliasing.  */
       if (!COMPLETE_TYPE_P (TREE_TYPE (type)) && warn_strict_aliasing == 2)
        {
-         warning (OPT_Wstrict_aliasing, "type-punning to incomplete type "
-                  "might break strict-aliasing rules");
+         warning_at (loc, OPT_Wstrict_aliasing,
+                     "type-punning to incomplete type "
+                     "might break strict-aliasing rules");
          return true;
        }
       else
@@ -645,15 +650,17 @@ strict_aliasing_warning (tree otype, tree type, tree expr)
              && !alias_set_subset_of (set2, set1)
              && !alias_sets_conflict_p (set1, set2))
            {
-             warning (OPT_Wstrict_aliasing, "dereferencing type-punned "
-                      "pointer will break strict-aliasing rules");
+             warning_at (loc, OPT_Wstrict_aliasing,
+                         "dereferencing type-punned "
+                         "pointer will break strict-aliasing rules");
              return true;
            }
          else if (warn_strict_aliasing == 2
                   && !alias_sets_must_conflict_p (set1, set2))
            {
-             warning (OPT_Wstrict_aliasing, "dereferencing type-punned "
-                      "pointer might break strict-aliasing rules");
+             warning_at (loc, OPT_Wstrict_aliasing,
+                         "dereferencing type-punned "
+                         "pointer might break strict-aliasing rules");
              return true;
            }
        }
@@ -669,8 +676,9 @@ strict_aliasing_warning (tree otype, tree type, tree expr)
       if (!COMPLETE_TYPE_P (type)
          || !alias_sets_must_conflict_p (set1, set2))
        {
-         warning (OPT_Wstrict_aliasing, "dereferencing type-punned "
-                  "pointer might break strict-aliasing rules");
+         warning_at (loc, OPT_Wstrict_aliasing,
+                     "dereferencing type-punned "
+                     "pointer might break strict-aliasing rules");
          return true;
        }
     }
index 97ae43c..bca7268 100644 (file)
@@ -1,3 +1,9 @@
+2018-02-09  Nathan Sidwell  <nathan@acm.org>
+
+       PR c/84293
+       * c-typeck.c (build_indirect_ref, build_c_cast): Pass expr location
+       to strict_aliasing_warning.
+
 2018-02-02  Paolo Carlini  <paolo.carlini@oracle.com>
 
        * c-typeck.c (really_start_incremental_init, push_init_level,
index b35c2c0..1eae4ea 100644 (file)
@@ -2524,7 +2524,7 @@ build_indirect_ref (location_t loc, tree ptr, ref_operator errstring)
             the backend.  This only needs to be done at
             warn_strict_aliasing > 2.  */
          if (warn_strict_aliasing > 2)
-           if (strict_aliasing_warning (TREE_TYPE (TREE_OPERAND (pointer, 0)),
+           if (strict_aliasing_warning (EXPR_LOCATION (pointer),
                                         type, TREE_OPERAND (pointer, 0)))
              TREE_NO_WARNING (pointer) = 1;
        }
@@ -5696,7 +5696,7 @@ build_c_cast (location_t loc, tree type, tree expr)
                    "of different size");
 
       if (warn_strict_aliasing <= 2)
-        strict_aliasing_warning (otype, type, expr);
+        strict_aliasing_warning (EXPR_LOCATION (value), type, expr);
 
       /* If pedantic, warn for conversions between function and object
         pointer types, except for converting a null pointer constant
index fa66e1b..cea51ff 100644 (file)
@@ -1,3 +1,9 @@
+2018-02-09  Nathan Sidwell  <nathan@acm.org>
+
+       PR c/84293
+       * typeck.c (cp_build_indirect_ref_1, build_reinterpret_cast_1):
+       Pass expr location to strict_aliasing_warning.
+
 2018-02-09  Jason Merrill  <jason@redhat.com>
 
        PR c++/84296 - ICE with qualified-id in template.
index fe18ea9..dfcf716 100644 (file)
@@ -3136,7 +3136,7 @@ cp_build_indirect_ref_1 (tree ptr, ref_operator errorstring,
             the backend.  This only needs to be done at
             warn_strict_aliasing > 2.  */
          if (warn_strict_aliasing > 2)
-           if (strict_aliasing_warning (TREE_TYPE (TREE_OPERAND (ptr, 0)),
+           if (strict_aliasing_warning (EXPR_LOCATION (ptr),
                                         type, TREE_OPERAND (ptr, 0)))
              TREE_NO_WARNING (ptr) = 1;
        }
@@ -7334,7 +7334,7 @@ build_reinterpret_cast_1 (tree type, tree expr, bool c_cast_p,
       expr = cp_build_addr_expr (expr, complain);
 
       if (warn_strict_aliasing > 2)
-       strict_aliasing_warning (TREE_TYPE (expr), type, expr);
+       strict_aliasing_warning (EXPR_LOCATION (expr), type, expr);
 
       if (expr != error_mark_node)
        expr = build_reinterpret_cast_1
@@ -7428,8 +7428,6 @@ build_reinterpret_cast_1 (tree type, tree expr, bool c_cast_p,
   else if ((TYPE_PTRDATAMEM_P (type) && TYPE_PTRDATAMEM_P (intype))
           || (TYPE_PTROBV_P (type) && TYPE_PTROBV_P (intype)))
     {
-      tree sexpr = expr;
-
       if (!c_cast_p
          && check_for_casting_away_constness (intype, type,
                                               REINTERPRET_CAST_EXPR,
@@ -7447,11 +7445,9 @@ build_reinterpret_cast_1 (tree type, tree expr, bool c_cast_p,
        warning (OPT_Wcast_align, "cast from %qH to %qI "
                 "increases required alignment of target type", intype, type);
 
-      /* We need to strip nops here, because the front end likes to
-        create (int *)&a for array-to-pointer decay, instead of &a[0].  */
-      STRIP_NOPS (sexpr);
       if (warn_strict_aliasing <= 2)
-       strict_aliasing_warning (intype, type, sexpr);
+       /* strict_aliasing_warning STRIP_NOPs its expr.  */
+       strict_aliasing_warning (EXPR_LOCATION (expr), type, expr);
 
       return build_nop (type, expr);
     }
index 9d80ab8..edafd88 100644 (file)
@@ -1,3 +1,9 @@
+2018-02-09  Nathan Sidwell  <nathan@acm.org>
+
+       PR c/84293
+       * c-c++-common/pr84293.h: New.
+       * c-c++-common/pr84293.c: New.
+
 2018-02-09  Vladimir Makarov  <vmakarov@redhat.com>
 
        PR rtl-optimization/57193
diff --git a/gcc/testsuite/c-c++-common/pr84293.c b/gcc/testsuite/c-c++-common/pr84293.c
new file mode 100644 (file)
index 0000000..dfcc859
--- /dev/null
@@ -0,0 +1,10 @@
+/* PR c/84293 unexpected warning from system header.  */
+#include "./pr84293.h"
+struct typeobject thing;
+
+#pragma GCC diagnostic warning "-Wstrict-aliasing"
+void __attribute__ ((optimize (2))) init ()
+{
+  INCREF_TDEF (&thing);
+  INCREF_STAG (&thing);
+}
diff --git a/gcc/testsuite/c-c++-common/pr84293.h b/gcc/testsuite/c-c++-common/pr84293.h
new file mode 100644 (file)
index 0000000..c129896
--- /dev/null
@@ -0,0 +1,7 @@
+/* PR c/84293 unexpected warning from system header expansion.  */
+#pragma GCC system_header
+struct typeobject { unsigned refs; };
+typedef struct object { unsigned refs; } Object;
+
+#define INCREF_TDEF(op) (((Object*)(op))->refs++)
+#define INCREF_STAG(op) (((struct object*)(op))->refs++)