New patch attached.

About using mangled name, I'm afraid this will make the command line
too long for C++. And also, using bfd_name makes it easier to specify
the pattern for common names. E.g. many class many have Log functions,
but they are all likely to be cold. Using bfd_name, we only need to
specify the pattern once.

Thanks,
Dehao

Index: gcc/doc/invoke.texi
===================================================================
--- gcc/doc/invoke.texi (revision 188050)
+++ gcc/doc/invoke.texi (working copy)
@@ -362,7 +362,8 @@
 -fdelete-null-pointer-checks -fdse -fdevirtualize -fdse @gol
 -fearly-inlining -fipa-sra -fexpensive-optimizations -ffast-math @gol
 -ffinite-math-only -ffloat-store -fexcess-precision=@var{style} @gol
--fforward-propagate -ffp-contract=@var{style} -ffunction-sections @gol
+-fforward-propagate -ffp-contract=@var{style} @gol
+-ffunction-attribute-list -ffunction-sections @gol
 -fgcse -fgcse-after-reload -fgcse-las -fgcse-lm -fgraphite-identity @gol
 -fgcse-sm -fif-conversion -fif-conversion2 -findirect-inlining @gol
 -finline-functions -finline-functions-called-once -finline-limit=@var{n} @gol
@@ -8585,6 +8586,10 @@
 specify this option and you may have problems with debugging if
 you specify both this option and @option{-g}.

+@item -ffunction-attribute-list
+@opindex ffunction-attribute-list
+List of function name patterns that will be applied specified attribute.
+
 @item -fbranch-target-load-optimize
 @opindex fbranch-target-load-optimize
 Perform branch target register load optimization before prologue / epilogue
Index: gcc/cgraph.c
===================================================================
--- gcc/cgraph.c        (revision 188050)
+++ gcc/cgraph.c        (working copy)
@@ -99,6 +99,7 @@
 #include "ipa-utils.h"
 #include "lto-streamer.h"
 #include "l-ipo.h"
+#include "opts.h"

 const char * const ld_plugin_symbol_resolution_names[]=
 {
@@ -520,6 +521,32 @@
     }
 }

+/* Match FNDECL's name with user specified patterns. If match is found, add
+   attributes to FNDECL.
+   name matches with pattern, iff one of the following conditions satisfy:
+     1. strcmp (name, pattern) == 0
+     2. pattern[len - 1] == '*' && strncmp (name, pattern, len - 1) == 0  */
+static void
+cgraph_match_attribute_by_name (tree fndecl)
+{
+  unsigned i;
+  attribute_pair_p p;
+  const char *name = lang_hooks.decl_printable_name(fndecl, 0);
+
+  if (!name)
+    return;
+
+  FOR_EACH_VEC_ELT (attribute_pair_p, function_attribute_list, i, p)
+    {
+      char *n = p->name;
+      int len = strlen (n);
+      if ((n[len - 1] == '*' && !strncmp (name, n, len - 1))
+          || !strcmp (name, n))
+        decl_attributes (&fndecl, tree_cons (
+            get_identifier (p->attribute), NULL, NULL), 0);
+    }
+}
+
 /* Return cgraph node assigned to DECL.  Create new one when needed.  */

 struct cgraph_node *
@@ -554,6 +581,7 @@
       node->origin->nested = node;
     }
   cgraph_add_assembler_hash_node (node);
+  cgraph_match_attribute_by_name (decl);
   return node;
 }

Index: gcc/opts.c
===================================================================
--- gcc/opts.c  (revision 188050)
+++ gcc/opts.c  (working copy)
@@ -1647,6 +1647,10 @@
       /* Deferred.  */
       break;

+    case OPT_ffunction_attribute_list_:
+      /* Deferred.  */
+      break;
+
     case OPT_fsched_verbose_:
 #ifdef INSN_SCHEDULING
       /* Handled with Var in common.opt.  */
Index: gcc/opts.h
===================================================================
--- gcc/opts.h  (revision 188050)
+++ gcc/opts.h  (working copy)
@@ -272,6 +272,15 @@
   struct cl_option_handler_func handlers[3];
 };

+typedef struct {
+  char *name;
+  char *attribute;
+} attribute_pair;
+typedef attribute_pair *attribute_pair_p;
+DEF_VEC_P(attribute_pair_p);
+DEF_VEC_ALLOC_P(attribute_pair_p,heap);
+extern VEC(attribute_pair_p,heap) *function_attribute_list;
+
 /* Input file names.  */

 extern const char **in_fnames;
Index: gcc/common.opt
===================================================================
--- gcc/common.opt      (revision 188050)
+++ gcc/common.opt      (working copy)
@@ -1242,6 +1242,10 @@
 Common Report Var(flag_function_sections)
 Place each function into its own section

+ffunction-attribute-list=
+Common Joined RejectNegative Var(common_deferred_options) Defer
+-ffunction-attribute-list=attribute:name,...  Add attribute to named functions
+
 fgcda=
 Common Joined RejectNegative Var(gcov_da_name)
 Set the gcov data file name.
Index: gcc/opts-global.c
===================================================================
--- gcc/opts-global.c   (revision 188050)
+++ gcc/opts-global.c   (working copy)
@@ -50,6 +50,8 @@
 const char **in_fnames;
 unsigned num_in_fnames;

+VEC(attribute_pair_p,heap) *function_attribute_list;
+
 /* Return a malloced slash-separated list of languages in MASK.  */

 static char *
@@ -79,6 +81,54 @@
   return result;
 }

+/* Add strings like attribute_str:name1,name2... to a char_pair_p vector.  */
+
+static void
+add_attribute_list_to_vector (VEC(attribute_pair_p,heap) **pvec,
+                             const char *arg)
+{
+  char *tmp;
+  char *r;
+  char *token_start;
+  char *attribute;
+  VEC(attribute_pair_p,heap) *vec = *pvec;
+
+  /* We never free this string.  */
+  tmp = xstrdup (arg);
+  attribute = tmp;
+
+  for (r = tmp; *r != '\0' && *r != ':'; ++r)
+    ;
+
+  if (*r != ':')
+    return;
+
+  *r = '\0';
+  token_start = r + 1;
+  r = strchr (token_start, ',');
+
+  while (r)
+    {
+      attribute_pair_p p = (attribute_pair_p) xmalloc (sizeof
(attribute_pair));
+      p->name = token_start;
+      p->attribute = attribute;
+      VEC_safe_push (attribute_pair_p, heap, vec, p);
+      *r = '\0';
+      token_start = r + 1;
+      r = strchr (token_start, ',');
+    }
+  if (*token_start != '\0')
+    {
+      attribute_pair_p p =
+         (attribute_pair_p) xmalloc (sizeof (attribute_pair));
+      p->name = token_start;
+      p->attribute = attribute;
+      VEC_safe_push (attribute_pair_p, heap, vec, p);
+    }
+
+  *pvec = vec;
+}
+
 /* Complain that switch DECODED does not apply to this front end (mask
    LANG_MASK).  */

@@ -452,6 +502,10 @@
          set_random_seed (opt->arg);
          break;

+       case OPT_ffunction_attribute_list_:
+         add_attribute_list_to_vector(&function_attribute_list, opt->arg);
+         break;
+
        case OPT_fstack_limit:
          /* The real switch is -fno-stack-limit.  */
          if (!opt->value)

Reply via email to