Hi,
   this patch introduces a new function lookup_attribute_starting that can find 
all attributes starting with a specified string. Purpose of the function is to 
be able to identify e.g. if a function has any 'omp' attribute.

Bootstrapped and tested on x86_64-linux.
OK for trunk?

Thanks,
Martin

2014-05-29  Martin Liska  <mli...@suse.cz>

        * tree.h (private_lookup_attribute_starting): New function.
        (lookup_attribute_starting): Likewise.
        * tree.c (private_lookup_attribute_starting): Likewise.

diff --git a/gcc/tree.c b/gcc/tree.c
index cf7e362..9c6b68c 100644
--- a/gcc/tree.c
+++ b/gcc/tree.c
@@ -5758,6 +5758,37 @@ private_lookup_attribute (const char *attr_name, size_t 
attr_len, tree list)
   return list;
 }
+tree
+private_lookup_attribute_starting (const char *attr_name, size_t attr_len, 
tree list)
+{
+  while (list)
+    {
+      size_t ident_len = IDENTIFIER_LENGTH (get_attribute_name (list));
+
+      if (attr_len > ident_len)
+       {
+         list = TREE_CHAIN (list);
+         continue;
+       }
+
+      const char *p = IDENTIFIER_POINTER (get_attribute_name (list));
+
+      if (strncmp (attr_name, p, attr_len) == 0)
+       break;
+
+      /* TODO: If we made sure that attributes were stored in the
+        canonical form without '__...__' (ie, as in 'text' as opposed
+        to '__text__') then we could avoid the following case.  */
+      if (p[0] == '_' && p[1] == '_' && strncmp (attr_name, p + 2, attr_len) 
== 0)
+       break;
+
+      list = TREE_CHAIN (list);
+    }
+
+  return list;
+}
+
+
 /* A variant of lookup_attribute() that can be used with an identifier
    as the first argument, and where the identifier can be either
    'text' or '__text__'.
diff --git a/gcc/tree.h b/gcc/tree.h
index 9fe7360..3e1b113 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -3731,6 +3731,10 @@ extern tree merge_type_attributes (tree, tree);
    and you should never call it directly.  */
 extern tree private_lookup_attribute (const char *, size_t, tree);
+/* This function is a private implementation detail
+   of lookup_attribute_starting() and you should never call it directly.  */
+extern tree private_lookup_attribute_starting (const char *, size_t, tree);
+
 /* Given an attribute name ATTR_NAME and a list of attributes LIST,
    return a pointer to the attribute's list element if the attribute
    is part of the list, or NULL_TREE if not found.  If the attribute
@@ -3753,6 +3757,23 @@ lookup_attribute (const char *attr_name, tree list)
     return private_lookup_attribute (attr_name, strlen (attr_name), list);
 }
+/* Given an attribute name ATTR_NAME and a list of attributes LIST,
+   return a pointer to the attribute's list element if the attribute
+   starts with ATTR_NAME. ATTR_NAME must be in the form 'text' (not
+   '__text__').  */
+
+static inline tree
+lookup_attribute_starting (const char *attr_name, tree list)
+{
+  gcc_checking_assert (attr_name[0] != '_');
+  /* In most cases, list is NULL_TREE.  */
+  if (list == NULL_TREE)
+    return NULL_TREE;
+  else
+    return private_lookup_attribute_starting (attr_name, strlen (attr_name), 
list);
+}
+
+
 /* This function is a private implementation detail of
    is_attribute_p() and you should never call it directly.  */
 extern bool private_is_attribute_p (const char *, size_t, const_tree);
--
1.8.4.5


Reply via email to