aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2016-10-31 14:39:49 +0100
committerJakub Jelinek <jakub@gcc.gnu.org>2016-10-31 14:39:49 +0100
commite8d8d3c8bfae148448cd3108db3cc15434137393 (patch)
treea034281920dc69d1e7d899387cf06c478db69a6b /gcc
parent84ff4775d41b716c1b862d4d91ff69127686b668 (diff)
downloadgcc-e8d8d3c8bfae148448cd3108db3cc15434137393.zip
gcc-e8d8d3c8bfae148448cd3108db3cc15434137393.tar.gz
gcc-e8d8d3c8bfae148448cd3108db3cc15434137393.tar.bz2
re PR c++/77886 (-Wimplicit-fallthrough: breaks duff's device (in function templates))
PR c++/77886 * pt.c (tsubst_expr) <case CASE_LABEL_EXPR> Copy over FALLTHROUGH_LABEL_P flag to the new LABEL_DECL. (tsubst_expr) <case LABEL_EXPR>: Likewise. * g++.dg/warn/Wimplicit-fallthrough-2.C: New test. From-SVN: r241700
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog7
-rw-r--r--gcc/cp/ChangeLog5
-rw-r--r--gcc/cp/pt.c7
-rw-r--r--gcc/testsuite/g++.dg/warn/Wimplicit-fallthrough-2.C66
4 files changed, 84 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 7905d95..9a45b66 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2016-10-31 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/77886
+ * pt.c (tsubst_expr) <case CASE_LABEL_EXPR> Copy over
+ FALLTHROUGH_LABEL_P flag to the new LABEL_DECL.
+ (tsubst_expr) <case LABEL_EXPR>: Likewise.
+
2016-09-11 Le-Chun Wu <lcwu@google.com>
Mark Wielaard <mjw@redhat.com>
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index be439ec..39da99e 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,8 @@
+2016-10-31 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/77886
+ * g++.dg/warn/Wimplicit-fallthrough-2.C: New test.
+
2016-09-11 Le-Chun Wu <lcwu@google.com>
Mark Wielaard <mjw@redhat.com>
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index c916e58..7352213 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -15487,7 +15487,10 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
{
tree low = RECUR (CASE_LOW (t));
tree high = RECUR (CASE_HIGH (t));
- finish_case_label (EXPR_LOCATION (t), low, high);
+ tree l = finish_case_label (EXPR_LOCATION (t), low, high);
+ if (l && TREE_CODE (l) == CASE_LABEL_EXPR)
+ FALLTHROUGH_LABEL_P (CASE_LABEL (l))
+ = FALLTHROUGH_LABEL_P (CASE_LABEL (t));
}
break;
@@ -15497,6 +15500,8 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
tree label;
label = finish_label_stmt (DECL_NAME (decl));
+ if (TREE_CODE (label) == LABEL_DECL)
+ FALLTHROUGH_LABEL_P (label) = FALLTHROUGH_LABEL_P (decl);
if (DECL_ATTRIBUTES (decl) != NULL_TREE)
cplus_decl_attributes (&label, DECL_ATTRIBUTES (decl), 0);
}
diff --git a/gcc/testsuite/g++.dg/warn/Wimplicit-fallthrough-2.C b/gcc/testsuite/g++.dg/warn/Wimplicit-fallthrough-2.C
new file mode 100644
index 0000000..cacaf55
--- /dev/null
+++ b/gcc/testsuite/g++.dg/warn/Wimplicit-fallthrough-2.C
@@ -0,0 +1,66 @@
+// PR c++/77886
+// { dg-do compile }
+// { dg-options "-Wimplicit-fallthrough" }
+
+template <int N>
+int
+foo (int x, int y)
+{
+ switch (x)
+ {
+ case 1:
+ x++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ // FALLTHROUGH
+ case 2:
+ x++;
+ break;
+ case 3:
+ x++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ // FALLTHROUGH
+ lab:
+ case 4:
+ x++;
+ break;
+ case 5:
+ x++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ // FALLTHROUGH
+ default:
+ x++;
+ break;
+ case 26:
+ goto lab;
+ }
+#if __cplusplus >= 201103L
+ switch (y)
+ {
+ case 1:
+ y++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ [[fallthrough]];
+ case 2:
+ y++;
+ break;
+ case 3:
+ y++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ [[fallthrough]];
+ lab2:
+ case 4:
+ y++;
+ break;
+ case 5:
+ y++; // { dg-bogus "this statement may f\[ahlotu\]*gh" }
+ [[fallthrough]];
+ default:
+ y++;
+ break;
+ case 26:
+ goto lab2;
+ }
+#endif
+ return x + y;
+}
+
+int
+bar (int x, int y)
+{
+ return foo<0> (x, y);
+}