I set up a new review, because not all the code I touched was marked as a change in old one anymore: https://reviews.llvm.org/D49990
In preparation for this review, there were two earlier ones:
- https://reviews.llvm.org/D49612 introduced the ItaniumPartialDemangler to LLDB demangling without conceptual changes
- https://reviews.llvm.org/D49909 added a unit test that covers all relevant code paths in the InitNameIndexes() function
Primary goals for this patch are:
(1) Use ItaniumPartialDemangler's rich mangling info for building LLDB's name index.
(2) Provide a uniform interface.
(3) Improve indexing performance.
The central implementation in this patch is our new function for explicit demangling:
const RichManglingInfo * Mangled::DemangleWithRichManglingInfo(RichManglingContext &, SkipMangledNameFn *)
It takes a context object and a filter function and provides read-only access to the rich mangling info on success, or otherwise returns null. The two new classes are:
- RichManglingInfo offers a uniform interface to query symbol properties like getFunctionDeclContextName() or isCtorOrDtor() that are forwarded to the respective provider internally (llvm::ItaniumPartialDemangler or lldb_private::CPlusPlusLanguage::MethodName).
- RichManglingContext works a bit like LLVMContext, it the actual RichManglingInfo returned from DemangleWithRichManglingInfo() and handles lifetime and configuration. It is likely stack-allocated and can be reused for multiple queries during batch processing.
The idea here is that DemangleWithRichManglingInfo() acts like a gate keeper. It only provides access to RichManglingInfo on success, which in turn avoids the need to handle a NoInfo state in every single one of its getters. Having it stored within the context, avoids extra heap allocations and aids (3). As instantiations of the IPD the are considered expensive, the context is the ideal place to store it too. An efficient filtering function SkipMangledNameFn is another piece in the performance puzzle and it helps to mimic the original behavior of InitNameIndexes.
- DemangleWithRichManglingInfo() is thread-safe, IFF using different contexts in different threads. This may be exploited in the future. (It's another thing that it has in common with LLVMContext.)
- The old implementation only parsed and indexed Itanium mangled names. The new RichManglingInfo can be extended for various mangling schemes and languages.
One problem with the implementation of RichManglingInfo is the inaccessibility of class CPlusPlusLanguage::MethodName (defined in source/Plugins/Language/..), from within any header in the Core components of LLDB. The rather hacky solution is to store a type erased reference and cast it to the correct type on access in the cpp - see RichManglingInfo::get<ParserT>(). At the moment there seems to be no better way to do it. IMHO CPlusPlusLanguage::MethodName should be a top-level class in order to enable forward delcarations (but that is a rather big change I guess).
First simple profiling shows a good speedup. target create clang now takes 0.64s on average. Before the change I observed runtimes between 0.76s an 1.01s. This is still no bulletproof data (I only ran it on one machine!), but it's a promising indicator I think.