diff mbox

C++ PATCH for c++/49932 (ICE mangling decltype()::)

Message ID 4E3713A1.7050100@redhat.com
State New
Headers show

Commit Message

Jason Merrill Aug. 1, 2011, 8:59 p.m. UTC
Needed to add mangling and demangling support for the recently added 
support for decltype as a nested-name-specifier.

Tested x86_64-pc-linux-gnu, applying to trunk.
diff mbox

Patch

commit fe8dd6eeab2b171504b87937021eb39a13828b77
Author: Jason Merrill <jason@redhat.com>
Date:   Mon Aug 1 16:16:20 2011 -0400

    	PR c++/49932
    gcc/cp/
    	* mangle.c (write_prefix): Handle decltype.
    libiberty/
    	* cp-demangle.c (d_prefix): Handle decltype.

diff --git a/gcc/cp/mangle.c b/gcc/cp/mangle.c
index 4a83c9a..eb3f144 100644
--- a/gcc/cp/mangle.c
+++ b/gcc/cp/mangle.c
@@ -952,6 +952,7 @@  write_nested_name (const tree decl)
 /* <prefix> ::= <prefix> <unqualified-name>
 	    ::= <template-param>
 	    ::= <template-prefix> <template-args>
+	    ::= <decltype>
 	    ::= # empty
 	    ::= <substitution>  */
 
@@ -968,6 +969,12 @@  write_prefix (const tree node)
 
   MANGLE_TRACE_TREE ("prefix", node);
 
+  if (TREE_CODE (node) == DECLTYPE_TYPE)
+    {
+      write_type (node);
+      return;
+    }
+
   if (find_substitution (node))
     return;
 
diff --git a/gcc/testsuite/g++.dg/abi/mangle49.C b/gcc/testsuite/g++.dg/abi/mangle49.C
new file mode 100644
index 0000000..a258dc2
--- /dev/null
+++ b/gcc/testsuite/g++.dg/abi/mangle49.C
@@ -0,0 +1,22 @@ 
+// PR c++/49932
+// { dg-options "-std=c++0x -fabi-version=0" }
+
+template < typename T >
+auto
+f1( T x ) // ICE on here
+  -> typename decltype( x )::type {}
+
+template < typename T >
+typename decltype( T() )::type
+f2( T x ) {} // ICE on here
+
+struct S { typedef void type; };
+
+void g()
+{
+  f1( S() );
+  f2( S() );
+}
+
+// { dg-final { scan-assembler "_Z2f1I1SENDtfp_E4typeET_" } }
+// { dg-final { scan-assembler "_Z2f2I1SENDTcvT__EE4typeES1_" } }
diff --git a/libiberty/cp-demangle.c b/libiberty/cp-demangle.c
index f41856b..d67a9e7 100644
--- a/libiberty/cp-demangle.c
+++ b/libiberty/cp-demangle.c
@@ -1280,6 +1280,7 @@  d_nested_name (struct d_info *di)
 /* <prefix> ::= <prefix> <unqualified-name>
             ::= <template-prefix> <template-args>
             ::= <template-param>
+            ::= <decltype>
             ::=
             ::= <substitution>
 
@@ -1308,10 +1309,19 @@  d_prefix (struct d_info *di)
 	 <template-param> here.  */
 
       comb_type = DEMANGLE_COMPONENT_QUAL_NAME;
-      if (IS_DIGIT (peek)
+      if (peek == 'D')
+	{
+	  char peek2 = d_peek_next_char (di);
+	  if (peek2 == 'T' || peek2 == 't')
+	    /* Decltype.  */
+	    dc = cplus_demangle_type (di);
+	  else
+	    /* Destructor name.  */
+	    dc = d_unqualified_name (di);
+	}
+      else if (IS_DIGIT (peek)
 	  || IS_LOWER (peek)
 	  || peek == 'C'
-	  || peek == 'D'
 	  || peek == 'U'
 	  || peek == 'L')
 	dc = d_unqualified_name (di);
diff --git a/libiberty/testsuite/demangle-expected b/libiberty/testsuite/demangle-expected
index f9e8447..3737cfd 100644
--- a/libiberty/testsuite/demangle-expected
+++ b/libiberty/testsuite/demangle-expected
@@ -3901,6 +3901,10 @@  java resource java/util/iso4217.properties
 --format=gnu-v3
 _Z3addIidEDTplfp_fp0_ET_T0_
 decltype ({parm#1}+{parm#2}) add<int, double>(int, double)
+# decltype scope test
+--format=gnu-v3
+_Z1fI1SENDtfp_E4typeET_
+decltype ({parm#1})::type f<S>(S)
 # decltype/fn call test
 --format=gnu-v3
 _Z4add3IidEDTclL_Z1gEfp_fp0_EET_T0_