The following avoids a diagnostic difference between -g0 and -g2 related
to artificial variables created by SRA.

This causes

+FAIL: gfortran.dg/goacc/modules.f95   -O   at line 22 (test for warnings, 
line 
20)
+XPASS: gfortran.dg/goacc/modules.f95   -O  TODO at line 21 (test for 
bogus mess
ages, line 20)

That's

!$ACC DATA PRESENT(arr) COPY(sum)
!$ACC PARALLEL LOOP REDUCTION(+ : sum)
  ! { dg-bogus {'sum\.[0-9]+' is used uninitialized} TODO { xfail *-*-* } 
.-1 }
  !   { dg-note {'sum\.[0-9]+' was declared here} {} { target *-*-* } .-2 
}
  DO k=y_min,y_max

and a whole load of similar fallout in libgomp.oacc-fortran.  It
probably does not fix whatever issue is present there (but it avoids
the diagnostic).  I've refrained from updating the testcases but
will happily do if the patch is approved.

Otherwise bootstrapped and tested on x86_64-unknown-linux-gnu.

OK with the goacc testcases adjusted?  OK to simply remove the
dg-note line or should I XFAIL it?

Thanks,
Richard.

        PR tree-optimization/123651
        * tree-ssa-uninit.cc (warn_uninit): Treat DECL_ARTIFICIAL
        var as if it were not present.

        * g++.dg/warn/Wuninitialized-pr123651.C: New testcase.
---
 .../g++.dg/warn/Wuninitialized-pr123651.C     | 29 +++++++++++++++++++
 gcc/tree-ssa-uninit.cc                        | 17 +++++++++--
 2 files changed, 43 insertions(+), 3 deletions(-)
 create mode 100644 gcc/testsuite/g++.dg/warn/Wuninitialized-pr123651.C

diff --git a/gcc/testsuite/g++.dg/warn/Wuninitialized-pr123651.C 
b/gcc/testsuite/g++.dg/warn/Wuninitialized-pr123651.C
new file mode 100644
index 00000000000..603009a475b
--- /dev/null
+++ b/gcc/testsuite/g++.dg/warn/Wuninitialized-pr123651.C
@@ -0,0 +1,29 @@
+// { dg-do compile }
+// { dg-options "-O2 -g -Wuninitialized" }
+
+void use(int *);
+
+struct Count {
+    int *p;
+    // We emitted the diagnostic only with -g and for an artificial
+    // SR.5 variable which would be not so useful in case of a call
+    // with multiple arguments.
+    // So an XFAILed expected diagnostic for the member 'p' would be
+    // what's truly wanted.
+    ~Count() { use(p); } // { dg-bogus "uninitialized" }
+    Count(Count &) {}
+};
+
+struct Ptr {
+    int x;
+    Count c;
+};
+
+void sink(int, Ptr) {}
+
+struct Holder {
+    template <typename T> void put(T v) { sink(v, ref_); }
+    Ptr ref_;
+};
+
+void test(Holder h) { h.put(0); }
diff --git a/gcc/tree-ssa-uninit.cc b/gcc/tree-ssa-uninit.cc
index 284445b20f8..54517ffc116 100644
--- a/gcc/tree-ssa-uninit.cc
+++ b/gcc/tree-ssa-uninit.cc
@@ -273,6 +273,17 @@ warn_uninit (opt_code opt, tree t, tree var, gimple 
*context,
        }
     }
 
+  /* Avoid diagnosing artificial decls - whether those are present or
+     not can depend on debug info level.  But make sure to diagnose
+     decls that are replacements for user variables as created by SRA.  */
+  tree orig_var = var;
+  if (var && DECL_ARTIFICIAL (var) && !DECL_HAS_DEBUG_EXPR_P (var)
+      /* ???  Fortran expects the artificial __result_<fn> to be
+        diagnosed about which isn't a RESULT_DECL, so key on
+        DECL_IGNORED_P.  */
+      && DECL_IGNORED_P (var))
+    var = NULL_TREE;
+
   if (var == NULL_TREE && var_name_str == NULL)
     return;
 
@@ -281,7 +292,7 @@ warn_uninit (opt_code opt, tree t, tree var, gimple 
*context,
   if (((warning_suppressed_p (context, OPT_Wuninitialized)
        || (gimple_assign_single_p (context)
            && get_no_uninit_warning (gimple_assign_rhs1 (context)))))
-      || (var && get_no_uninit_warning (var))
+      || (orig_var && get_no_uninit_warning (orig_var))
       || (var_name_str
          && warning_suppressed_p (var_def_stmt, OPT_Wuninitialized)))
     return;
@@ -322,8 +333,8 @@ warn_uninit (opt_code opt, tree t, tree var, gimple 
*context,
     }
 
   /* Avoid subsequent warnings for reads of the same variable again.  */
-  if (var)
-    suppress_warning (var, opt);
+  if (orig_var)
+    suppress_warning (orig_var, opt);
   else if (var_name_str)
     suppress_warning (var_def_stmt, opt);
 
-- 
2.51.0

Reply via email to