[cfe-commits] [libcxxabi] r133632 - in /libcxxabi/trunk: include/cxa_demangle.h src/cxa_demangle.cpp test/test_demangle.cpp

Howard Hinnant hhinnant at apple.com
Wed Jun 22 12:27:39 PDT 2011


Author: hhinnant
Date: Wed Jun 22 14:27:39 2011
New Revision: 133632

URL: http://llvm.org/viewvc/llvm-project?rev=133632&view=rev
Log:
In cxa_demangle.cpp, rewrite __parse_unresolved_name to reflect updated understanding and sync with updated clang mangling.  Also fix think-o in __parse_encoding enabling the parsing of trailing .eh and .b.

Modified:
    libcxxabi/trunk/include/cxa_demangle.h
    libcxxabi/trunk/src/cxa_demangle.cpp
    libcxxabi/trunk/test/test_demangle.cpp

Modified: libcxxabi/trunk/include/cxa_demangle.h
URL: http://llvm.org/viewvc/llvm-project/libcxxabi/trunk/include/cxa_demangle.h?rev=133632&r1=133631&r2=133632&view=diff
==============================================================================
--- libcxxabi/trunk/include/cxa_demangle.h (original)
+++ libcxxabi/trunk/include/cxa_demangle.h Wed Jun 22 14:27:39 2011
@@ -127,6 +127,7 @@
     const char* __parse_pack_expansion(const char*, const char*);
     const char* __parse_sizeof_function_param_pack_expr(const char*, const char*);
     const char* __parse_dot_suffix(const char*, const char*);
+    const char* __parse_unresolved_qualifier_level(const char*, const char*);
     const char* __parse_hex_number(const char*, const char*, unsigned long long&);
 
     template <class _Tp> bool __make();

Modified: libcxxabi/trunk/src/cxa_demangle.cpp
URL: http://llvm.org/viewvc/llvm-project/libcxxabi/trunk/src/cxa_demangle.cpp?rev=133632&r1=133631&r2=133632&view=diff
==============================================================================
--- libcxxabi/trunk/src/cxa_demangle.cpp (original)
+++ libcxxabi/trunk/src/cxa_demangle.cpp Wed Jun 22 14:27:39 2011
@@ -11308,68 +11308,107 @@
     return first;
 }
 
+// <unresolved-qualifier-level> ::= <source-name> [ <template-args> ]
+
+const char*
+__demangle_tree::__parse_unresolved_qualifier_level(const char* first, const char* last)
+{
+    if (first != last)
+    {
+            const char* t = __parse_source_name(first, last);
+            if (t != first)
+                first = __parse_template_args(t, last);
+    }
+    return first;
+}
+
 // <unresolved-name>
-//                   ::= sr <name> <base-unresolved-name>                # extension, subtly different than srN ...
-//                   ::= sr <unresolved-type> <base-unresolved-name>     # T::x / decltype(p)::x
-//                                                                       # T::N::x /decltype(p)::N::x
+//  extension        ::= srN <unresolved-type> [<template-args>] <unresolved-qualifier-level>* E <base-unresolved-name>
 //                   ::= [gs] <base-unresolved-name>                     # x or (with "gs") ::x
 //                   ::= [gs] sr <unresolved-qualifier-level>+ E <base-unresolved-name>  
 //                                                                       # A::x, N::y, A<T>::z; "gs" means leading "::"
-//  (ignored)        ::= srN <unresolved-type> <unresolved-qualifier-level>+ E <base-unresolved-name>
+//                   ::= sr <unresolved-type> <base-unresolved-name>     # T::x / decltype(p)::x
+//                                                                       # T::N::x /decltype(p)::N::x
+//  (ignored)        ::= srN <unresolved-type>  <unresolved-qualifier-level>+ E <base-unresolved-name>
 
 const char*
 __demangle_tree::__parse_unresolved_name(const char* first, const char* last)
 {
     if (last - first > 2)
     {
-        if (first[0] == 's' && first[1] == 'r')
+        const char* t = first;
+        bool global = false;
+        if (t[0] == 'g' && t[1] == 's')
         {
-            const char* t = __parse_name(first+2, last);
-            if (t == first+2)
-                t = __parse_unresolved_type(first+2, last);
-            if (t != first+2)
-            {
-                __node* name = __root_;
-                const char* t2 = __parse_base_unresolved_name(t, last);
-                if (t2 != t && __make<__unresolved_name>(name, __root_))
-                    first = t2;
-            }
+            global = true;
+            t += 2;
         }
-        else
+        const char* t2 = __parse_base_unresolved_name(t, last);
+        if (t2 != t)
+        {
+            if (__make<__unresolved_name>(global, (__node*)0, __root_))
+                first = t2;
+        }
+        else if (last - t > 2 && t[0] == 's' && t[1] == 'r')
         {
-            const char* t = first;
-            bool global = false;
-            if (t[0] == 'g' && t[1] == 's')
+            if (!global && t[2] == 'N')
             {
-                global = true;
-                t += 2;
+                t2 = __parse_unresolved_type(t+3, last);
+                if (t2 != t+3 && t2 != last)
+                {
+                    t = __parse_template_args(t2, last);
+                    if (t == last)
+                        return first;
+                    __node* name = __root_;
+                    while (*t != 'E')
+                    {
+                        t2 = __parse_unresolved_qualifier_level(t, last);
+                        if (t2 == t || t2 == last)
+                            return first;
+                        if (!__make<__nested_delimeter>(name, __root_))
+                            return first;
+                        name = __root_;
+                        t = t2;
+                    }
+                    t2 = __parse_base_unresolved_name(++t, last);
+                    if (t2 != t && __make<__unresolved_name>(false, name, __root_))
+                        first = t2;
+                }
             }
-            if (last - t > 2)
+            else
             {
-                const char* t2;
-                __node* name = NULL;
-                if (t[0] == 's' && t[1] == 'r')
-                {
-                    t += 2;
-                    t2 = __parse_simple_id(t, last);
-                    if (t2 == t || t2 == last)
-                        return first;
-                    name = __root_;
-                    while (*t2 != 'E')
+                if (!global)
+                {
+                    t2 = __parse_unresolved_type(t+2, last);
+                    if (t2 != t+2)
                     {
                         t = t2;
-                        t2 = __parse_simple_id(t, last);
-                        if (t2 == t)
+                        __node* name = __root_;
+                        t2 = __parse_base_unresolved_name(t, last);
+                        if (t2 != t && __make<__unresolved_name>(false, name, __root_))
+                            return t2;
+                        return first;
+                    }
+                }
+                t2 = __parse_unresolved_qualifier_level(t+2, last);
+                if (t2 != t+2 && t2 != last)
+                {
+                    __node* name = __root_;
+                    t = t2;
+                    while (*t != 'E')
+                    {
+                        t2 = __parse_unresolved_qualifier_level(t, last);
+                        if (t2 == t || t2 == last)
                             return first;
                         if (!__make<__nested_delimeter>(name, __root_))
                             return first;
                         name = __root_;
+                        t = t2;
                     }
-                    t = t2+1;
+                    t2 = __parse_base_unresolved_name(++t, last);
+                    if (t2 != t && __make<__unresolved_name>(global, name, __root_))
+                        first = t2;
                 }
-                t2 = __parse_base_unresolved_name(t, last);
-                if (t2 != t && __make<__unresolved_name>(global, name, __root_))
-                    first = t2;
             }
         }
     }
@@ -14696,7 +14735,7 @@
     const char* t = __parse_name(first, last);
     if (t != first)
     {
-        if (t != last && *t != 'E')
+        if (t != last && *t != 'E' && *t != '.')
         {
             __node* name = __root_;
             bool has_return = name->ends_with_template() &&

Modified: libcxxabi/trunk/test/test_demangle.cpp
URL: http://llvm.org/viewvc/llvm-project/libcxxabi/trunk/test/test_demangle.cpp?rev=133632&r1=133631&r2=133632&view=diff
==============================================================================
--- libcxxabi/trunk/test/test_demangle.cpp (original)
+++ libcxxabi/trunk/test/test_demangle.cpp Wed Jun 22 14:27:39 2011
@@ -29500,8 +29500,8 @@
     {"_ZplRK1YRA100_P1X", "operator+(Y const&, X* (&) [100])"},
     {"_Z1fno", "f(__int128, unsigned __int128)"},
     {"_Z1fM1SKFvvE", "f(void (S::*)() const)"},
-    {"_Z3ft7IiEN11__enable_ifIXsr11__is_scalarIT_E7__valueEvE6__typeEv", "__enable_if<__is_scalar<int>::__value, void>::__type ft7<int>()"},
-    {"_Z3ft7IPvEN11__enable_ifIXsr11__is_scalarIT_E7__valueEvE6__typeEv", "__enable_if<__is_scalar<void*>::__value, void>::__type ft7<void*>()"},
+    {"_Z3ft7IiEN11__enable_ifIXsr16__is_scalar_typeIT_EE7__valueEvE6__typeEv", "__enable_if<__is_scalar_type<int>::__value, void>::__type ft7<int>()"},
+    {"_Z3ft7IPvEN11__enable_ifIXsr16__is_scalar_typeIT_EE7__valueEvE6__typeEv", "__enable_if<__is_scalar_type<void*>::__value, void>::__type ft7<void*>()"},
     {"_ZN6PR57968__fill_aIiEENS_11__enable_ifIXntsrNS_11__is_scalarIT_EE7__valueEvE6__typeEv", "PR5796::__enable_if<!(PR5796::__is_scalar<int>::__value), void>::__type PR5796::__fill_a<int>()"},
     {"_ZN11Expressions2f1ILi1EEEvPAplngT_Li2E_i", "void Expressions::f1<1>(int (*) [(-(1)) + (2)])"},
     {"_ZN11Expressions2f2ILi1EEEvPApsT__i", "void Expressions::f2<1>(int (*) [+(1)])"},





More information about the cfe-commits mailing list