aboutsummaryrefslogtreecommitdiff
path: root/gcc/testsuite
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2022-10-07 09:01:04 +0200
committerJakub Jelinek <jakub@redhat.com>2022-10-07 09:01:04 +0200
commit88f04e90f63f08620cc9cd2f059a1315b70bed3b (patch)
tree868dae2613d56d7f3cb26d24e62ff81a8d2d7745 /gcc/testsuite
parent348e46fa8cba960c23170673bfc0c1b4fb384975 (diff)
downloadgcc-88f04e90f63f08620cc9cd2f059a1315b70bed3b.zip
gcc-88f04e90f63f08620cc9cd2f059a1315b70bed3b.tar.gz
gcc-88f04e90f63f08620cc9cd2f059a1315b70bed3b.tar.bz2
c++: Improve handling of foreigner namespace attributes
In some cases we want to look up or remove both standard attributes and attributes from gnu namespace but not others. This patch arranges for ATTR_NS of "" to stand for ATTR_NS NULL or "gnu", so that we don't need 2 separate calls, and introduces is_attribute_namespace_p function which allows testing the namespace of an attribute similar way. The patch also uses the new lookup_attribute overload and extra tests to avoid emitting weird warnings on foreign namespace attributes which we should just ignore (perhaps with a warning), but shouldn't imply any meaning to them just because they have a name matching some standard or gnu attribute name. 2022-10-07 Jakub Jelinek <jakub@redhat.com> gcc/ * attribs.h (is_attribute_namespace_p): New inline function. (lookup_attribute): Document meaning of ATTR_NS equal to "". * attribs.cc (remove_attribute): Use is_attribute_namespace_p. (private_lookup_attribute): For ATTR_NS "" match either standard attribute or "gnu" namespace one. gcc/c-family/ * c-common.cc (attribute_fallthrough_p): Lookup fallthrough attribute only in gnu namespace or as standard attribute, treat fallthrough attributes in other namespaces like any other unknown attribute. gcc/cp/ * parser.cc (cp_parser_check_std_attribute): Only do checks if attribute is a standard attribute or in gnu namespace and only lookup other attributes in those namespaces. * cp-gimplify.cc (lookup_hotness_attribute): Adjust function comment. Only return true for standard attribute or gnu namespace attribute. (remove_hotness_attribute): Only remove hotness attributes when they are standard or in gnu namespace, implement it in a single loop rather than former 4 now 8 remove_attribute calls. gcc/testsuite/ * g++.dg/cpp1z/fallthrough2.C: New test. * g++.dg/cpp2a/attr-likely7.C: New test.
Diffstat (limited to 'gcc/testsuite')
-rw-r--r--gcc/testsuite/g++.dg/cpp1z/fallthrough2.C24
-rw-r--r--gcc/testsuite/g++.dg/cpp2a/attr-likely7.C38
2 files changed, 62 insertions, 0 deletions
diff --git a/gcc/testsuite/g++.dg/cpp1z/fallthrough2.C b/gcc/testsuite/g++.dg/cpp1z/fallthrough2.C
new file mode 100644
index 0000000..b74323f
--- /dev/null
+++ b/gcc/testsuite/g++.dg/cpp1z/fallthrough2.C
@@ -0,0 +1,24 @@
+// { dg-do compile { target c++17 } }
+// { dg-options "-Wextra -Wall -Wpedantic" }
+
+int
+foo (int i)
+{
+ switch (i)
+ {
+ case 2:
+ ++i;
+ [[fallthrough, whatever::fallthrough]]; // { dg-bogus "attribute 'fallthrough' specified multiple times" }
+ case 3: // { dg-warning "'fallthrough' attribute ignored" "" { target *-*-* } .-1 }
+ ++i;
+ [[fallthrough, whatever2::fallthrough(1, 2, 3)]]; // { dg-bogus "attribute 'fallthrough' specified multiple times" }
+ case 4: // { dg-warning "'fallthrough' attribute ignored" "" { target *-*-* } .-1 }
+ [[whatever3::fallthrough("abcd")]]; // { dg-warning "attributes at the beginning of statement are ignored" }
+ case 5:
+ [[whatever4::fallthrough]]; // { dg-bogus "attribute 'fallthrough' not preceding a case label or default label" }
+ ++i; // { dg-warning "attributes at the beginning of statement are ignored" "" { target *-*-* } .-1 }
+ default:
+ break;
+ }
+ return i;
+}
diff --git a/gcc/testsuite/g++.dg/cpp2a/attr-likely7.C b/gcc/testsuite/g++.dg/cpp2a/attr-likely7.C
new file mode 100644
index 0000000..638a6d9
--- /dev/null
+++ b/gcc/testsuite/g++.dg/cpp2a/attr-likely7.C
@@ -0,0 +1,38 @@
+// { dg-do compile { target c++20 } }
+// { dg-additional-options -fdump-tree-gimple }
+// { dg-final { scan-tree-dump-times "hot label" 5 "gimple" } }
+// { dg-final { scan-tree-dump-times "cold label" 3 "gimple" } }
+
+bool b;
+
+template <class T> int f()
+{
+ if (b)
+ [[likely, whatever::unlikely ("abcd")]] return 0; // { dg-bogus "ignoring attribute 'unlikely' after earlier 'likely'" }
+ else // { dg-warning "attributes at the beginning of statement are ignored" "" { target *-*-* } .-1 }
+ [[unlikely, whatever2::hot]] flabel: return 1; // { dg-warning "'whatever2::hot' scoped attribute directive ignored" }
+ switch (b)
+ {
+ [[likely, whatever3::cold (1, 2, 3)]] case true: break; // { dg-warning "'whatever3::cold' scoped attribute directive ignored" }
+ };
+ return 1;
+}
+
+int main()
+{
+ if (b)
+ [[whatever4::unlikely (1), likely]] return 0; // { dg-bogus "ignoring attribute 'likely' after earlier 'unlikely'" }
+ else if (b) // { dg-warning "attributes at the beginning of statement are ignored" "" { target *-*-* } .-1 }
+ [[whatever5::hot, unlikely]] elabel: // { dg-warning "'whatever5::hot' scoped attribute directive ignored" }
+ return 1;
+ else
+ [[whatever6::cold, likely]] b = false; // { dg-bogus "ignoring attribute 'likely' after earlier 'cold'" }
+ // { dg-warning "attributes at the beginning of statement are ignored" "" { target *-*-* } .-1 }
+ f<int>();
+
+ switch (b)
+ {
+ [[whatever7::unlikely (1), likely]] case true: break; // { dg-warning "'whatever7::unlikely' scoped attribute directive ignored" }
+ [[whatever8::unlikely, unlikely]] case false: break; // { dg-bogus "attribute 'unlikely' specified multiple times" }
+ }; // { dg-warning "'whatever8::unlikely' scoped attribute directive ignored" "" { target *-*-* } .-1 }
+}