aboutsummaryrefslogtreecommitdiff
path: root/gcc/c-family
diff options
context:
space:
mode:
authorJavier Martinez <javier.martinez.bugzilla@gmail.com>2023-08-23 15:02:40 +0200
committerJason Merrill <jason@redhat.com>2023-09-19 15:03:28 -0400
commit4f52e61e0665e760b95975b4d49437873967be2e (patch)
treed295e1e617ed5c9275f70a637703c30511c06aa9 /gcc/c-family
parentb9912332c5b6fc9433ee11f5488acad117868888 (diff)
downloadgcc-4f52e61e0665e760b95975b4d49437873967be2e.zip
gcc-4f52e61e0665e760b95975b4d49437873967be2e.tar.gz
gcc-4f52e61e0665e760b95975b4d49437873967be2e.tar.bz2
c++: extend cold, hot attributes to classes
Most code is cold. This patch extends support for attribute ((cold)) to C++ Classes, Unions, and Structs (RECORD_TYPES and UNION_TYPES) to benefit from encapsulation - reducing the verbosity of using the attribute where deserved. The ((hot)) attribute is also extended for its semantic relation. gcc/c-family/ChangeLog: * c-attribs.cc (handle_hot_attribute): remove warning on RECORD_TYPE and UNION_TYPE when in c_dialect_xx. (handle_cold_attribute): Likewise. gcc/cp/ChangeLog: * class.cc (propagate_class_warmth_attribute): New function. (check_bases_and_members): propagate hot and cold attributes to all FUNCTION_DECL when the record is marked hot or cold. * cp-tree.h (maybe_propagate_warmth_attributes): New function. * decl2.cc (maybe_propagate_warmth_attributes): New function. * method.cc (lazily_declare_fn): propagate hot and cold attributes to lazily declared functions when the record is marked hot or cold. gcc/ChangeLog: * doc/extend.texi: Document attributes hot, cold on C++ types. gcc/testsuite/ChangeLog: * g++.dg/ext/attr-hotness.C: New test. Signed-off-by: Javier Martinez <javier.martinez.bugzilla@gmail.com> Reviewed-by: Jason Merrill <jason@redhat.com>
Diffstat (limited to 'gcc/c-family')
-rw-r--r--gcc/c-family/c-attribs.cc50
1 files changed, 48 insertions, 2 deletions
diff --git a/gcc/c-family/c-attribs.cc b/gcc/c-family/c-attribs.cc
index e0c4259..dca7548 100644
--- a/gcc/c-family/c-attribs.cc
+++ b/gcc/c-family/c-attribs.cc
@@ -452,10 +452,10 @@ const struct attribute_spec c_common_attribute_table[] =
{ "alloc_size", 1, 2, false, true, true, false,
handle_alloc_size_attribute,
attr_alloc_exclusions },
- { "cold", 0, 0, true, false, false, false,
+ { "cold", 0, 0, false, false, false, false,
handle_cold_attribute,
attr_cold_hot_exclusions },
- { "hot", 0, 0, true, false, false, false,
+ { "hot", 0, 0, false, false, false, false,
handle_hot_attribute,
attr_cold_hot_exclusions },
{ "no_address_safety_analysis",
@@ -1110,6 +1110,29 @@ handle_hot_attribute (tree *node, tree name, tree ARG_UNUSED (args),
{
/* Attribute hot processing is done later with lookup_attribute. */
}
+ else if ((TREE_CODE (*node) == RECORD_TYPE
+ || TREE_CODE (*node) == UNION_TYPE)
+ && c_dialect_cxx ()
+ && (flags & (int) ATTR_FLAG_TYPE_IN_PLACE))
+ {
+ /* Check conflict here as decl_attributes will otherwise only catch
+ it late at the function when the attribute is used on a class. */
+ tree cold_attr = lookup_attribute ("cold", TYPE_ATTRIBUTES (*node));
+ if (cold_attr)
+ {
+ warning (OPT_Wattributes, "ignoring attribute %qE because it "
+ "conflicts with attribute %qs", name, "cold");
+ *no_add_attrs = true;
+ }
+ }
+ else if (flags & ((int) ATTR_FLAG_FUNCTION_NEXT
+ | (int) ATTR_FLAG_DECL_NEXT))
+ {
+ /* Avoid applying the attribute to a function return type when
+ used as: void __attribute ((hot)) foo (void). It will be
+ passed to the function. */
+ *no_add_attrs = true;
+ }
else
{
warning (OPT_Wattributes, "%qE attribute ignored", name);
@@ -1131,6 +1154,29 @@ handle_cold_attribute (tree *node, tree name, tree ARG_UNUSED (args),
{
/* Attribute cold processing is done later with lookup_attribute. */
}
+ else if ((TREE_CODE (*node) == RECORD_TYPE
+ || TREE_CODE (*node) == UNION_TYPE)
+ && c_dialect_cxx ()
+ && (flags & (int) ATTR_FLAG_TYPE_IN_PLACE))
+ {
+ /* Check conflict here as decl_attributes will otherwise only catch
+ it late at the function when the attribute is used on a class. */
+ tree hot_attr = lookup_attribute ("hot", TYPE_ATTRIBUTES (*node));
+ if (hot_attr)
+ {
+ warning (OPT_Wattributes, "ignoring attribute %qE because it "
+ "conflicts with attribute %qs", name, "hot");
+ *no_add_attrs = true;
+ }
+ }
+ else if (flags & ((int) ATTR_FLAG_FUNCTION_NEXT
+ | (int) ATTR_FLAG_DECL_NEXT))
+ {
+ /* Avoid applying the attribute to a function return type when
+ used as: void __attribute ((cold)) foo (void). It will be
+ passed to the function. */
+ *no_add_attrs = true;
+ }
else
{
warning (OPT_Wattributes, "%qE attribute ignored", name);