[Patch,avr]: PR target/52692: Imlpement TARGET_BUILTIN_DECL

2012-03-26 Thread Georg-Johann Lay
This implements TARGET_BUILTIN_DECL which is needed to make
LTO work with target-specific built-ins.

struct avr_builtin_description gets a new field .fndecl which is
initialized during avr_init_builtins and looked up in new hook
avr_builtin_decl.

The built-ins are initialized in such a way that there is always
  avr_bdesc[x].id == x
i.e. .id is superfluous and avr_expand_builtin can use id to access
the array and need no search loop to find built-in id.

Johann

Ok?

gcc/
PR target/52692
* config/avr/avr.c (TARGET_BUILTIN_DECL): New define.
(avr_builtin_decl): New static function.
(struct avr_builtin_description, avr_bdesc): Move up.
Add GTY marker. Add field fndecl. Remove redundant field id.
(avr_init_builtins): Initialize avr_bdesc[ID].fndecl.
(avr_expand_builtin): Code cleanup because .id is removed.

testsuite/
* gcc.target/avr/torture/builtins-2.c: New test.
Index: config/avr/avr.c
===
--- config/avr/avr.c	(revision 185792)
+++ config/avr/avr.c	(working copy)
@@ -10285,6 +10285,42 @@ enum avr_builtin_id
 AVR_BUILTIN_COUNT
   };
 
+struct GTY(()) avr_builtin_description
+{
+  enum insn_code icode;
+  const char *name;
+  int n_args;
+  tree fndecl;
+};
+
+
+/* Notice that avr_bdesc[] and avr_builtin_id are initialized in such a way
+   that a built-in's ID can be used to access the built-in by means of
+   avr_bdesc[ID]  */
+
+static GTY(()) struct avr_builtin_description
+avr_bdesc[AVR_BUILTIN_COUNT] =
+  {
+
+#define DEF_BUILTIN(NAME, N_ARGS, ID, TYPE, ICODE)  \
+{ ICODE, NAME, N_ARGS, NULL_TREE },
+#include builtins.def  
+#undef DEF_BUILTIN
+  };
+
+
+/* Implement `TARGET_BUILTIN_DECL'.  */
+
+static tree
+avr_builtin_decl (unsigned id, bool initialize_p ATTRIBUTE_UNUSED)
+{
+  if (id  AVR_BUILTIN_COUNT)
+return avr_bdesc[id].fndecl;
+
+  return error_mark_node;
+}
+
+
 static void
 avr_init_builtin_int24 (void)
 {
@@ -10295,6 +10331,7 @@ avr_init_builtin_int24 (void)
   (*lang_hooks.types.register_builtin_type) (uint24_type, __uint24);
 }
 
+
 /* Implement `TARGET_INIT_BUILTINS' */
 /* Set up all builtin functions for this target.  */
 
@@ -10348,7 +10385,9 @@ avr_init_builtins (void)
   NULL);
 
 #define DEF_BUILTIN(NAME, N_ARGS, ID, TYPE, CODE)   \
-  add_builtin_function (NAME, TYPE, ID, BUILT_IN_MD, NULL, NULL_TREE);
+  gcc_assert (ID  AVR_BUILTIN_COUNT);  \
+  avr_bdesc[ID].fndecl  \
+= add_builtin_function (NAME, TYPE, ID, BUILT_IN_MD, NULL, NULL_TREE);
 #include builtins.def  
 #undef DEF_BUILTIN
   
@@ -10356,27 +10395,6 @@ avr_init_builtins (void)
 }
 
 
-struct avr_builtin_description
-{
-  enum insn_code icode;
-  const char *name;
-  enum avr_builtin_id id;
-  int n_args;
-};
-
-static const struct avr_builtin_description
-avr_bdesc[] =
-  {
-
-#define DEF_BUILTIN(NAME, N_ARGS, ID, TYPE, ICODE)  \
-{ ICODE, NAME, ID, N_ARGS },
-#include builtins.def  
-#undef DEF_BUILTIN
-
-{ CODE_FOR_nothing, NULL, 0, -1 }
-  };
-
-
 /* Subroutine of avr_expand_builtin to take care of unop insns.  */
 
 static rtx
@@ -10545,6 +10563,7 @@ avr_expand_triop_builtin (enum insn_code
 }
 
 
+/* Implement `TARGET_EXPAND_BUILTIN'.  */
 /* Expand an expression EXP that calls a built-in function,
with result going to TARGET if that's convenient
(and in mode MODE if that's convenient).
@@ -10557,13 +10576,15 @@ avr_expand_builtin (tree exp, rtx target
 enum machine_mode mode ATTRIBUTE_UNUSED,
 int ignore ATTRIBUTE_UNUSED)
 {
-  size_t i;
   tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
   const char* bname = IDENTIFIER_POINTER (DECL_NAME (fndecl));
   unsigned int id = DECL_FUNCTION_CODE (fndecl);
+  const struct avr_builtin_description *d = avr_bdesc[id];
   tree arg0;
   rtx op0;
 
+  gcc_assert (id  AVR_BUILTIN_COUNT);
+
   switch (id)
 {
 case AVR_BUILTIN_NOP:
@@ -10597,29 +10618,22 @@ avr_expand_builtin (tree exp, rtx target
   }
 }
 
-  for (i = 0; avr_bdesc[i].name; i++)
+  /* No special treatment needed: vanilla expand.  */
+  
+  switch (d-n_args)
 {
-  const struct avr_builtin_description *d = avr_bdesc[i];
+case 0:
+  emit_insn ((GEN_FCN (d-icode)) (target));
+  return 0;
   
-  if (d-id == id)
-switch (d-n_args)
-  {
-  case 0:
-emit_insn ((GEN_FCN (d-icode)) (target));
-return 0;
-
-  case 1:
-return avr_expand_unop_builtin (d-icode, exp, target);
-
-  case 2:
-return avr_expand_binop_builtin (d-icode, exp, target);
-
-  case 3:
-return avr_expand_triop_builtin (d-icode, exp, target);
-
-  default:
-gcc_unreachable();
-}
+   

Re: [Patch,avr]: PR target/52692: Imlpement TARGET_BUILTIN_DECL

2012-03-26 Thread Denis Chertykov
2012/3/26 Georg-Johann Lay a...@gjlay.de:
 This implements TARGET_BUILTIN_DECL which is needed to make
 LTO work with target-specific built-ins.

 struct avr_builtin_description gets a new field .fndecl which is
 initialized during avr_init_builtins and looked up in new hook
 avr_builtin_decl.

 The built-ins are initialized in such a way that there is always
  avr_bdesc[x].id == x
 i.e. .id is superfluous and avr_expand_builtin can use id to access
 the array and need no search loop to find built-in id.

 Johann

 Ok?

 gcc/
        PR target/52692
        * config/avr/avr.c (TARGET_BUILTIN_DECL): New define.
        (avr_builtin_decl): New static function.
        (struct avr_builtin_description, avr_bdesc): Move up.
        Add GTY marker. Add field fndecl. Remove redundant field id.
        (avr_init_builtins): Initialize avr_bdesc[ID].fndecl.
        (avr_expand_builtin): Code cleanup because .id is removed.

 testsuite/
        * gcc.target/avr/torture/builtins-2.c: New test.

Please, apply.

Denis.