2006-11-30 Andrew Pinski <andrew_pinski@playstation.sony.com>
authorpinskia <pinskia@138bc75d-0d04-0410-961f-82ee72b054a4>
Fri, 1 Dec 2006 02:38:47 +0000 (02:38 +0000)
committerpinskia <pinskia@138bc75d-0d04-0410-961f-82ee72b054a4>
Fri, 1 Dec 2006 02:38:47 +0000 (02:38 +0000)
        * config/spu/spu.c (spu_builtin_range): Move from spu-c.c
        (TARGET_RESOLVE_OVERLOADED_BUILTIN): Delete.
        (spu_cpu_cpp_builtins): Remove.
        (spu_override_options): Don't set warn_main.
        (spu_force_reg): Move from spu-c.c.
        (spu_check_builtin_parm): Likewise.
        (expand_builtin_args): Likewise.
        (spu_expand_builtin_1): Likewise.
        (spu_expand_builtin): Likewise.
        * config/spu/spu.h (REGISTER_TARGET_PRAGMAS): Define, set
        warn_main and targetm.resolve_overloaded_builtin.
        * config/spu/spu-c.c (spu_builtin_range): Remove.
        (spu_check_builtin_parm): Remove.
        (expand_builtin_args): Remove.
        (spu_expand_builtin_1): Remove.
        (spu_expand_builtin): Remove.
        (spu_cpu_cpp_builtins): Moved from spu.c
        (spu_force_reg): Remove.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@119397 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/config/spu/spu-c.c
gcc/config/spu/spu.c
gcc/config/spu/spu.h

index 559be89..4995449 100644 (file)
@@ -1,3 +1,24 @@
+2006-11-30  Andrew Pinski  <andrew_pinski@playstation.sony.com>
+
+       * config/spu/spu.c (spu_builtin_range): Move from spu-c.c
+       (TARGET_RESOLVE_OVERLOADED_BUILTIN): Delete.
+       (spu_cpu_cpp_builtins): Remove.
+       (spu_override_options): Don't set warn_main.
+       (spu_force_reg): Move from spu-c.c.
+       (spu_check_builtin_parm): Likewise.
+       (expand_builtin_args): Likewise.
+       (spu_expand_builtin_1): Likewise.
+       (spu_expand_builtin): Likewise.
+       * config/spu/spu.h (REGISTER_TARGET_PRAGMAS): Define, set
+       warn_main and targetm.resolve_overloaded_builtin.
+       * config/spu/spu-c.c (spu_builtin_range): Remove.
+       (spu_check_builtin_parm): Remove.
+       (expand_builtin_args): Remove.
+       (spu_expand_builtin_1): Remove.
+       (spu_expand_builtin): Remove.
+       (spu_cpu_cpp_builtins): Moved from spu.c
+       (spu_force_reg): Remove.
+
 2006-12-01  Joseph Myers  <joseph@codesourcery.com>
             David Edelsohn  <edelsohn@gnu.org>
 
index 80a5701..b975e83 100644 (file)
 #include "recog.h"
 #include "optabs.h"
 #include "spu-builtins.h"
-
-static rtx spu_expand_builtin_1 (struct spu_builtin_description *d,
-                                tree arglist, rtx target);
-static void spu_check_builtin_parm (struct spu_builtin_description *, rtx,
-                                   int);
-static void expand_builtin_args (struct spu_builtin_description *, tree, rtx,
-                                rtx[]);
-static rtx spu_force_reg (enum machine_mode mode, rtx op);
-
-/* Builtin types, data and prototypes. */
-struct spu_builtin_range
-{
-  int low, high;
-};
-
-static struct spu_builtin_range spu_builtin_range[] = {
-  {-0x40ll, 0x7fll},           /* SPU_BTI_7     */
-  {-0x40ll, 0x3fll},           /* SPU_BTI_S7    */
-  {0ll, 0x7fll},               /* SPU_BTI_U7    */
-  {-0x200ll, 0x1ffll},         /* SPU_BTI_S10   */
-  {-0x2000ll, 0x1fffll},       /* SPU_BTI_S10_4 */
-  {0ll, 0x3fffll},             /* SPU_BTI_U14   */
-  {-0x8000ll, 0xffffll},       /* SPU_BTI_16    */
-  {-0x8000ll, 0x7fffll},       /* SPU_BTI_S16   */
-  {-0x20000ll, 0x1ffffll},     /* SPU_BTI_S16_2 */
-  {0ll, 0xffffll},             /* SPU_BTI_U16   */
-  {0ll, 0x3ffffll},            /* SPU_BTI_U16_2 */
-  {0ll, 0x3ffffll},            /* SPU_BTI_U18   */
-};
 \f
 
 /* Helper for spu_resolve_overloaded_builtin.  */
@@ -181,263 +152,13 @@ spu_resolve_overloaded_builtin (tree fndecl, tree fnargs)
   return spu_build_overload_builtin (match, fnargs);
 }
 
-static void
-spu_check_builtin_parm (struct spu_builtin_description *d, rtx op, int p)
-{
-  HOST_WIDE_INT v = 0;
-  int lsbits;
-  /* Check the range of immediate operands. */
-  if (p >= SPU_BTI_7 && p <= SPU_BTI_U18)
-    {
-      int range = p - SPU_BTI_7;
-      if (!CONSTANT_P (op)
-         || (GET_CODE (op) == CONST_INT
-             && (INTVAL (op) < spu_builtin_range[range].low
-                 || INTVAL (op) > spu_builtin_range[range].high)))
-       error ("%s expects an integer literal in the range [%d, %d].",
-              d->name,
-              spu_builtin_range[range].low, spu_builtin_range[range].high);
-
-      if (GET_CODE (op) == CONST
-         && (GET_CODE (XEXP (op, 0)) == PLUS
-             || GET_CODE (XEXP (op, 0)) == MINUS))
-       {
-         v = INTVAL (XEXP (XEXP (op, 0), 1));
-         op = XEXP (XEXP (op, 0), 0);
-       }
-      else if (GET_CODE (op) == CONST_INT)
-       v = INTVAL (op);
-
-      switch (p)
-       {
-       case SPU_BTI_S10_4:
-         lsbits = 4;
-         break;
-       case SPU_BTI_U16_2:
-         /* This is only used in lqa, and stqa.  Even though the insns
-            encode 16 bits of the address (all but the 2 least
-            significant), only 14 bits are used because it is masked to
-            be 16 byte aligned. */
-         lsbits = 4;
-         break;
-       case SPU_BTI_S16_2:
-         /* This is used for lqr and stqr. */
-         lsbits = 2;
-         break;
-       default:
-         lsbits = 0;
-       }
-
-      if (GET_CODE (op) == LABEL_REF
-         || (GET_CODE (op) == SYMBOL_REF
-             && SYMBOL_REF_FUNCTION_P (op))
-         || (INTVAL (op) & ((1 << lsbits) - 1)) != 0)
-       warning (0, "%d least significant bits of %s are ignored.", lsbits,
-                d->name);
-    }
-}
-
-static void
-expand_builtin_args (struct spu_builtin_description *d, tree arglist,
-                    rtx target, rtx ops[])
-{
-  enum insn_code icode = d->icode;
-  int i = 0;
-
-  /* Expand the arguments into rtl. */
-
-  if (d->parm[0] != SPU_BTI_VOID)
-    ops[i++] = target;
-
-  for (; i < insn_data[icode].n_operands; i++)
-    {
-      tree arg = TREE_VALUE (arglist);
-      if (arg == 0)
-       abort ();
-      ops[i] = expand_expr (arg, NULL_RTX, VOIDmode, 0);
-      arglist = TREE_CHAIN (arglist);
-    }
-}
-
-static rtx
-spu_expand_builtin_1 (struct spu_builtin_description *d,
-                     tree arglist, rtx target)
-{
-  rtx pat;
-  rtx ops[8];
-  enum insn_code icode = d->icode;
-  enum machine_mode mode, tmode;
-  int i, p;
-  tree return_type;
-
-  /* Set up ops[] with values from arglist. */
-  expand_builtin_args (d, arglist, target, ops);
-
-  /* Handle the target operand which must be operand 0. */
-  i = 0;
-  if (d->parm[0] != SPU_BTI_VOID)
-    {
-
-      /* We prefer the mode specified for the match_operand otherwise
-         use the mode from the builtin function prototype. */
-      tmode = insn_data[d->icode].operand[0].mode;
-      if (tmode == VOIDmode)
-       tmode = TYPE_MODE (spu_builtin_types[d->parm[0]]);
-
-      /* Try to use target because not using it can lead to extra copies
-         and when we are using all of the registers extra copies leads
-         to extra spills.  */
-      if (target && GET_CODE (target) == REG && GET_MODE (target) == tmode)
-       ops[0] = target;
-      else
-       target = ops[0] = gen_reg_rtx (tmode);
-
-      if (!(*insn_data[icode].operand[0].predicate) (ops[0], tmode))
-       abort ();
-
-      i++;
-    }
-
-  /* Ignore align_hint, but still expand it's args in case they have
-     side effects. */
-  if (icode == CODE_FOR_spu_align_hint)
-    return 0;
-
-  /* Handle the rest of the operands. */
-  for (p = 1; i < insn_data[icode].n_operands; i++, p++)
-    {
-      if (insn_data[d->icode].operand[i].mode != VOIDmode)
-       mode = insn_data[d->icode].operand[i].mode;
-      else
-       mode = TYPE_MODE (spu_builtin_types[d->parm[i]]);
-
-      /* mode can be VOIDmode here for labels */
-
-      /* For specific intrinsics with an immediate operand, e.g.,
-         si_ai(), we sometimes need to convert the scalar argument to a
-         vector argument by splatting the scalar. */
-      if (VECTOR_MODE_P (mode)
-         && (GET_CODE (ops[i]) == CONST_INT
-             || GET_MODE_CLASS (GET_MODE (ops[i])) == MODE_INT
-             || GET_MODE_CLASS (GET_MODE (ops[i])) == MODE_FLOAT))
-       {
-         if (GET_CODE (ops[i]) == CONST_INT)
-           ops[i] = spu_const (mode, INTVAL (ops[i]));
-         else
-           {
-             rtx reg = gen_reg_rtx (mode);
-             enum machine_mode imode = GET_MODE_INNER (mode);
-             if (!spu_nonmem_operand (ops[i], GET_MODE (ops[i])))
-               ops[i] = force_reg (GET_MODE (ops[i]), ops[i]);
-             if (imode != GET_MODE (ops[i]))
-               ops[i] = convert_to_mode (imode, ops[i],
-                                         TYPE_UNSIGNED (spu_builtin_types
-                                                        [d->parm[i]]));
-             emit_insn (gen_spu_splats (reg, ops[i]));
-             ops[i] = reg;
-           }
-       }
-
-      if (!(*insn_data[icode].operand[i].predicate) (ops[i], mode))
-       ops[i] = spu_force_reg (mode, ops[i]);
-
-      spu_check_builtin_parm (d, ops[i], d->parm[p]);
-    }
-
-  switch (insn_data[icode].n_operands)
-    {
-    case 0:
-      pat = GEN_FCN (icode) (0);
-      break;
-    case 1:
-      pat = GEN_FCN (icode) (ops[0]);
-      break;
-    case 2:
-      pat = GEN_FCN (icode) (ops[0], ops[1]);
-      break;
-    case 3:
-      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2]);
-      break;
-    case 4:
-      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3]);
-      break;
-    case 5:
-      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3], ops[4]);
-      break;
-    case 6:
-      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3], ops[4], ops[5]);
-      break;
-    default:
-      abort ();
-    }
-
-  if (!pat)
-    abort ();
-
-  if (d->type == B_CALL || d->type == B_BISLED)
-    emit_call_insn (pat);
-  else if (d->type == B_JUMP)
-    {
-      emit_jump_insn (pat);
-      emit_barrier ();
-    }
-  else
-    emit_insn (pat);
-
-  return_type = spu_builtin_types[d->parm[0]];
-  if (d->parm[0] != SPU_BTI_VOID
-      && GET_MODE (target) != TYPE_MODE (return_type))
-    {
-      /* target is the return value.  It should always be the mode of
-         the builtin function prototype. */
-      target = spu_force_reg (TYPE_MODE (return_type), target);
-    }
 
-  return target;
-}
-
-rtx
-spu_expand_builtin (tree exp,
-                   rtx target,
-                   rtx subtarget ATTRIBUTE_UNUSED,
-                   enum machine_mode mode ATTRIBUTE_UNUSED,
-                   int ignore ATTRIBUTE_UNUSED)
+void
+spu_cpu_cpp_builtins (struct cpp_reader *pfile)
 {
-  tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
-  unsigned int fcode = DECL_FUNCTION_CODE (fndecl) - END_BUILTINS;
-  tree arglist = TREE_OPERAND (exp, 1);
-  struct spu_builtin_description *d;
-
-  if (fcode < NUM_SPU_BUILTINS)
-    {
-      d = &spu_builtins[fcode];
-
-      return spu_expand_builtin_1 (d, arglist, target);
-    }
-  abort ();
+  builtin_define_std ("__SPU__");
+  cpp_assert (pfile, "cpu=spu");
+  cpp_assert (pfile, "machine=spu");
+  builtin_define_std ("__vector=__attribute__((__spu_vector__))");
 }
 
-static rtx
-spu_force_reg (enum machine_mode mode, rtx op)
-{
-  rtx x, r;
-  if (GET_MODE (op) == VOIDmode || GET_MODE (op) == BLKmode)
-    {
-      if ((SCALAR_INT_MODE_P (mode) && GET_CODE (op) == CONST_INT)
-         || GET_MODE (op) == BLKmode)
-       return force_reg (mode, convert_to_mode (mode, op, 0));
-      abort ();
-    }
-
-  r = force_reg (GET_MODE (op), op);
-  if (GET_MODE_SIZE (GET_MODE (op)) == GET_MODE_SIZE (mode))
-    {
-      x = simplify_gen_subreg (mode, r, GET_MODE (op), 0);
-      if (x)
-       return x;
-    }
-
-  x = gen_reg_rtx (mode);
-  emit_insn (gen_spu_convert (x, r));
-  return x;
-}
index fc0ed19..a1158e7 100644 (file)
 #include "tree-gimple.h"
 #include "tm-constrs.h"
 #include "spu-builtins.h"
+
+/* Builtin types, data and prototypes. */
+struct spu_builtin_range
+{
+  int low, high;
+};
+
+static struct spu_builtin_range spu_builtin_range[] = {
+  {-0x40ll, 0x7fll},           /* SPU_BTI_7     */
+  {-0x40ll, 0x3fll},           /* SPU_BTI_S7    */
+  {0ll, 0x7fll},               /* SPU_BTI_U7    */
+  {-0x200ll, 0x1ffll},         /* SPU_BTI_S10   */
+  {-0x2000ll, 0x1fffll},       /* SPU_BTI_S10_4 */
+  {0ll, 0x3fffll},             /* SPU_BTI_U14   */
+  {-0x8000ll, 0xffffll},       /* SPU_BTI_16    */
+  {-0x8000ll, 0x7fffll},       /* SPU_BTI_S16   */
+  {-0x20000ll, 0x1ffffll},     /* SPU_BTI_S16_2 */
+  {0ll, 0xffffll},             /* SPU_BTI_U16   */
+  {0ll, 0x3ffffll},            /* SPU_BTI_U16_2 */
+  {0ll, 0x3ffffll},            /* SPU_BTI_U18   */
+};
+
 \f
 /*  Target specific attribute specifications.  */
 char regs_ever_allocated[FIRST_PSEUDO_REGISTER];
@@ -133,9 +155,6 @@ tree spu_builtin_types[SPU_BTI_MAX];
 #undef TARGET_INIT_BUILTINS
 #define TARGET_INIT_BUILTINS spu_init_builtins
 
-#undef TARGET_RESOLVE_OVERLOADED_BUILTIN
-#define TARGET_RESOLVE_OVERLOADED_BUILTIN  spu_resolve_overloaded_builtin
-
 #undef TARGET_EXPAND_BUILTIN
 #define TARGET_EXPAND_BUILTIN spu_expand_builtin
 
@@ -213,16 +232,6 @@ const struct attribute_spec spu_attribute_table[];
 
 struct gcc_target targetm = TARGET_INITIALIZER;
 
-void
-spu_cpu_cpp_builtins (struct cpp_reader *pfile)
-{
-  extern void builtin_define_std (const char *);
-  builtin_define_std ("__SPU__");
-  cpp_assert (pfile, "cpu=spu");
-  cpp_assert (pfile, "machine=spu");
-  builtin_define_std ("__vector=__attribute__((__spu_vector__))");
-}
-
 /* Sometimes certain combinations of command options do not make sense
    on a particular target machine.  You can define a macro
    OVERRIDE_OPTIONS to take account of this. This macro, if defined, is
@@ -231,9 +240,6 @@ void
 spu_override_options (void)
 {
 
-  /* Don't give warnings about the main() function. */
-  warn_main = 0;
-
   /* Override some of the default param values.  With so many registers
      larger values are better for these params.  */
   if (MAX_UNROLLED_INSNS == 100)
@@ -4467,3 +4473,266 @@ spu_expand_vector_init (rtx target, rtx vals)
        }
     }
 }
+
+static rtx
+spu_force_reg (enum machine_mode mode, rtx op)
+{
+  rtx x, r;
+  if (GET_MODE (op) == VOIDmode || GET_MODE (op) == BLKmode)
+    {
+      if ((SCALAR_INT_MODE_P (mode) && GET_CODE (op) == CONST_INT)
+         || GET_MODE (op) == BLKmode)
+       return force_reg (mode, convert_to_mode (mode, op, 0));
+      abort ();
+    }
+
+  r = force_reg (GET_MODE (op), op);
+  if (GET_MODE_SIZE (GET_MODE (op)) == GET_MODE_SIZE (mode))
+    {
+      x = simplify_gen_subreg (mode, r, GET_MODE (op), 0);
+      if (x)
+       return x;
+    }
+
+  x = gen_reg_rtx (mode);
+  emit_insn (gen_spu_convert (x, r));
+  return x;
+}
+
+static void
+spu_check_builtin_parm (struct spu_builtin_description *d, rtx op, int p)
+{
+  HOST_WIDE_INT v = 0;
+  int lsbits;
+  /* Check the range of immediate operands. */
+  if (p >= SPU_BTI_7 && p <= SPU_BTI_U18)
+    {
+      int range = p - SPU_BTI_7;
+      if (!CONSTANT_P (op)
+         || (GET_CODE (op) == CONST_INT
+             && (INTVAL (op) < spu_builtin_range[range].low
+                 || INTVAL (op) > spu_builtin_range[range].high)))
+       error ("%s expects an integer literal in the range [%d, %d].",
+              d->name,
+              spu_builtin_range[range].low, spu_builtin_range[range].high);
+
+      if (GET_CODE (op) == CONST
+         && (GET_CODE (XEXP (op, 0)) == PLUS
+             || GET_CODE (XEXP (op, 0)) == MINUS))
+       {
+         v = INTVAL (XEXP (XEXP (op, 0), 1));
+         op = XEXP (XEXP (op, 0), 0);
+       }
+      else if (GET_CODE (op) == CONST_INT)
+       v = INTVAL (op);
+
+      switch (p)
+       {
+       case SPU_BTI_S10_4:
+         lsbits = 4;
+         break;
+       case SPU_BTI_U16_2:
+         /* This is only used in lqa, and stqa.  Even though the insns
+            encode 16 bits of the address (all but the 2 least
+            significant), only 14 bits are used because it is masked to
+            be 16 byte aligned. */
+         lsbits = 4;
+         break;
+       case SPU_BTI_S16_2:
+         /* This is used for lqr and stqr. */
+         lsbits = 2;
+         break;
+       default:
+         lsbits = 0;
+       }
+
+      if (GET_CODE (op) == LABEL_REF
+         || (GET_CODE (op) == SYMBOL_REF
+             && SYMBOL_REF_FUNCTION_P (op))
+         || (INTVAL (op) & ((1 << lsbits) - 1)) != 0)
+       warning (0, "%d least significant bits of %s are ignored.", lsbits,
+                d->name);
+    }
+}
+
+
+static void
+expand_builtin_args (struct spu_builtin_description *d, tree arglist,
+                    rtx target, rtx ops[])
+{
+  enum insn_code icode = d->icode;
+  int i = 0;
+
+  /* Expand the arguments into rtl. */
+
+  if (d->parm[0] != SPU_BTI_VOID)
+    ops[i++] = target;
+
+  for (; i < insn_data[icode].n_operands; i++)
+    {
+      tree arg = TREE_VALUE (arglist);
+      if (arg == 0)
+       abort ();
+      ops[i] = expand_expr (arg, NULL_RTX, VOIDmode, 0);
+      arglist = TREE_CHAIN (arglist);
+    }
+}
+
+static rtx
+spu_expand_builtin_1 (struct spu_builtin_description *d,
+                     tree arglist, rtx target)
+{
+  rtx pat;
+  rtx ops[8];
+  enum insn_code icode = d->icode;
+  enum machine_mode mode, tmode;
+  int i, p;
+  tree return_type;
+
+  /* Set up ops[] with values from arglist. */
+  expand_builtin_args (d, arglist, target, ops);
+
+  /* Handle the target operand which must be operand 0. */
+  i = 0;
+  if (d->parm[0] != SPU_BTI_VOID)
+    {
+
+      /* We prefer the mode specified for the match_operand otherwise
+         use the mode from the builtin function prototype. */
+      tmode = insn_data[d->icode].operand[0].mode;
+      if (tmode == VOIDmode)
+       tmode = TYPE_MODE (spu_builtin_types[d->parm[0]]);
+
+      /* Try to use target because not using it can lead to extra copies
+         and when we are using all of the registers extra copies leads
+         to extra spills.  */
+      if (target && GET_CODE (target) == REG && GET_MODE (target) == tmode)
+       ops[0] = target;
+      else
+       target = ops[0] = gen_reg_rtx (tmode);
+
+      if (!(*insn_data[icode].operand[0].predicate) (ops[0], tmode))
+       abort ();
+
+      i++;
+    }
+
+  /* Ignore align_hint, but still expand it's args in case they have
+     side effects. */
+  if (icode == CODE_FOR_spu_align_hint)
+    return 0;
+
+  /* Handle the rest of the operands. */
+  for (p = 1; i < insn_data[icode].n_operands; i++, p++)
+    {
+      if (insn_data[d->icode].operand[i].mode != VOIDmode)
+       mode = insn_data[d->icode].operand[i].mode;
+      else
+       mode = TYPE_MODE (spu_builtin_types[d->parm[i]]);
+
+      /* mode can be VOIDmode here for labels */
+
+      /* For specific intrinsics with an immediate operand, e.g.,
+         si_ai(), we sometimes need to convert the scalar argument to a
+         vector argument by splatting the scalar. */
+      if (VECTOR_MODE_P (mode)
+         && (GET_CODE (ops[i]) == CONST_INT
+             || GET_MODE_CLASS (GET_MODE (ops[i])) == MODE_INT
+             || GET_MODE_CLASS (GET_MODE (ops[i])) == MODE_FLOAT))
+       {
+         if (GET_CODE (ops[i]) == CONST_INT)
+           ops[i] = spu_const (mode, INTVAL (ops[i]));
+         else
+           {
+             rtx reg = gen_reg_rtx (mode);
+             enum machine_mode imode = GET_MODE_INNER (mode);
+             if (!spu_nonmem_operand (ops[i], GET_MODE (ops[i])))
+               ops[i] = force_reg (GET_MODE (ops[i]), ops[i]);
+             if (imode != GET_MODE (ops[i]))
+               ops[i] = convert_to_mode (imode, ops[i],
+                                         TYPE_UNSIGNED (spu_builtin_types
+                                                        [d->parm[i]]));
+             emit_insn (gen_spu_splats (reg, ops[i]));
+             ops[i] = reg;
+           }
+       }
+
+      if (!(*insn_data[icode].operand[i].predicate) (ops[i], mode))
+       ops[i] = spu_force_reg (mode, ops[i]);
+
+      spu_check_builtin_parm (d, ops[i], d->parm[p]);
+    }
+
+  switch (insn_data[icode].n_operands)
+    {
+    case 0:
+      pat = GEN_FCN (icode) (0);
+      break;
+    case 1:
+      pat = GEN_FCN (icode) (ops[0]);
+      break;
+    case 2:
+      pat = GEN_FCN (icode) (ops[0], ops[1]);
+      break;
+    case 3:
+      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2]);
+      break;
+    case 4:
+      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3]);
+      break;
+    case 5:
+      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3], ops[4]);
+      break;
+    case 6:
+      pat = GEN_FCN (icode) (ops[0], ops[1], ops[2], ops[3], ops[4], ops[5]);
+      break;
+    default:
+      abort ();
+    }
+
+  if (!pat)
+    abort ();
+
+  if (d->type == B_CALL || d->type == B_BISLED)
+    emit_call_insn (pat);
+  else if (d->type == B_JUMP)
+    {
+      emit_jump_insn (pat);
+      emit_barrier ();
+    }
+  else
+    emit_insn (pat);
+
+  return_type = spu_builtin_types[d->parm[0]];
+  if (d->parm[0] != SPU_BTI_VOID
+      && GET_MODE (target) != TYPE_MODE (return_type))
+    {
+      /* target is the return value.  It should always be the mode of
+         the builtin function prototype. */
+      target = spu_force_reg (TYPE_MODE (return_type), target);
+    }
+
+  return target;
+}
+
+rtx
+spu_expand_builtin (tree exp,
+                   rtx target,
+                   rtx subtarget ATTRIBUTE_UNUSED,
+                   enum machine_mode mode ATTRIBUTE_UNUSED,
+                   int ignore ATTRIBUTE_UNUSED)
+{
+  tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
+  unsigned int fcode = DECL_FUNCTION_CODE (fndecl) - END_BUILTINS;
+  tree arglist = TREE_OPERAND (exp, 1);
+  struct spu_builtin_description *d;
+
+  if (fcode < NUM_SPU_BUILTINS)
+    {
+      d = &spu_builtins[fcode];
+
+      return spu_expand_builtin_1 (d, arglist, target);
+    }
+  abort ();
+}
+
index a9714cb..b56ff14 100644 (file)
@@ -238,6 +238,12 @@ enum reg_class {
         ((GET_MODE_SIZE (FROM) > 4 || GET_MODE_SIZE (TO) > 4) \
         && GET_MODE_SIZE (FROM) != GET_MODE_SIZE (TO))
 
+#define REGISTER_TARGET_PRAGMAS() do {                                 \
+targetm.resolve_overloaded_builtin = spu_resolve_overloaded_builtin;   \
+  /* Don't give warnings about the main() function. */                 \
+warn_main = 0;                                                         \
+}while (0);
+
 \f
 /* Frame Layout */