| //===-- TypeList.cpp --------------------------------------------*- C++ -*-===// |
| // |
| // The LLVM Compiler Infrastructure |
| // |
| // This file is distributed under the University of Illinois Open Source |
| // License. See LICENSE.TXT for details. |
| // |
| //===----------------------------------------------------------------------===// |
| |
| |
| // C Includes |
| // C++ Includes |
| #include <vector> |
| |
| // Other libraries and framework includes |
| #include "clang/AST/ASTConsumer.h" |
| #include "clang/AST/ASTContext.h" |
| #include "clang/AST/Decl.h" |
| #include "clang/AST/DeclCXX.h" |
| #include "clang/AST/DeclGroup.h" |
| |
| #include "clang/Basic/Builtins.h" |
| #include "clang/Basic/IdentifierTable.h" |
| #include "clang/Basic/LangOptions.h" |
| #include "clang/Basic/SourceManager.h" |
| #include "clang/Basic/TargetInfo.h" |
| |
| #include "llvm/Support/FormattedStream.h" |
| #include "llvm/Support/raw_ostream.h" |
| |
| // Project includes |
| #include "lldb/Symbol/ClangASTContext.h" |
| #include "lldb/Symbol/SymbolFile.h" |
| #include "lldb/Symbol/SymbolVendor.h" |
| #include "lldb/Symbol/Type.h" |
| #include "lldb/Symbol/TypeList.h" |
| |
| using namespace lldb; |
| using namespace lldb_private; |
| using namespace clang; |
| |
| TypeList::TypeList(const char *target_triple) : |
| m_types(), |
| m_ast(target_triple) |
| { |
| } |
| |
| //---------------------------------------------------------------------- |
| // Destructor |
| //---------------------------------------------------------------------- |
| TypeList::~TypeList() |
| { |
| } |
| |
| //---------------------------------------------------------------------- |
| // Add a base type to the type list |
| //---------------------------------------------------------------------- |
| |
| //struct CampareDCTypeBaton |
| //{ |
| // CampareDCTypeBaton(const std::vector<TypeSP>& _types, const Type* _search_type) : |
| // types(_types), |
| // search_type(_search_type) |
| // { |
| // } |
| // const std::vector<TypeSP>& types; |
| // const Type* search_type; |
| //}; |
| // |
| //static int |
| //compare_dc_type (const void *key, const void *arrmem) |
| //{ |
| // const Type* search_type = ((CampareDCTypeBaton*) key)->search_type; |
| // uint32_t curr_index = *(uint32_t *)arrmem; |
| // const Type* curr_type = ((CampareDCTypeBaton*) key)->types[curr_index].get(); |
| // Type::CompareState state; |
| // return Type::Compare(*search_type, *curr_type, state); |
| //} |
| // |
| //struct LessThanBinaryPredicate |
| //{ |
| // LessThanBinaryPredicate(const CampareDCTypeBaton& _compare_baton) : |
| // compare_baton(_compare_baton) |
| // { |
| // } |
| // |
| // bool operator() (uint32_t a, uint32_t b) const |
| // { |
| // Type::CompareState state; |
| // return Type::Compare(*compare_baton.search_type, *compare_baton.types[b].get(), state) < 0; |
| // } |
| // const CampareDCTypeBaton& compare_baton; |
| //}; |
| |
| TypeSP |
| TypeList::InsertUnique(TypeSP& type_sp) |
| { |
| #if 0 |
| // Stream s(stdout); |
| // s << "TypeList::InsertUnique for type "; |
| // type_sp->Dump(s); |
| // s << "Current list:\n"; |
| // Dump(s); |
| |
| CampareDCTypeBaton compare_baton(m_types, type_sp.get()); |
| uint32_t* match_index_ptr = (uint32_t*)bsearch(&compare_baton, &m_sorted_indexes[0], m_sorted_indexes.size(), sizeof(uint32_t), compare_dc_type); |
| if (match_index_ptr) |
| { |
| // s << "returning existing type: " << (void *)m_types[*match_index_ptr].get() << "\n"; |
| return m_types[*match_index_ptr]; |
| } |
| |
| // Get the new index within the m_types array before we add the new type |
| uint32_t uniqued_type_index = m_types.size(); |
| // Add the new shared pointer to our type by appending it to the end of the types array |
| m_types.push_back(type_sp); |
| // Figure out what the sorted index of this new type should be |
| uint32_t fake_index = 0; |
| LessThanBinaryPredicate compare_func_obj(compare_baton); |
| std::vector<uint32_t>::iterator insert_pos = std::upper_bound(m_sorted_indexes.begin(), m_sorted_indexes.end(), fake_index, compare_func_obj); |
| // Insert the sorted index into our sorted index array |
| m_sorted_indexes.insert(insert_pos, uniqued_type_index); |
| #else |
| // Just push each type on the back for now. We will worry about uniquing later |
| m_types.push_back (type_sp); |
| #endif |
| // s << "New list:\n"; |
| // Dump(s); |
| |
| return type_sp; |
| } |
| |
| //---------------------------------------------------------------------- |
| // Find a base type by its unique ID. |
| //---------------------------------------------------------------------- |
| TypeSP |
| TypeList::FindType(lldb::user_id_t uid) |
| { |
| TypeSP type_sp; |
| iterator pos, end; |
| for (pos = m_types.begin(), end = m_types.end(); pos != end; ++pos) |
| if ((*pos)->GetID() == uid) |
| return *pos; |
| |
| return type_sp; |
| } |
| |
| //---------------------------------------------------------------------- |
| // Find a type by name. |
| //---------------------------------------------------------------------- |
| TypeList |
| TypeList::FindTypes(const ConstString &name) |
| { |
| TypeList types(m_ast.getTargetInfo()->getTriple().getTriple().c_str()); |
| iterator pos, end; |
| for (pos = m_types.begin(), end = m_types.end(); pos != end; ++pos) |
| if ((*pos)->GetName() == name) |
| types.InsertUnique(*pos); |
| return types; |
| } |
| |
| void |
| TypeList::Clear() |
| { |
| m_types.clear(); |
| } |
| |
| uint32_t |
| TypeList::GetSize() const |
| { |
| return m_types.size(); |
| } |
| |
| TypeSP |
| TypeList::GetTypeAtIndex(uint32_t idx) |
| { |
| TypeSP type_sp; |
| if (idx < m_types.size()) |
| type_sp = m_types[idx]; |
| return type_sp; |
| } |
| |
| void |
| TypeList::Dump(Stream *s, bool show_context) |
| { |
| // std::vector<uint32_t>::const_iterator pos, end; |
| // for (pos = end = m_sorted_indexes.begin(), end = m_sorted_indexes.end(); pos != end; ++pos) |
| // { |
| // m_types[*pos]->Dump(s, show_context); |
| // } |
| |
| m_ast.getASTContext()->getTranslationUnitDecl()->print(llvm::fouts(), 0); |
| const size_t num_types = m_types.size(); |
| for (size_t i=0; i<num_types; ++i) |
| { |
| m_types[i]->Dump(s, show_context); |
| } |
| // ASTContext *ast_context = GetClangASTContext ().getASTContext(); |
| // if (ast_context) |
| // ast_context->PrintStats(); |
| } |
| |
| |
| ClangASTContext & |
| TypeList::GetClangASTContext () |
| { |
| return m_ast; |
| } |
| |
| void * |
| TypeList::CreateClangPointerType (Type *type) |
| { |
| assert(type); |
| return m_ast.CreatePointerType(type->GetOpaqueClangQualType()); |
| } |
| |
| void * |
| TypeList::CreateClangTypedefType (Type *typedef_type, Type *base_type) |
| { |
| assert(typedef_type && base_type); |
| return m_ast.CreateTypedefType(typedef_type->GetName().AsCString(), base_type->GetOpaqueClangQualType(), typedef_type->GetSymbolFile()->GetClangDeclContextForTypeUID(typedef_type->GetID())); |
| } |
| |
| void * |
| TypeList::CreateClangLValueReferenceType (Type *type) |
| { |
| assert(type); |
| return m_ast.CreateLValueReferenceType(type->GetOpaqueClangQualType()); |
| } |
| |
| void * |
| TypeList::CreateClangRValueReferenceType (Type *type) |
| { |
| assert(type); |
| return m_ast.CreateRValueReferenceType (type->GetOpaqueClangQualType()); |
| } |
| |
| |
| |