[Lldb-commits] [lldb] r234922 - Added support to ClangUserExpression for importing
Sean Callanan
scallanan at apple.com
Tue Apr 14 11:36:18 PDT 2015
Author: spyffe
Date: Tue Apr 14 13:36:17 2015
New Revision: 234922
URL: http://llvm.org/viewvc/llvm-project?rev=234922&view=rev
Log:
Added support to ClangUserExpression for importing
all the macros from the modules the user has loaded.
These macros are currently imported textually into
the expression's source code, which turns out not to
impose the horrific string processing overhead that
I thought it would, but I still plan to look into
performance improvements.
Also modified TestCModules to test that this works.
Modified:
lldb/trunk/include/lldb/Core/ClangForward.h
lldb/trunk/include/lldb/Expression/ClangModulesDeclVendor.h
lldb/trunk/source/Expression/ClangModulesDeclVendor.cpp
lldb/trunk/source/Expression/ClangUserExpression.cpp
lldb/trunk/test/lang/c/modules/TestCModules.py
Modified: lldb/trunk/include/lldb/Core/ClangForward.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/ClangForward.h?rev=234922&r1=234921&r2=234922&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Core/ClangForward.h (original)
+++ lldb/trunk/include/lldb/Core/ClangForward.h Tue Apr 14 13:36:17 2015
@@ -72,11 +72,14 @@ namespace clang
class FunctionTemplateSpecializationInfo;
class GotoStmt;
class HeaderSearchOptions;
+ class IdentifierInfo;
class IdentifierTable;
class IntegerLiteral;
class LabelStmt;
class LangOptions;
+ class MacroDirective;
class MemberExpr;
+ class Module;
class NamedDecl;
class NamespaceDecl;
class NonTypeTemplateParmDecl;
Modified: lldb/trunk/include/lldb/Expression/ClangModulesDeclVendor.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/ClangModulesDeclVendor.h?rev=234922&r1=234921&r2=234922&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/ClangModulesDeclVendor.h (original)
+++ lldb/trunk/include/lldb/Expression/ClangModulesDeclVendor.h Tue Apr 14 13:36:17 2015
@@ -52,6 +52,9 @@ public:
//------------------------------------------------------------------
virtual bool
AddModule(std::vector<llvm::StringRef> &path, Stream &error_stream) = 0;
+
+ virtual void
+ ForEachMacro(std::function<bool (const std::string &)> handler) = 0;
};
}
Modified: lldb/trunk/source/Expression/ClangModulesDeclVendor.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangModulesDeclVendor.cpp?rev=234922&r1=234921&r2=234922&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangModulesDeclVendor.cpp (original)
+++ lldb/trunk/source/Expression/ClangModulesDeclVendor.cpp Tue Apr 14 13:36:17 2015
@@ -62,13 +62,16 @@ namespace {
virtual bool
AddModule(std::vector<llvm::StringRef> &path,
- Stream &error_stream);
+ Stream &error_stream) override;
virtual uint32_t
FindDecls (const ConstString &name,
bool append,
uint32_t max_matches,
- std::vector <clang::NamedDecl*> &decls);
+ std::vector <clang::NamedDecl*> &decls) override;
+
+ virtual void
+ ForEachMacro(std::function<bool (const std::string &)> handler) override;
~ClangModulesDeclVendorImpl();
@@ -253,6 +256,146 @@ ClangModulesDeclVendorImpl::FindDecls (c
return num_matches;
}
+void
+ClangModulesDeclVendorImpl::ForEachMacro(std::function<bool (const std::string &)> handler)
+{
+
+ for (clang::Preprocessor::macro_iterator mi = m_compiler_instance->getPreprocessor().macro_begin(),
+ me = m_compiler_instance->getPreprocessor().macro_end();
+ mi != me;
+ ++mi)
+ {
+ if (mi->second->getKind() == clang::MacroDirective::MD_Define)
+ {
+ std::string macro_expansion = "#define ";
+ macro_expansion.append(mi->first->getName().str().c_str());
+
+ if (clang::MacroInfo *macro_info = mi->second->getMacroInfo())
+ {
+ if (macro_info->isFunctionLike())
+ {
+ macro_expansion.append("(");
+
+ bool first_arg = true;
+
+ for (clang::MacroInfo::arg_iterator ai = macro_info->arg_begin(),
+ ae = macro_info->arg_end();
+ ai != ae;
+ ++ai)
+ {
+ if (!first_arg)
+ {
+ macro_expansion.append(", ");
+ }
+ else
+ {
+ first_arg = false;
+ }
+
+ macro_expansion.append((*ai)->getName().str());
+ }
+
+ if (macro_info->isC99Varargs())
+ {
+ if (first_arg)
+ {
+ macro_expansion.append("...");
+ }
+ else
+ {
+ macro_expansion.append(", ...");
+ }
+ }
+ else if (macro_info->isGNUVarargs())
+ {
+ macro_expansion.append("...");
+ }
+
+ macro_expansion.append(")");
+ }
+
+ macro_expansion.append(" ");
+
+ bool first_token = true;
+
+ for (clang::MacroInfo::tokens_iterator ti = macro_info->tokens_begin(),
+ te = macro_info->tokens_end();
+ ti != te;
+ ++ti)
+ {
+ if (!first_token)
+ {
+ macro_expansion.append(" ");
+ }
+ else
+ {
+ first_token = false;
+ }
+
+ if (ti->isLiteral())
+ {
+ if (const char *literal_data = ti->getLiteralData())
+ {
+ std::string token_str(literal_data, ti->getLength());
+ macro_expansion.append(token_str);
+ }
+ else
+ {
+ bool invalid = false;
+ const char *literal_source = m_compiler_instance->getSourceManager().getCharacterData(ti->getLocation(), &invalid);
+
+ if (invalid)
+ {
+#ifdef LLDB_CONFIGURATION_DEBUG
+ assert(!"Unhandled token kind");
+#endif
+ macro_expansion.append("<unknown literal value>");
+ }
+ else
+ {
+ macro_expansion.append(std::string(literal_source, ti->getLength()));
+ }
+ }
+ }
+ else if (const char *punctuator_spelling = clang::tok::getPunctuatorSpelling(ti->getKind()))
+ {
+ macro_expansion.append(punctuator_spelling);
+ }
+ else if (const char *keyword_spelling = clang::tok::getKeywordSpelling(ti->getKind()))
+ {
+ macro_expansion.append(keyword_spelling);
+ }
+ else
+ {
+ switch (ti->getKind())
+ {
+ case clang::tok::TokenKind::identifier:
+ macro_expansion.append(ti->getIdentifierInfo()->getName().str());
+ break;
+ case clang::tok::TokenKind::raw_identifier:
+ macro_expansion.append(ti->getRawIdentifier().str());
+ default:
+ macro_expansion.append(ti->getName());
+ break;
+ }
+ }
+ }
+ }
+ else
+ {
+#ifdef LLDB_CONFIGURATION_DEBUG
+ assert(!"#define with no macro info");
+#endif
+ }
+
+ if (handler(macro_expansion))
+ {
+ return;
+ }
+ }
+ }
+}
+
ClangModulesDeclVendorImpl::~ClangModulesDeclVendorImpl()
{
}
Modified: lldb/trunk/source/Expression/ClangUserExpression.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangUserExpression.cpp?rev=234922&r1=234921&r2=234922&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangUserExpression.cpp (original)
+++ lldb/trunk/source/Expression/ClangUserExpression.cpp Tue Apr 14 13:36:17 2015
@@ -26,6 +26,7 @@
#include "lldb/Expression/ClangExpressionDeclMap.h"
#include "lldb/Expression/ClangExpressionParser.h"
#include "lldb/Expression/ClangFunction.h"
+#include "lldb/Expression/ClangModulesDeclVendor.h"
#include "lldb/Expression/ClangPersistentVariables.h"
#include "lldb/Expression/ClangUserExpression.h"
#include "lldb/Expression/ExpressionSourceCode.h"
@@ -453,8 +454,19 @@ ClangUserExpression::Parse (Stream &erro
ApplyObjcCastHack(m_expr_text);
//ApplyUnicharHack(m_expr_text);
- std::unique_ptr<ExpressionSourceCode> source_code (ExpressionSourceCode::CreateWrapped(m_expr_prefix.c_str(), m_expr_text.c_str()));
-
+ std::string prefix = m_expr_prefix;
+
+ if (ClangModulesDeclVendor *decl_vendor = m_target->GetClangModulesDeclVendor())
+ {
+ decl_vendor->ForEachMacro([log, &prefix] (const std::string &expansion) -> bool {
+ prefix.append(expansion);
+ prefix.append("\n");
+ return false;
+ });
+ }
+
+ std::unique_ptr<ExpressionSourceCode> source_code (ExpressionSourceCode::CreateWrapped(prefix.c_str(), m_expr_text.c_str()));
+
lldb::LanguageType lang_type;
if (m_cplusplus)
Modified: lldb/trunk/test/lang/c/modules/TestCModules.py
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/test/lang/c/modules/TestCModules.py?rev=234922&r1=234921&r2=234922&view=diff
==============================================================================
--- lldb/trunk/test/lang/c/modules/TestCModules.py (original)
+++ lldb/trunk/test/lang/c/modules/TestCModules.py Tue Apr 14 13:36:17 2015
@@ -73,6 +73,9 @@ class CModulesTestCase(TestBase):
self.expect("expr *myFile", VARIABLES_DISPLAYED_CORRECTLY,
substrs = ["a", "5", "b", "9"])
+
+ self.expect("expr MIN((uint64_t)2, (uint64_t)3)", VARIABLES_DISPLAYED_CORRECTLY,
+ substrs = ["uint64_t", "2"])
if __name__ == '__main__':
import atexit
More information about the lldb-commits
mailing list