[SFN] sync up debug-only stmt list's side effects with empty stmts too
authorAlexandre Oliva <aoliva@redhat.com>
Fri, 22 Dec 2017 02:07:31 +0000 (02:07 +0000)
committerAlexandre Oliva <aoliva@gcc.gnu.org>
Fri, 22 Dec 2017 02:07:31 +0000 (02:07 +0000)
for  gcc/c-family/ChangeLog

PR debug/83527
PR debug/83419
* c-semantics.c (only_debug_stmts_after_p): New.
(pop_stmt_list): Clear side effects in debug-only stmt list.
Check for single nondebug stmt followed by debug stmts only.

for  gcc/testsuite/ChangeLog

PR debug/83527
PR debug/83419
* gcc.dg/pr83527.c: New.

From-SVN: r255966

gcc/c-family/ChangeLog
gcc/c-family/c-semantics.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/pr83527.c [new file with mode: 0644]

index 6f62034..ba61fce 100644 (file)
@@ -1,3 +1,11 @@
+2017-12-22  Alexandre Oliva <aoliva@redhat.com>
+
+       PR debug/83527
+       PR debug/83419
+       * c-semantics.c (only_debug_stmts_after_p): New.
+       (pop_stmt_list): Clear side effects in debug-only stmt list.
+       Check for single nondebug stmt followed by debug stmts only.
+
 2017-12-21  Alexandre Oliva  <aoliva@redhat.com>
 
        PR debug/83419
index 3a972c3..21d908e 100644 (file)
@@ -35,6 +35,17 @@ push_stmt_list (void)
   return t;
 }
 
+/* Return TRUE if, after I, there are any nondebug stmts.  */
+
+static inline bool
+only_debug_stmts_after_p (tree_stmt_iterator i)
+{
+  for (tsi_next (&i); !tsi_end_p (i); tsi_next (&i))
+    if (TREE_CODE (tsi_stmt (i)) != DEBUG_BEGIN_STMT)
+      return false;
+  return true;
+}
+
 /* Finish the statement tree rooted at T.  */
 
 tree
@@ -99,11 +110,15 @@ pop_stmt_list (tree t)
          while (!tsi_end_p (i)
                 && TREE_CODE (tsi_stmt (i)) == DEBUG_BEGIN_STMT)
            tsi_next (&i);
-         /* If there's only one nondebug stmt in the list, we'd have
-            extracted the stmt and dropped the list, and we'd take
-            TREE_SIDE_EFFECTS from that statement, so keep the list's
+         /* If there are only debug stmts in the list, without them
+            we'd have an empty stmt without side effects.  If there's
+            only one nondebug stmt, we'd have extracted the stmt and
+            dropped the list, and we'd take TREE_SIDE_EFFECTS from
+            that statement.  In either case, keep the list's
             TREE_SIDE_EFFECTS in sync.  */
-         if (tsi_one_before_end_p (i))
+         if (tsi_end_p (i))
+           TREE_SIDE_EFFECTS (t) = 0;
+         else if (only_debug_stmts_after_p (i))
            TREE_SIDE_EFFECTS (t) = TREE_SIDE_EFFECTS (tsi_stmt (i));
        }
     }
index 79ee49c..3969bd2 100644 (file)
@@ -1,3 +1,9 @@
+2017-12-22  Alexandre Oliva <aoliva@redhat.com>
+
+       PR debug/83527
+       PR debug/83419
+       * gcc.dg/pr83527.c: New.
+
 2017-12-21  Martin Sebor  <msebor@redhat.com>
 
        PR testsuite/83462
diff --git a/gcc/testsuite/gcc.dg/pr83527.c b/gcc/testsuite/gcc.dg/pr83527.c
new file mode 100644 (file)
index 0000000..effef43
--- /dev/null
@@ -0,0 +1,26 @@
+/* PR debug/83527 */
+/* { dg-do compile } */
+/* { dg-options "-O2 -fcompare-debug" } */
+
+extern void fn2(void);
+extern void fn3(void);
+int a, b;
+void fn1() {
+  int c;
+  short d;
+  switch (a) {
+  case 32800:
+    fn2();
+  case 32769:
+    b = 0;
+  case 32771:
+  case 32772:
+  case 32782:
+    fn3();
+  }
+  if (d || c) {
+    do
+      ;
+    while (0);
+  }
+}