This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [ARM] ARM NEON support part 2/7: NEON support


Mark Mitchell wrote:
Julian Brown wrote:
Paul Brook wrote:
This patch adds support for the NEON ISA, including RTL patterns which
can be used for autovectorization (some current features may not yet be
supported, however), and a (large) set of intrinsics. The latter are
provided via an auto-generated header file, "arm_neon.h", which should
provide the same capabilities as the header file of the same name
supplied with ARM's proprietary compiler tools.
Ok, except a couple of tweaks, and if you haven't already done so you
need to get a c++ maintainer to sign off on the new target hook.
C++ maintainers: is the new target hook bit OK?

I think it would be slightly better to rename the existing mangle_fundamental_type hook to just plain mangle_type, and then call it for all types. Then, if we find yet another case where we need back-end help for mangling, we already have the hook we need.

OK with that change.

I've tried this: it's a slight semantic change for the target hook too, since it's now called with a type argument which has not been resolved to its main variant (typedefs are not looked through before invoking the hook). I've changed tm.texi to that effect, and tweaked several backends which used the previous hook to use the new one instead.


I've tested (with the rest of the Neon support patch) on ARM with no regressions, and also natively on x86. Other affected backends are alpha, ia64, rs6000, s390 and sparc, though the changes are pretty trivial. I don't think I have the capacity to test all those targets in a reasonable time frame though -- so if anyone wants to volunteer to test their favourite target with this patch, I'd be grateful.

Alternatively, is it OK to commit as-is without further testing?

Cheers,

Julian

ChangeLog

    gcc/
    * config/alpha/alpha.c (alpha_mangle_fundamental_type): Rename to...
    (alpha_mangle_type): This.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * config/arm/arm-protos.h (arm_mangle_type): Add prototype.
    * config/arm/arm.c (TARGET_MANGLE_TYPE): Define target hook.
    (arm_init_neon_builtins): Fix comment.
    (arm_mangle_map_entry): New.
    (arm_mangle_map): New.
    (arm_mangle_type): New.
    * config/i386/i386.c (ix86_mangle_fundamental_type): Rename to...
    (ix86_mangle_type): This. Use TYPE_MAIN_VARIANT and restrict
    mangled types to VOID_TYPE, BOOLEAN_TYPE, INTEGER_TYPE, REAL_TYPE.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * config/ia64/ia64.c (ia64_mangle_fundamental_type): Rename to...
    (ia64_mangle_type): This. Use TYPE_MAIN_VARIANT  and restrict
    mangled types to VOID_TYPE, BOOLEAN_TYPE, INTEGER_TYPE, REAL_TYPE.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * config/rs6000/rs6000.c (rs6000_mangle_fundamental_type): Rename
    to...
    (rs6000_mangle_type): This. Use TYPE_MAIN_VARIANT.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * config/s390/s390.c (s390_mangle_fundamental_type): Rename to...
    (s390_mangle_type): This.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * config/sparc/sparc.c (sparc_mangle_fundamental_type): Rename to...
    (sparc_mangle_type): This.
    (TARGET_MANGLE_FUNDAMENTAL_TYPE): Don't define.
    (TARGET_MANGLE_TYPE): Define this instead.
    * cp/mangle.c (write_type): Call mangle_type target hook on all
    types before mangling.  Use original type, not main variant, as
    argument.
    * target-def.h (TARGET_MANGLE_FUNDAMENTAL_TYPE): Rename hook to...
    (TARGET_MANGLE_TYPE): This.
    * target.h (gcc_target): Rename mangle_fundamental_type to
    mangle_type.
    * doc/tm.texi (TARGET_MANGLE_FUNDAMENTAL_TYPE): Rename section to...
    (TARGET_MANGLE_TYPE): This. Note slightly different semantics.
--- .pc/type-mangling/gcc/config/alpha/alpha.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/alpha/alpha.c	2007-07-16 12:29:09.000000000 -0700
@@ -238,10 +238,10 @@ alpha_handle_option (size_t code, const 
 }
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-/* Implement TARGET_MANGLE_FUNDAMENTAL_TYPE.  */
+/* Implement TARGET_MANGLE_TYPE.  */
 
 static const char *
-alpha_mangle_fundamental_type (tree type)
+alpha_mangle_type (tree type)
 {
   if (TYPE_MAIN_VARIANT (type) == long_double_type_node
       && TARGET_LONG_DOUBLE_128)
@@ -10709,8 +10709,8 @@ alpha_init_libfuncs (void)
 #define TARGET_HANDLE_OPTION alpha_handle_option
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE alpha_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE alpha_mangle_type
 #endif
 
 struct gcc_target targetm = TARGET_INITIALIZER;
--- .pc/type-mangling/gcc/config/arm/arm-protos.h	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/arm/arm-protos.h	2007-07-16 12:29:09.000000000 -0700
@@ -210,4 +210,6 @@ extern void arm_pr_long_calls (struct cp
 extern void arm_pr_no_long_calls (struct cpp_reader *);
 extern void arm_pr_long_calls_off (struct cpp_reader *);
 
+extern const char *arm_mangle_type (tree);
+
 #endif /* ! GCC_ARM_PROTOS_H */
--- .pc/type-mangling/gcc/config/arm/arm.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/arm/arm.c	2007-07-16 12:29:09.000000000 -0700
@@ -382,6 +382,9 @@ static void arm_output_dwarf_dtprel (FIL
 #undef TARGET_CANNOT_FORCE_CONST_MEM
 #define TARGET_CANNOT_FORCE_CONST_MEM arm_tls_referenced_p
 
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE arm_mangle_type
+
 #ifdef HAVE_AS_TLS
 #undef TARGET_ASM_OUTPUT_DWARF_DTPREL
 #define TARGET_ASM_OUTPUT_DWARF_DTPREL arm_output_dwarf_dtprel
@@ -14825,7 +14828,7 @@ arm_init_neon_builtins (void)
 
   /* Define typedefs which exactly correspond to the modes we are basing vector
      types on.  If you change these names you'll need to change
-     the table used by arm_mangle_vector_type too.  */
+     the table used by arm_mangle_type too.  */
   (*lang_hooks.types.register_builtin_type) (neon_intQI_type_node,
 					     "__builtin_neon_qi");
   (*lang_hooks.types.register_builtin_type) (neon_intHI_type_node,
@@ -18829,4 +18832,69 @@ thumb2_output_casesi (rtx *operands)
     }
 }
 
+/* A table and a function to perform ARM-specific name mangling for
+   NEON vector types in order to conform to the AAPCS (see "Procedure
+   Call Standard for the ARM Architecture", Appendix A).  To qualify
+   for emission with the mangled names defined in that document, a
+   vector type must not only be of the correct mode but also be
+   composed of NEON vector element types (e.g. __builtin_neon_qi).  */
+typedef struct
+{
+  enum machine_mode mode;
+  const char *element_type_name;
+  const char *aapcs_name;
+} arm_mangle_map_entry;
+
+static arm_mangle_map_entry arm_mangle_map[] = {
+  /* 64-bit containerized types.  */
+  { V8QImode,  "__builtin_neon_qi",     "15__simd64_int8_t" },
+  { V8QImode,  "__builtin_neon_uqi",    "16__simd64_uint8_t" },
+  { V4HImode,  "__builtin_neon_hi",     "16__simd64_int16_t" },
+  { V4HImode,  "__builtin_neon_uhi",    "17__simd64_uint16_t" },
+  { V2SImode,  "__builtin_neon_si",     "16__simd64_int32_t" },
+  { V2SImode,  "__builtin_neon_usi",    "17__simd64_uint32_t" },
+  { V2SFmode,  "__builtin_neon_sf",     "18__simd64_float32_t" },
+  { V8QImode,  "__builtin_neon_poly8",  "16__simd64_poly8_t" },
+  { V4HImode,  "__builtin_neon_poly16", "17__simd64_poly16_t" },
+  /* 128-bit containerized types.  */
+  { V16QImode, "__builtin_neon_qi",     "16__simd128_int8_t" },
+  { V16QImode, "__builtin_neon_uqi",    "17__simd128_uint8_t" },
+  { V8HImode,  "__builtin_neon_hi",     "17__simd128_int16_t" },
+  { V8HImode,  "__builtin_neon_uhi",    "18__simd128_uint16_t" },
+  { V4SImode,  "__builtin_neon_si",     "17__simd128_int32_t" },
+  { V4SImode,  "__builtin_neon_usi",    "18__simd128_uint32_t" },
+  { V4SFmode,  "__builtin_neon_sf",     "19__simd128_float32_t" },
+  { V16QImode, "__builtin_neon_poly8",  "17__simd128_poly8_t" },
+  { V8HImode,  "__builtin_neon_poly16", "18__simd128_poly16_t" },
+  { VOIDmode, NULL, NULL }
+};
+
+const char *
+arm_mangle_type (tree type)
+{
+  arm_mangle_map_entry *pos = arm_mangle_map;
+
+  if (TREE_CODE (type) != VECTOR_TYPE)
+    return NULL;
+
+  /* Check the mode of the vector type, and the name of the vector
+     element type, against the table.  */
+  while (pos->mode != VOIDmode)
+    {
+      tree elt_type = TREE_TYPE (type);
+
+      if (pos->mode == TYPE_MODE (type)
+	  && TREE_CODE (TYPE_NAME (elt_type)) == TYPE_DECL
+	  && !strcmp (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (elt_type))),
+		      pos->element_type_name))
+        return pos->aapcs_name;
+
+      pos++;
+    }
+
+  /* Use the default mangling for unrecognized (possibly user-defined)
+     vector types.  */
+  return NULL;
+}
+
 #include "gt-arm.h"
--- .pc/type-mangling/gcc/config/i386/i386.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/i386/i386.c	2007-07-16 12:29:09.000000000 -0700
@@ -22707,8 +22707,14 @@ i386_solaris_elf_named_section (const ch
 /* Return the mangling of TYPE if it is an extended fundamental type.  */
 
 static const char *
-ix86_mangle_fundamental_type (tree type)
+ix86_mangle_type (tree type)
 {
+  type = TYPE_MAIN_VARIANT (type);
+
+  if (TREE_CODE (type) != VOID_TYPE && TREE_CODE (type) != BOOLEAN_TYPE
+      && TREE_CODE (type) != INTEGER_TYPE && TREE_CODE (type) != REAL_TYPE)
+    return NULL;
+
   switch (TYPE_MODE (type))
     {
     case TFmode:
@@ -23539,8 +23545,8 @@ static const struct attribute_spec ix86_
 #define TARGET_INSERT_ATTRIBUTES SUBTARGET_INSERT_ATTRIBUTES
 #endif
 
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE ix86_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE ix86_mangle_type
 
 #undef TARGET_STACK_PROTECT_FAIL
 #define TARGET_STACK_PROTECT_FAIL ix86_stack_protect_fail
--- .pc/type-mangling/gcc/config/ia64/ia64.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/ia64/ia64.c	2007-07-16 12:29:09.000000000 -0700
@@ -279,7 +279,7 @@ static tree ia64_gimplify_va_arg (tree, 
 static bool ia64_scalar_mode_supported_p (enum machine_mode mode);
 static bool ia64_vector_mode_supported_p (enum machine_mode mode);
 static bool ia64_cannot_force_const_mem (rtx);
-static const char *ia64_mangle_fundamental_type (tree);
+static const char *ia64_mangle_type (tree);
 static const char *ia64_invalid_conversion (tree, tree);
 static const char *ia64_invalid_unary_op (int, tree);
 static const char *ia64_invalid_binary_op (int, tree, tree);
@@ -476,8 +476,8 @@ static const struct attribute_spec ia64_
 #undef TARGET_CANNOT_FORCE_CONST_MEM
 #define TARGET_CANNOT_FORCE_CONST_MEM ia64_cannot_force_const_mem
 
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE ia64_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE ia64_mangle_type
 
 #undef TARGET_INVALID_CONVERSION
 #define TARGET_INVALID_CONVERSION ia64_invalid_conversion
@@ -9739,8 +9739,14 @@ ia64_profile_hook (int labelno)
 /* Return the mangling of TYPE if it is an extended fundamental type.  */
 
 static const char *
-ia64_mangle_fundamental_type (tree type)
+ia64_mangle_type (tree type)
 {
+  type = TYPE_MAIN_VARIANT (type);
+
+  if (TREE_CODE (type) != VOID_TYPE && TREE_CODE (type) != BOOLEAN_TYPE
+      && TREE_CODE (type) != INTEGER_TYPE && TREE_CODE (type) != REAL_TYPE)
+    return NULL;
+
   /* On HP-UX, "long double" is mangled as "e" so __float128 is
      mangled as "e".  */
   if (!TARGET_HPUX && TYPE_MODE (type) == TFmode)
--- .pc/type-mangling/gcc/config/rs6000/rs6000.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/rs6000/rs6000.c	2007-07-16 12:29:10.000000000 -0700
@@ -643,7 +643,7 @@ static tree rs6000_handle_altivec_attrib
 static bool rs6000_ms_bitfield_layout_p (tree);
 static tree rs6000_handle_struct_attribute (tree *, tree, tree, int, bool *);
 static void rs6000_eliminate_indexed_memrefs (rtx operands[2]);
-static const char *rs6000_mangle_fundamental_type (tree);
+static const char *rs6000_mangle_type (tree);
 extern const struct attribute_spec rs6000_attribute_table[];
 static void rs6000_set_default_type_attributes (tree);
 static bool rs6000_reg_live_or_pic_offset_p (int);
@@ -994,8 +994,8 @@ static const char alt_reg_names[][8] =
 #undef TARGET_EXPAND_BUILTIN
 #define TARGET_EXPAND_BUILTIN rs6000_expand_builtin
 
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE rs6000_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE rs6000_mangle_type
 
 #undef TARGET_INIT_LIBFUNCS
 #define TARGET_INIT_LIBFUNCS rs6000_init_libfuncs
@@ -18884,8 +18884,14 @@ rs6000_handle_altivec_attribute (tree *n
    elements; we must teach the compiler how to mangle them.  */
 
 static const char *
-rs6000_mangle_fundamental_type (tree type)
+rs6000_mangle_type (tree type)
 {
+  type = TYPE_MAIN_VARIANT (type);
+
+  if (TREE_CODE (type) != VOID_TYPE && TREE_CODE (type) != BOOLEAN_TYPE
+      && TREE_CODE (type) != INTEGER_TYPE && TREE_CODE (type) != REAL_TYPE)
+    return NULL;
+
   if (type == bool_char_type_node) return "U6__boolc";
   if (type == bool_short_type_node) return "U6__bools";
   if (type == pixel_type_node) return "u7__pixel";
--- .pc/type-mangling/gcc/config/s390/s390.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/s390/s390.c	2007-07-16 12:29:10.000000000 -0700
@@ -4368,10 +4368,10 @@ s390_output_dwarf_dtprel (FILE *file, in
 }
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-/* Implement TARGET_MANGLE_FUNDAMENTAL_TYPE.  */
+/* Implement TARGET_MANGLE_TYPE.  */
 
 static const char *
-s390_mangle_fundamental_type (tree type)
+s390_mangle_type (tree type)
 {
   if (TYPE_MAIN_VARIANT (type) == long_double_type_node
       && TARGET_LONG_DOUBLE_128)
@@ -9343,8 +9343,8 @@ s390_reorg (void)
 #endif
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE s390_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE s390_mangle_type
 #endif
 
 #undef TARGET_SCALAR_MODE_SUPPORTED_P
--- .pc/type-mangling/gcc/config/sparc/sparc.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/config/sparc/sparc.c	2007-07-16 12:29:10.000000000 -0700
@@ -396,7 +396,7 @@ static void sparc_dwarf_handle_frame_uns
 static void sparc_output_dwarf_dtprel (FILE *, int, rtx) ATTRIBUTE_UNUSED;
 static void sparc_file_end (void);
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-static const char *sparc_mangle_fundamental_type (tree);
+static const char *sparc_mangle_type (tree);
 #endif
 #ifdef SUBTARGET_ATTRIBUTE_TABLE
 const struct attribute_spec sparc_attribute_table[];
@@ -558,8 +558,8 @@ static bool fpu_option_set = false;
 #define TARGET_ASM_FILE_END sparc_file_end
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-#undef TARGET_MANGLE_FUNDAMENTAL_TYPE
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE sparc_mangle_fundamental_type
+#undef TARGET_MANGLE_TYPE
+#define TARGET_MANGLE_TYPE sparc_mangle_type
 #endif
 
 struct gcc_target targetm = TARGET_INITIALIZER;
@@ -8888,10 +8888,10 @@ sparc_file_end (void)
 }
 
 #ifdef TARGET_ALTERNATE_LONG_DOUBLE_MANGLING
-/* Implement TARGET_MANGLE_FUNDAMENTAL_TYPE.  */
+/* Implement TARGET_MANGLE_TYPE.  */
 
 static const char *
-sparc_mangle_fundamental_type (tree type)
+sparc_mangle_type (tree type)
 {
   if (!TARGET_64BIT
       && TYPE_MAIN_VARIANT (type) == long_double_type_node
--- .pc/type-mangling/gcc/cp/mangle.c	2007-07-16 12:27:24.000000000 -0700
+++ gcc/cp/mangle.c	2007-07-16 12:29:10.000000000 -0700
@@ -1575,21 +1575,18 @@ write_type (tree type)
     write_array_type (type);
   else
     {
+      tree type_orig = type;
+
       /* See through any typedefs.  */
       type = TYPE_MAIN_VARIANT (type);
 
       if (TYPE_PTRMEM_P (type))
 	write_pointer_to_member_type (type);
-      else switch (TREE_CODE (type))
-	{
-	case VOID_TYPE:
-	case BOOLEAN_TYPE:
-	case INTEGER_TYPE:  /* Includes wchar_t.  */
-	case REAL_TYPE:
-	{
+      else
+        {
 	  /* Handle any target-specific fundamental types.  */
 	  const char *target_mangling
-	    = targetm.mangle_fundamental_type (type);
+	    = targetm.mangle_type (type_orig);
 
 	  if (target_mangling)
 	    {
@@ -1597,81 +1594,89 @@ write_type (tree type)
 	      return;
 	    }
 
-	  /* If this is a typedef, TYPE may not be one of
-	     the standard builtin type nodes, but an alias of one.  Use
-	     TYPE_MAIN_VARIANT to get to the underlying builtin type.  */
-	  write_builtin_type (TYPE_MAIN_VARIANT (type));
-	  ++is_builtin_type;
-	  break;
-	}
-
-	case COMPLEX_TYPE:
-	  write_char ('C');
-	  write_type (TREE_TYPE (type));
-	  break;
-
-	case FUNCTION_TYPE:
-	case METHOD_TYPE:
-	  write_function_type (type);
-	  break;
-
-	case UNION_TYPE:
-	case RECORD_TYPE:
-	case ENUMERAL_TYPE:
-	  /* A pointer-to-member function is represented as a special
-	     RECORD_TYPE, so check for this first.  */
-	  if (TYPE_PTRMEMFUNC_P (type))
-	    write_pointer_to_member_type (type);
-	  else
-	    write_class_enum_type (type);
-	  break;
-
-	case TYPENAME_TYPE:
-	case UNBOUND_CLASS_TEMPLATE:
-	  /* We handle TYPENAME_TYPEs and UNBOUND_CLASS_TEMPLATEs like
-	     ordinary nested names.  */
-	  write_nested_name (TYPE_STUB_DECL (type));
-	  break;
-
-	case POINTER_TYPE:
-	  write_char ('P');
-	  write_type (TREE_TYPE (type));
-	  break;
-
-	case REFERENCE_TYPE:
-	  if (TYPE_REF_IS_RVALUE (type))
-            write_char('R');
-	  write_char ('R');
-	  write_type (TREE_TYPE (type));
-	  break;
-
-	case TEMPLATE_TYPE_PARM:
-	case TEMPLATE_PARM_INDEX:
-	  write_template_param (type);
-	  break;
-
-	case TEMPLATE_TEMPLATE_PARM:
-	  write_template_template_param (type);
-	  break;
-
-	case BOUND_TEMPLATE_TEMPLATE_PARM:
-	  write_template_template_param (type);
-	  write_template_args
-	    (TI_ARGS (TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO (type)));
-	  break;
+	  switch (TREE_CODE (type))
+	    {
+	    case VOID_TYPE:
+	    case BOOLEAN_TYPE:
+	    case INTEGER_TYPE:  /* Includes wchar_t.  */
+	    case REAL_TYPE:
+	      {
+		/* If this is a typedef, TYPE may not be one of
+		   the standard builtin type nodes, but an alias of one.  Use
+		   TYPE_MAIN_VARIANT to get to the underlying builtin type.  */
+		write_builtin_type (TYPE_MAIN_VARIANT (type));
+		++is_builtin_type;
+	      }
+	      break;
 
-	case VECTOR_TYPE:
-	  write_string ("U8__vector");
-	  write_type (TREE_TYPE (type));
-	  break;
+	    case COMPLEX_TYPE:
+	      write_char ('C');
+	      write_type (TREE_TYPE (type));
+	      break;
+
+	    case FUNCTION_TYPE:
+	    case METHOD_TYPE:
+	      write_function_type (type);
+	      break;
+
+	    case UNION_TYPE:
+	    case RECORD_TYPE:
+	    case ENUMERAL_TYPE:
+	      /* A pointer-to-member function is represented as a special
+		 RECORD_TYPE, so check for this first.  */
+	      if (TYPE_PTRMEMFUNC_P (type))
+		write_pointer_to_member_type (type);
+	      else
+		write_class_enum_type (type);
+	      break;
 
-        case TYPE_PACK_EXPANSION:
-          write_string ("U10__variadic");
-          write_type (PACK_EXPANSION_PATTERN (type));
-          break;
+	    case TYPENAME_TYPE:
+	    case UNBOUND_CLASS_TEMPLATE:
+	      /* We handle TYPENAME_TYPEs and UNBOUND_CLASS_TEMPLATEs like
+		 ordinary nested names.  */
+	      write_nested_name (TYPE_STUB_DECL (type));
+	      break;
+
+	    case POINTER_TYPE:
+	      write_char ('P');
+	      write_type (TREE_TYPE (type));
+	      break;
+
+	    case REFERENCE_TYPE:
+	      if (TYPE_REF_IS_RVALUE (type))
+        	write_char('R');
+	      write_char ('R');
+	      write_type (TREE_TYPE (type));
+	      break;
+
+	    case TEMPLATE_TYPE_PARM:
+	    case TEMPLATE_PARM_INDEX:
+	      write_template_param (type);
+	      break;
+
+	    case TEMPLATE_TEMPLATE_PARM:
+	      write_template_template_param (type);
+	      break;
+
+	    case BOUND_TEMPLATE_TEMPLATE_PARM:
+	      write_template_template_param (type);
+	      write_template_args
+		(TI_ARGS (TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO (type)));
+	      break;
+
+	    case VECTOR_TYPE:
+	      write_string ("U8__vector");
+	      write_type (TREE_TYPE (type));
+	      break;
+
+            case TYPE_PACK_EXPANSION:
+              write_string ("U10__variadic");
+              write_type (PACK_EXPANSION_PATTERN (type));
+              break;
 
-	default:
-	  gcc_unreachable ();
+	    default:
+	      gcc_unreachable ();
+	    }
 	}
     }
 
--- .pc/type-mangling/gcc/target-def.h	2007-07-16 12:27:24.000000000 -0700
+++ gcc/target-def.h	2007-07-16 12:29:10.000000000 -0700
@@ -468,7 +468,7 @@ Foundation, 51 Franklin Street, Fifth Fl
 #define TARGET_ALIGN_ANON_BITFIELD hook_bool_void_false
 #define TARGET_NARROW_VOLATILE_BITFIELD hook_bool_void_false
 #define TARGET_RTX_COSTS hook_bool_rtx_int_int_intp_false
-#define TARGET_MANGLE_FUNDAMENTAL_TYPE hook_constcharptr_tree_null
+#define TARGET_MANGLE_TYPE hook_constcharptr_tree_null
 #define TARGET_ALLOCATE_INITIAL_VALUE NULL
 
 #ifndef TARGET_INIT_LIBFUNCS
@@ -696,7 +696,7 @@ Foundation, 51 Franklin Street, Fifth Fl
   TARGET_RESOLVE_OVERLOADED_BUILTIN,		\
   TARGET_FOLD_BUILTIN,				\
   TARGET_BUILTIN_RECIPROCAL,			\
-  TARGET_MANGLE_FUNDAMENTAL_TYPE,		\
+  TARGET_MANGLE_TYPE,				\
   TARGET_INIT_LIBFUNCS,				\
   TARGET_SECTION_TYPE_FLAGS,			\
   TARGET_CANNOT_MODIFY_JUMPS_P,			\
--- .pc/type-mangling/gcc/target.h	2007-07-16 12:27:24.000000000 -0700
+++ gcc/target.h	2007-07-16 12:29:10.000000000 -0700
@@ -505,10 +505,10 @@ struct gcc_target
      reciprocal of the function, or NULL_TREE if not available.  */
   tree (* builtin_reciprocal) (unsigned, bool, bool);
 
-  /* For a vendor-specific fundamental TYPE, return a pointer to
-     a statically-allocated string containing the C++ mangling for
-     TYPE.  In all other cases, return NULL.  */
-  const char * (* mangle_fundamental_type) (tree type);
+  /* For a vendor-specific TYPE, return a pointer to a statically-allocated
+     string containing the C++ mangling for TYPE.  In all other cases, return
+     NULL.  */
+  const char * (* mangle_type) (tree type);
 
   /* Make any adjustments to libfunc names needed for this target.  */
   void (* init_libfuncs) (void);
--- .pc/type-mangling/gcc/doc/tm.texi	2007-07-12 12:17:20.000000000 -0700
+++ gcc/doc/tm.texi	2007-07-16 13:15:43.000000000 -0700
@@ -1502,15 +1502,16 @@ may affect its placement.
 Returns true if the target supports decimal floating point.
 @end deftypefn
 
-@deftypefn {Target Hook} {const char *} TARGET_MANGLE_FUNDAMENTAL_TYPE (tree @var{type})
-If your target defines any fundamental types, define this hook to
-return the appropriate encoding for these types as part of a C++
-mangled name.  The @var{type} argument is the tree structure
-representing the type to be mangled.  The hook may be applied to trees
-which are not target-specific fundamental types; it should return
-@code{NULL} for all such types, as well as arguments it does not
-recognize.  If the return value is not @code{NULL}, it must point to
-a statically-allocated string constant.
+@deftypefn {Target Hook} {const char *} TARGET_MANGLE_TYPE (tree @var{type})
+If your target defines any fundamental types, or any types your target
+uses should be mangled differently from the default, define this hook
+to return the appropriate encoding for these types as part of a C++
+mangled name.  The @var{type} argument is the tree structure representing
+the type to be mangled.  The hook may be applied to trees which are
+not target-specific fundamental types; it should return @code{NULL}
+for all such types, as well as arguments it does not recognize.  If the
+return value is not @code{NULL}, it must point to a statically-allocated
+string constant.
 
 Target-specific fundamental types might be new fundamental types or
 qualified versions of ordinary fundamental types.  Encode new
@@ -1525,6 +1526,11 @@ code used to represent the unqualified v
 codes.)  In both cases the spaces are for clarity; do not include any
 spaces in your string.
 
+This hook is applied to types prior to typedef resolution.  If the mangled
+name for a particular type depends only on that type's main variant, you
+can perform typedef resolution yourself using @code{TYPE_MAIN_VARIANT}
+before mangling.
+
 The default version of this hook always returns @code{NULL}, which is
 appropriate for a target that does not define any new fundamental
 types.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]