RichManglingContext: Make m_ipd_str_len a local variable and simplify processIPDStrRe...
authorStefan Granitz <stefan.graenitz@gmail.com>
Fri, 10 Aug 2018 15:21:33 +0000 (15:21 +0000)
committerStefan Granitz <stefan.graenitz@gmail.com>
Fri, 10 Aug 2018 15:21:33 +0000 (15:21 +0000)
llvm-svn: 339440

lldb/include/lldb/Core/RichManglingContext.h
lldb/source/Core/Mangled.cpp
lldb/source/Core/RichManglingContext.cpp
lldb/unittests/Core/RichManglingContextTest.cpp

index bfa910c..393305c 100644 (file)
@@ -25,10 +25,9 @@ namespace lldb_private {
 /// providers. See Mangled::DemangleWithRichManglingInfo()
 class RichManglingContext {
 public:
-  RichManglingContext()
-      : m_provider(None), m_ipd_buf_size(2048), m_ipd_str_len(0) {
+  RichManglingContext() : m_provider(None), m_ipd_buf_size(2048) {
     m_ipd_buf = static_cast<char *>(std::malloc(m_ipd_buf_size));
-    m_ipd_buf[m_ipd_str_len] = '\0';
+    m_ipd_buf[0] = '\0';
   }
 
   ~RichManglingContext() { std::free(m_ipd_buf); }
@@ -65,6 +64,7 @@ public:
   /// most recent ParseXy() operation. The next ParseXy() call invalidates it.
   llvm::StringRef GetBufferRef() const {
     assert(m_provider != None && "Initialize a provider first");
+    assert(m_buffer.data() != nullptr && "Parse first");
     return m_buffer;
   }
 
@@ -81,7 +81,6 @@ private:
   llvm::ItaniumPartialDemangler m_ipd;
   char *m_ipd_buf;
   size_t m_ipd_buf_size;
-  size_t m_ipd_str_len;
 
   /// Members for PluginCxxLanguage
   /// Cannot forward declare inner class CPlusPlusLanguage::MethodName. The
index 64d4495..c01df6c 100644 (file)
@@ -261,9 +261,10 @@ static char *GetMSVCDemangledStr(const char *M) {
 #endif
 }
 
-static char *GetItaniumDemangledStr(const char *M,
-                                    llvm::ItaniumPartialDemangler &ipd) {
+static char *GetItaniumDemangledStr(const char *M) {
   char *demangled_cstr = nullptr;
+
+  llvm::ItaniumPartialDemangler ipd;
   bool err = ipd.partialDemangle(M);
   if (!err) {
     // Default buffer and size (will realloc in case it's too small).
@@ -384,8 +385,7 @@ Mangled::GetDemangledName(lldb::LanguageType language) const {
         demangled_name = GetMSVCDemangledStr(mangled_name);
         break;
       case eManglingSchemeItanium: {
-        llvm::ItaniumPartialDemangler ipd;
-        demangled_name = GetItaniumDemangledStr(mangled_name, ipd);
+        demangled_name = GetItaniumDemangledStr(mangled_name);
         break;
       }
       case eManglingSchemeNone:
index da009e4..0ff602f 100644 (file)
@@ -89,37 +89,32 @@ bool RichManglingContext::IsFunction() const {
 }
 
 void RichManglingContext::processIPDStrResult(char *ipd_res, size_t res_size) {
+  // Error case: Clear the buffer.
   if (LLVM_UNLIKELY(ipd_res == nullptr)) {
     assert(res_size == m_ipd_buf_size &&
            "Failed IPD queries keep the original size in the N parameter");
 
-    // Error case: Clear the buffer.
-    m_ipd_str_len = 0;
-    m_ipd_buf[m_ipd_str_len] = '\0';
-  } else {
-    // IPD's res_size includes null terminator.
-    size_t res_len = res_size - 1;
-    assert(ipd_res[res_len] == '\0' &&
-           "IPD returns null-terminated strings and we rely on that");
-
-    if (LLVM_UNLIKELY(ipd_res != m_ipd_buf)) {
-      // Realloc case: Take over the new buffer.
-      m_ipd_buf = ipd_res; // std::realloc freed or reused the old buffer.
-      m_ipd_buf_size =
-          res_size; // Actual buffer may be bigger, but we can't know.
-      m_ipd_str_len = res_len;
-
-      Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE);
-      if (log)
-        log->Printf("ItaniumPartialDemangler Realloc: new buffer size %lu",
-                    m_ipd_buf_size);
-    } else {
-      // 99% case: Just remember the string length.
-      m_ipd_str_len = res_len;
-    }
+    m_ipd_buf[0] = '\0';
+    m_buffer = llvm::StringRef(m_ipd_buf, 0);
+    return;
+  }
+
+  // IPD's res_size includes null terminator.
+  assert(ipd_res[res_size - 1] == '\0' &&
+         "IPD returns null-terminated strings and we rely on that");
+
+  // Update buffer/size on realloc.
+  if (LLVM_UNLIKELY(ipd_res != m_ipd_buf || res_size > m_ipd_buf_size)) {
+    m_ipd_buf = ipd_res;       // std::realloc freed or reused the old buffer.
+    m_ipd_buf_size = res_size; // May actually be bigger, but we can't know.
+
+    if (Log *log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_DEMANGLE))
+      LLDB_LOG(log, "ItaniumPartialDemangler Realloc: new buffer size is {0}",
+               m_ipd_buf_size);
   }
 
-  m_buffer = llvm::StringRef(m_ipd_buf, m_ipd_str_len);
+  // 99% case: Just remember the string length.
+  m_buffer = llvm::StringRef(m_ipd_buf, res_size - 1);
 }
 
 void RichManglingContext::ParseFunctionBaseName() {
index bf68099..19329ac 100644 (file)
@@ -79,10 +79,10 @@ TEST(RichManglingContextTest, SwitchProvider) {
 
 TEST(RichManglingContextTest, IPDRealloc) {
   // The demangled name should fit into the Itanium default buffer.
-  const char *short_mangled = "_ZN3foo3barEv";
+  const char *ShortMangled = "_ZN3foo3barEv";
 
   // The demangled name for this will certainly not fit into the default buffer.
-  const char *long_mangled =
+  const char *LongMangled =
       "_ZNK3shk6detail17CallbackPublisherIZNS_5ThrowERKNSt15__exception_"
       "ptr13exception_ptrEEUlOT_E_E9SubscribeINS0_9ConcatMapINS0_"
       "18CallbackSubscriberIZNS_6GetAllIiNS1_IZZNS_9ConcatMapIZNS_6ConcatIJNS1_"
@@ -100,15 +100,18 @@ TEST(RichManglingContextTest, IPDRealloc) {
 
   RichManglingContext RMC;
 
-  // Demangle the short one and remember the buffer address.
-  EXPECT_TRUE(RMC.FromItaniumName(ConstString(short_mangled)));
+  // Demangle the short one.
+  EXPECT_TRUE(RMC.FromItaniumName(ConstString(ShortMangled)));
   RMC.ParseFullName();
-  const char *short_demangled_ptr = RMC.GetBufferRef().data();
+  const char *ShortDemangled = RMC.GetBufferRef().data();
 
-  // Demangle the long one and make sure the buffer address changed.
-  EXPECT_TRUE(RMC.FromItaniumName(ConstString(long_mangled)));
+  // Demangle the long one.
+  EXPECT_TRUE(RMC.FromItaniumName(ConstString(LongMangled)));
   RMC.ParseFullName();
-  const char *long_demangled_ptr = RMC.GetBufferRef().data();
+  const char *LongDemangled = RMC.GetBufferRef().data();
 
-  EXPECT_TRUE(short_demangled_ptr != long_demangled_ptr);
+  // Make sure a new buffer was allocated or the default buffer was extended.
+  bool AllocatedNewBuffer = (ShortDemangled != LongDemangled);
+  bool ExtendedExistingBuffer = (strlen(LongDemangled) > 2048);
+  EXPECT_TRUE(AllocatedNewBuffer || ExtendedExistingBuffer);
 }