1439 lines · cpp
1//===-- ClangASTImporter.cpp ----------------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9#include "lldb/Core/Module.h"10#include "lldb/Utility/LLDBAssert.h"11#include "lldb/Utility/LLDBLog.h"12#include "lldb/Utility/Log.h"13#include "clang/AST/ASTContext.h"14#include "clang/AST/Decl.h"15#include "clang/AST/DeclCXX.h"16#include "clang/AST/DeclObjC.h"17#include "clang/AST/RecordLayout.h"18#include "clang/Sema/Lookup.h"19#include "clang/Sema/Sema.h"20#include "llvm/Support/raw_ostream.h"21 22#include "Plugins/ExpressionParser/Clang/ClangASTImporter.h"23#include "Plugins/ExpressionParser/Clang/ClangASTMetadata.h"24#include "Plugins/ExpressionParser/Clang/ClangASTSource.h"25#include "Plugins/ExpressionParser/Clang/ClangExternalASTSourceCallbacks.h"26#include "Plugins/ExpressionParser/Clang/ClangUtil.h"27#include "Plugins/TypeSystem/Clang/TypeSystemClang.h"28 29#include <memory>30#include <optional>31#include <type_traits>32 33using namespace lldb_private;34using namespace clang;35 36CompilerType ClangASTImporter::CopyType(TypeSystemClang &dst_ast,37 const CompilerType &src_type) {38 clang::ASTContext &dst_clang_ast = dst_ast.getASTContext();39 40 auto src_ast = src_type.GetTypeSystem<TypeSystemClang>();41 if (!src_ast)42 return CompilerType();43 44 clang::ASTContext &src_clang_ast = src_ast->getASTContext();45 46 clang::QualType src_qual_type = ClangUtil::GetQualType(src_type);47 48 ImporterDelegateSP delegate_sp(GetDelegate(&dst_clang_ast, &src_clang_ast));49 if (!delegate_sp)50 return CompilerType();51 52 ASTImporterDelegate::CxxModuleScope std_scope(*delegate_sp, &dst_clang_ast);53 54 llvm::Expected<QualType> ret_or_error = delegate_sp->Import(src_qual_type);55 if (!ret_or_error) {56 Log *log = GetLog(LLDBLog::Expressions);57 LLDB_LOG_ERROR(log, ret_or_error.takeError(),58 "Couldn't import type: {0}");59 return CompilerType();60 }61 62 lldb::opaque_compiler_type_t dst_clang_type = ret_or_error->getAsOpaquePtr();63 64 if (dst_clang_type)65 return CompilerType(dst_ast.weak_from_this(), dst_clang_type);66 return CompilerType();67}68 69clang::Decl *ClangASTImporter::CopyDecl(clang::ASTContext *dst_ast,70 clang::Decl *decl) {71 ImporterDelegateSP delegate_sp;72 73 clang::ASTContext *src_ast = &decl->getASTContext();74 delegate_sp = GetDelegate(dst_ast, src_ast);75 76 ASTImporterDelegate::CxxModuleScope std_scope(*delegate_sp, dst_ast);77 78 if (!delegate_sp)79 return nullptr;80 81 llvm::Expected<clang::Decl *> result = delegate_sp->Import(decl);82 if (!result) {83 Log *log = GetLog(LLDBLog::Expressions);84 LLDB_LOG_ERROR(log, result.takeError(), "Couldn't import decl: {0}");85 if (log) {86 lldb::user_id_t user_id = LLDB_INVALID_UID;87 if (std::optional<ClangASTMetadata> metadata = GetDeclMetadata(decl))88 user_id = metadata->GetUserID();89 90 if (NamedDecl *named_decl = dyn_cast<NamedDecl>(decl))91 LLDB_LOG(log,92 " [ClangASTImporter] WARNING: Failed to import a {0} "93 "'{1}', metadata {2}",94 decl->getDeclKindName(), named_decl->getNameAsString(),95 user_id);96 else97 LLDB_LOG(log,98 " [ClangASTImporter] WARNING: Failed to import a {0}, "99 "metadata {1}",100 decl->getDeclKindName(), user_id);101 }102 return nullptr;103 }104 105 return *result;106}107 108class DeclContextOverride {109private:110 struct Backup {111 clang::DeclContext *decl_context;112 clang::DeclContext *lexical_decl_context;113 };114 115 llvm::DenseMap<clang::Decl *, Backup> m_backups;116 117 void OverrideOne(clang::Decl *decl) {118 if (m_backups.contains(decl)) {119 return;120 }121 122 m_backups[decl] = {decl->getDeclContext(), decl->getLexicalDeclContext()};123 124 decl->setDeclContext(decl->getASTContext().getTranslationUnitDecl());125 decl->setLexicalDeclContext(decl->getASTContext().getTranslationUnitDecl());126 // Changing the DeclContext might change the linkage. For example, if the127 // entity was previously declared inside a function, it will not be128 // external, but changing the declaration context to the TU will make it129 // external. Make sure this will recompute the linkage if it was computed130 // before.131 decl->invalidateCachedLinkage();132 }133 134 bool ChainPassesThrough(135 clang::Decl *decl, clang::DeclContext *base,136 clang::DeclContext *(clang::Decl::*contextFromDecl)(),137 clang::DeclContext *(clang::DeclContext::*contextFromContext)()) {138 for (DeclContext *decl_ctx = (decl->*contextFromDecl)(); decl_ctx;139 decl_ctx = (decl_ctx->*contextFromContext)()) {140 if (decl_ctx == base) {141 return true;142 }143 }144 145 return false;146 }147 148 clang::Decl *GetEscapedChild(clang::Decl *decl,149 clang::DeclContext *base = nullptr) {150 if (base) {151 // decl's DeclContext chains must pass through base.152 153 if (!ChainPassesThrough(decl, base, &clang::Decl::getDeclContext,154 &clang::DeclContext::getParent) ||155 !ChainPassesThrough(decl, base, &clang::Decl::getLexicalDeclContext,156 &clang::DeclContext::getLexicalParent)) {157 return decl;158 }159 } else {160 base = clang::dyn_cast<clang::DeclContext>(decl);161 162 if (!base) {163 return nullptr;164 }165 }166 167 if (clang::DeclContext *context =168 clang::dyn_cast<clang::DeclContext>(decl)) {169 for (clang::Decl *decl : context->decls()) {170 if (clang::Decl *escaped_child = GetEscapedChild(decl)) {171 return escaped_child;172 }173 }174 }175 176 return nullptr;177 }178 179 void Override(clang::Decl *decl) {180 if (clang::Decl *escaped_child = GetEscapedChild(decl)) {181 Log *log = GetLog(LLDBLog::Expressions);182 183 LLDB_LOG(log,184 " [ClangASTImporter] DeclContextOverride couldn't "185 "override ({0}Decl*){1} - its child ({2}Decl*){3} escapes",186 decl->getDeclKindName(), decl, escaped_child->getDeclKindName(),187 escaped_child);188 lldbassert(0 && "Couldn't override!");189 }190 191 OverrideOne(decl);192 }193 194public:195 DeclContextOverride() = default;196 197 void OverrideAllDeclsFromContainingFunction(clang::Decl *decl) {198 for (DeclContext *decl_context = decl->getLexicalDeclContext();199 decl_context; decl_context = decl_context->getLexicalParent()) {200 DeclContext *redecl_context = decl_context->getRedeclContext();201 202 if (llvm::isa<FunctionDecl>(redecl_context) &&203 llvm::isa<TranslationUnitDecl>(redecl_context->getLexicalParent())) {204 for (clang::Decl *child_decl : decl_context->decls()) {205 Override(child_decl);206 }207 }208 }209 }210 211 ~DeclContextOverride() {212 for (const std::pair<clang::Decl *, Backup> &backup : m_backups) {213 backup.first->setDeclContext(backup.second.decl_context);214 backup.first->setLexicalDeclContext(backup.second.lexical_decl_context);215 }216 }217};218 219namespace {220/// Completes all imported TagDecls at the end of the scope.221///222/// While in a CompleteTagDeclsScope, every decl that could be completed will223/// be completed at the end of the scope (including all Decls that are224/// imported while completing the original Decls).225class CompleteTagDeclsScope : public ClangASTImporter::NewDeclListener {226 ClangASTImporter::ImporterDelegateSP m_delegate;227 /// List of declarations in the target context that need to be completed.228 /// Every declaration should only be completed once and therefore should only229 /// be once in this list.230 llvm::SetVector<NamedDecl *> m_decls_to_complete;231 /// Set of declarations that already were successfully completed (not just232 /// added to m_decls_to_complete).233 llvm::SmallPtrSet<NamedDecl *, 32> m_decls_already_completed;234 clang::ASTContext *m_dst_ctx;235 clang::ASTContext *m_src_ctx;236 ClangASTImporter &importer;237 238 void CompleteDecl(239 Decl *decl,240 lldb_private::ClangASTImporter::ASTContextMetadata const &to_context_md) {241 // The decl that should be completed has to be imported into the target242 // context from some other context.243 assert(to_context_md.hasOrigin(decl));244 // We should only complete decls coming from the source context.245 assert(to_context_md.getOrigin(decl).ctx == m_src_ctx);246 247 Decl *original_decl = to_context_md.getOrigin(decl).decl;248 249 // Complete the decl now.250 TypeSystemClang::GetCompleteDecl(m_src_ctx, original_decl);251 if (auto *tag_decl = dyn_cast<TagDecl>(decl)) {252 if (auto *original_tag_decl = dyn_cast<TagDecl>(original_decl)) {253 if (original_tag_decl->isCompleteDefinition()) {254 m_delegate->ImportDefinitionTo(tag_decl, original_tag_decl);255 tag_decl->setCompleteDefinition(true);256 }257 }258 259 tag_decl->setHasExternalLexicalStorage(false);260 tag_decl->setHasExternalVisibleStorage(false);261 } else if (auto *container_decl = dyn_cast<ObjCContainerDecl>(decl)) {262 container_decl->setHasExternalLexicalStorage(false);263 container_decl->setHasExternalVisibleStorage(false);264 }265 }266 267public:268 /// Constructs a CompleteTagDeclsScope.269 /// \param importer The ClangASTImporter that we should observe.270 /// \param dst_ctx The ASTContext to which Decls are imported.271 /// \param src_ctx The ASTContext from which Decls are imported.272 explicit CompleteTagDeclsScope(ClangASTImporter &importer,273 clang::ASTContext *dst_ctx,274 clang::ASTContext *src_ctx)275 : m_delegate(importer.GetDelegate(dst_ctx, src_ctx)), m_dst_ctx(dst_ctx),276 m_src_ctx(src_ctx), importer(importer) {277 m_delegate->SetImportListener(this);278 }279 280 ~CompleteTagDeclsScope() override {281 ClangASTImporter::ASTContextMetadataSP to_context_md =282 importer.GetContextMetadata(m_dst_ctx);283 284 // Complete all decls we collected until now.285 while (!m_decls_to_complete.empty()) {286 NamedDecl *decl = m_decls_to_complete.pop_back_val();287 m_decls_already_completed.insert(decl);288 289 CompleteDecl(decl, *to_context_md);290 291 to_context_md->removeOrigin(decl);292 }293 294 // Stop listening to imported decls. We do this after clearing the295 // Decls we needed to import to catch all Decls they might have pulled in.296 m_delegate->RemoveImportListener();297 }298 299 void NewDeclImported(clang::Decl *from, clang::Decl *to) override {300 // Filter out decls that we can't complete later.301 if (!isa<TagDecl>(to) && !isa<ObjCInterfaceDecl>(to))302 return;303 auto *from_record_decl = dyn_cast<CXXRecordDecl>(from);304 // We don't need to complete injected class name decls.305 if (from_record_decl && from_record_decl->isInjectedClassName())306 return;307 308 NamedDecl *to_named_decl = dyn_cast<NamedDecl>(to);309 // Check if we already completed this type.310 if (m_decls_already_completed.contains(to_named_decl))311 return;312 // Queue this type to be completed.313 m_decls_to_complete.insert(to_named_decl);314 }315};316} // namespace317 318CompilerType ClangASTImporter::DeportType(TypeSystemClang &dst,319 const CompilerType &src_type) {320 Log *log = GetLog(LLDBLog::Expressions);321 322 auto src_ctxt = src_type.GetTypeSystem<TypeSystemClang>();323 if (!src_ctxt)324 return {};325 326 LLDB_LOG(log,327 " [ClangASTImporter] DeportType called on ({0}Type*){1:x} "328 "from (ASTContext*){2:x} to (ASTContext*){3:x}",329 src_type.GetTypeName(), src_type.GetOpaqueQualType(),330 &src_ctxt->getASTContext(), &dst.getASTContext());331 332 DeclContextOverride decl_context_override;333 334 if (auto *t = ClangUtil::GetQualType(src_type)->getAs<TagType>())335 decl_context_override.OverrideAllDeclsFromContainingFunction(t->getDecl());336 337 CompleteTagDeclsScope complete_scope(*this, &dst.getASTContext(),338 &src_ctxt->getASTContext());339 return CopyType(dst, src_type);340}341 342clang::Decl *ClangASTImporter::DeportDecl(clang::ASTContext *dst_ctx,343 clang::Decl *decl) {344 Log *log = GetLog(LLDBLog::Expressions);345 346 clang::ASTContext *src_ctx = &decl->getASTContext();347 LLDB_LOG(log,348 " [ClangASTImporter] DeportDecl called on ({0}Decl*){1:x} from "349 "(ASTContext*){2:x} to (ASTContext*){3:x}",350 decl->getDeclKindName(), decl, src_ctx, dst_ctx);351 352 DeclContextOverride decl_context_override;353 354 decl_context_override.OverrideAllDeclsFromContainingFunction(decl);355 356 clang::Decl *result;357 {358 CompleteTagDeclsScope complete_scope(*this, dst_ctx, src_ctx);359 result = CopyDecl(dst_ctx, decl);360 }361 362 if (!result)363 return nullptr;364 365 LLDB_LOG(log,366 " [ClangASTImporter] DeportDecl deported ({0}Decl*){1:x} to "367 "({2}Decl*){3:x}",368 decl->getDeclKindName(), decl, result->getDeclKindName(), result);369 370 return result;371}372 373bool ClangASTImporter::CanImport(const Decl *d) {374 if (!d)375 return false;376 if (isa<TagDecl>(d))377 return GetDeclOrigin(d).Valid();378 if (isa<ObjCInterfaceDecl>(d))379 return GetDeclOrigin(d).Valid();380 return false;381}382 383bool ClangASTImporter::CanImport(const CompilerType &type) {384 if (!ClangUtil::IsClangType(type))385 return false;386 387 clang::QualType qual_type(388 ClangUtil::GetCanonicalQualType(ClangUtil::RemoveFastQualifiers(type)));389 390 const clang::Type::TypeClass type_class = qual_type->getTypeClass();391 switch (type_class) {392 case clang::Type::Record:393 return CanImport(qual_type->getAsCXXRecordDecl());394 case clang::Type::Enum:395 return CanImport(llvm::cast<clang::EnumType>(qual_type)->getDecl());396 case clang::Type::ObjCObject:397 case clang::Type::ObjCInterface: {398 const clang::ObjCObjectType *objc_class_type =399 llvm::dyn_cast<clang::ObjCObjectType>(qual_type);400 if (objc_class_type) {401 clang::ObjCInterfaceDecl *class_interface_decl =402 objc_class_type->getInterface();403 // We currently can't complete objective C types through the newly added404 // ASTContext because it only supports TagDecl objects right now...405 return CanImport(class_interface_decl);406 }407 } break;408 409 case clang::Type::Typedef:410 return CanImport(CompilerType(type.GetTypeSystem(),411 llvm::cast<clang::TypedefType>(qual_type)412 ->getDecl()413 ->getUnderlyingType()414 .getAsOpaquePtr()));415 416 case clang::Type::Auto:417 return CanImport(CompilerType(type.GetTypeSystem(),418 llvm::cast<clang::AutoType>(qual_type)419 ->getDeducedType()420 .getAsOpaquePtr()));421 422 case clang::Type::Paren:423 return CanImport(CompilerType(424 type.GetTypeSystem(),425 llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));426 427 default:428 break;429 }430 431 return false;432}433 434bool ClangASTImporter::Import(const CompilerType &type) {435 if (!ClangUtil::IsClangType(type))436 return false;437 438 clang::QualType qual_type(439 ClangUtil::GetCanonicalQualType(ClangUtil::RemoveFastQualifiers(type)));440 441 const clang::Type::TypeClass type_class = qual_type->getTypeClass();442 switch (type_class) {443 case clang::Type::Record: {444 const clang::CXXRecordDecl *cxx_record_decl =445 qual_type->getAsCXXRecordDecl();446 if (cxx_record_decl) {447 if (GetDeclOrigin(cxx_record_decl).Valid())448 return CompleteAndFetchChildren(qual_type);449 }450 } break;451 452 case clang::Type::Enum: {453 clang::EnumDecl *enum_decl =454 llvm::cast<clang::EnumType>(qual_type)->getDecl();455 if (enum_decl) {456 if (GetDeclOrigin(enum_decl).Valid())457 return CompleteAndFetchChildren(qual_type);458 }459 } break;460 461 case clang::Type::ObjCObject:462 case clang::Type::ObjCInterface: {463 const clang::ObjCObjectType *objc_class_type =464 llvm::dyn_cast<clang::ObjCObjectType>(qual_type);465 if (objc_class_type) {466 clang::ObjCInterfaceDecl *class_interface_decl =467 objc_class_type->getInterface();468 // We currently can't complete objective C types through the newly added469 // ASTContext because it only supports TagDecl objects right now...470 if (class_interface_decl) {471 if (GetDeclOrigin(class_interface_decl).Valid())472 return CompleteAndFetchChildren(qual_type);473 }474 }475 } break;476 477 case clang::Type::Typedef:478 return Import(CompilerType(type.GetTypeSystem(),479 llvm::cast<clang::TypedefType>(qual_type)480 ->getDecl()481 ->getUnderlyingType()482 .getAsOpaquePtr()));483 484 case clang::Type::Auto:485 return Import(CompilerType(type.GetTypeSystem(),486 llvm::cast<clang::AutoType>(qual_type)487 ->getDeducedType()488 .getAsOpaquePtr()));489 490 case clang::Type::Paren:491 return Import(CompilerType(492 type.GetTypeSystem(),493 llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));494 495 default:496 break;497 }498 return false;499}500 501bool ClangASTImporter::CompleteType(const CompilerType &compiler_type) {502 if (!CanImport(compiler_type))503 return false;504 505 if (Import(compiler_type)) {506 TypeSystemClang::CompleteTagDeclarationDefinition(compiler_type);507 return true;508 }509 510 TypeSystemClang::SetHasExternalStorage(compiler_type.GetOpaqueQualType(),511 false);512 return false;513}514 515/// Copy layout information from \ref source_map to the \ref destination_map.516///517/// In the process of copying over layout info, we may need to import518/// decls from the \ref source_map. This function will use the supplied519/// \ref importer to import the necessary decls into \ref dest_ctx.520///521/// \param[in,out] dest_ctx Destination ASTContext into which we import522/// decls from the \ref source_map.523/// \param[out] destination_map A map from decls in \ref dest_ctx to an524/// integral offest, which will be copies525/// of the decl/offest pairs in \ref source_map526/// if successful.527/// \param[in] source_map A map from decls to integral offests. These will528/// be copied into \ref destination_map.529/// \param[in,out] importer Used to import decls into \ref dest_ctx.530///531/// \returns On success, will return 'true' and the offsets in \ref532/// destination_map533/// are usable copies of \ref source_map.534template <class D, class O>535static bool ImportOffsetMap(clang::ASTContext *dest_ctx,536 llvm::DenseMap<const D *, O> &destination_map,537 llvm::DenseMap<const D *, O> &source_map,538 ClangASTImporter &importer) {539 // When importing fields into a new record, clang has a hard requirement that540 // fields be imported in field offset order. Since they are stored in a541 // DenseMap with a pointer as the key type, this means we cannot simply542 // iterate over the map, as the order will be non-deterministic. Instead we543 // have to sort by the offset and then insert in sorted order.544 typedef llvm::DenseMap<const D *, O> MapType;545 typedef typename MapType::value_type PairType;546 std::vector<PairType> sorted_items;547 sorted_items.reserve(source_map.size());548 sorted_items.assign(source_map.begin(), source_map.end());549 llvm::sort(sorted_items, llvm::less_second());550 551 for (const auto &item : sorted_items) {552 DeclFromUser<D> user_decl(const_cast<D *>(item.first));553 DeclFromParser<D> parser_decl(user_decl.Import(dest_ctx, importer));554 if (parser_decl.IsInvalid())555 return false;556 destination_map.insert(557 std::pair<const D *, O>(parser_decl.decl, item.second));558 }559 560 return true;561}562 563/// Given a CXXRecordDecl, will calculate and populate \ref base_offsets564/// with the integral offsets of any of its (possibly virtual) base classes.565///566/// \param[in] record_layout ASTRecordLayout of \ref record.567/// \param[in] record The record that we're calculating the base layouts of.568/// \param[out] base_offsets Map of base-class decl to integral offset which569/// this function will fill in.570///571/// \returns On success, will return 'true' and the offsets in \ref base_offsets572/// are usable.573template <bool IsVirtual>574bool ExtractBaseOffsets(const ASTRecordLayout &record_layout,575 DeclFromUser<const CXXRecordDecl> &record,576 llvm::DenseMap<const clang::CXXRecordDecl *,577 clang::CharUnits> &base_offsets) {578 for (CXXRecordDecl::base_class_const_iterator579 bi = (IsVirtual ? record->vbases_begin() : record->bases_begin()),580 be = (IsVirtual ? record->vbases_end() : record->bases_end());581 bi != be; ++bi) {582 if (!IsVirtual && bi->isVirtual())583 continue;584 585 const clang::Type *origin_base_type = bi->getType().getTypePtr();586 const clang::RecordType *origin_base_record_type =587 origin_base_type->getAs<RecordType>();588 589 if (!origin_base_record_type)590 return false;591 592 DeclFromUser<RecordDecl> origin_base_record(593 origin_base_record_type->getDecl());594 595 if (origin_base_record.IsInvalid())596 return false;597 598 DeclFromUser<CXXRecordDecl> origin_base_cxx_record(599 DynCast<CXXRecordDecl>(origin_base_record));600 601 if (origin_base_cxx_record.IsInvalid())602 return false;603 604 CharUnits base_offset;605 606 if (IsVirtual)607 base_offset =608 record_layout.getVBaseClassOffset(origin_base_cxx_record.decl);609 else610 base_offset =611 record_layout.getBaseClassOffset(origin_base_cxx_record.decl);612 613 base_offsets.insert(std::pair<const CXXRecordDecl *, CharUnits>(614 origin_base_cxx_record.decl, base_offset));615 }616 617 return true;618}619 620bool ClangASTImporter::importRecordLayoutFromOrigin(621 const RecordDecl *record, uint64_t &size, uint64_t &alignment,622 llvm::DenseMap<const clang::FieldDecl *, uint64_t> &field_offsets,623 llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>624 &base_offsets,625 llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>626 &vbase_offsets) {627 628 Log *log = GetLog(LLDBLog::Expressions);629 630 clang::ASTContext &dest_ctx = record->getASTContext();631 LLDB_LOG(log,632 "LayoutRecordType on (ASTContext*){0:x} '{1}' for (RecordDecl*)"633 "{2:x} [name = '{3}']",634 &dest_ctx,635 TypeSystemClang::GetASTContext(&dest_ctx)->getDisplayName(), record,636 record->getName());637 638 DeclFromParser<const RecordDecl> parser_record(record);639 DeclFromUser<const RecordDecl> origin_record(parser_record.GetOrigin(*this));640 641 if (origin_record.IsInvalid())642 return false;643 644 std::remove_reference_t<decltype(field_offsets)> origin_field_offsets;645 std::remove_reference_t<decltype(base_offsets)> origin_base_offsets;646 std::remove_reference_t<decltype(vbase_offsets)> origin_virtual_base_offsets;647 648 TypeSystemClang::GetCompleteDecl(649 &origin_record->getASTContext(),650 const_cast<RecordDecl *>(origin_record.decl));651 652 clang::RecordDecl *definition = origin_record.decl->getDefinition();653 if (!definition || !definition->isCompleteDefinition())654 return false;655 656 const ASTRecordLayout &record_layout(657 origin_record->getASTContext().getASTRecordLayout(origin_record.decl));658 659 int field_idx = 0, field_count = record_layout.getFieldCount();660 661 for (RecordDecl::field_iterator fi = origin_record->field_begin(),662 fe = origin_record->field_end();663 fi != fe; ++fi) {664 if (field_idx >= field_count)665 return false; // Layout didn't go well. Bail out.666 667 uint64_t field_offset = record_layout.getFieldOffset(field_idx);668 669 origin_field_offsets.insert(670 std::pair<const FieldDecl *, uint64_t>(*fi, field_offset));671 672 field_idx++;673 }674 675 DeclFromUser<const CXXRecordDecl> origin_cxx_record(676 DynCast<const CXXRecordDecl>(origin_record));677 678 if (origin_cxx_record.IsValid()) {679 if (!ExtractBaseOffsets<false>(record_layout, origin_cxx_record,680 origin_base_offsets) ||681 !ExtractBaseOffsets<true>(record_layout, origin_cxx_record,682 origin_virtual_base_offsets))683 return false;684 }685 686 if (!ImportOffsetMap(&dest_ctx, field_offsets, origin_field_offsets, *this) ||687 !ImportOffsetMap(&dest_ctx, base_offsets, origin_base_offsets, *this) ||688 !ImportOffsetMap(&dest_ctx, vbase_offsets, origin_virtual_base_offsets,689 *this))690 return false;691 692 size = record_layout.getSize().getQuantity() * dest_ctx.getCharWidth();693 alignment =694 record_layout.getAlignment().getQuantity() * dest_ctx.getCharWidth();695 696 if (log) {697 LLDB_LOG(log, "LRT returned:");698 LLDB_LOG(log, "LRT Original = (RecordDecl*){0:x}",699 static_cast<const void *>(origin_record.decl));700 LLDB_LOG(log, "LRT Size = {0}", size);701 LLDB_LOG(log, "LRT Alignment = {0}", alignment);702 LLDB_LOG(log, "LRT Fields:");703 for (RecordDecl::field_iterator fi = record->field_begin(),704 fe = record->field_end();705 fi != fe; ++fi) {706 LLDB_LOG(707 log,708 "LRT (FieldDecl*){0:x}, Name = '{1}', Type = '{2}', Offset = "709 "{3} bits",710 *fi, fi->getName(), fi->getType().getAsString(), field_offsets[*fi]);711 }712 DeclFromParser<const CXXRecordDecl> parser_cxx_record =713 DynCast<const CXXRecordDecl>(parser_record);714 if (parser_cxx_record.IsValid()) {715 LLDB_LOG(log, "LRT Bases:");716 for (CXXRecordDecl::base_class_const_iterator717 bi = parser_cxx_record->bases_begin(),718 be = parser_cxx_record->bases_end();719 bi != be; ++bi) {720 bool is_virtual = bi->isVirtual();721 722 QualType base_type = bi->getType();723 const RecordType *base_record_type = base_type->getAs<RecordType>();724 DeclFromParser<RecordDecl> base_record(base_record_type->getDecl());725 DeclFromParser<CXXRecordDecl> base_cxx_record =726 DynCast<CXXRecordDecl>(base_record);727 728 LLDB_LOG(log,729 "LRT {0}(CXXRecordDecl*){1:x}, Name = '{2}', Offset = "730 "{3} chars",731 (is_virtual ? "Virtual " : ""), base_cxx_record.decl,732 base_cxx_record.decl->getName(),733 (is_virtual734 ? vbase_offsets[base_cxx_record.decl].getQuantity()735 : base_offsets[base_cxx_record.decl].getQuantity()));736 }737 } else {738 LLDB_LOG(log, "LRD Not a CXXRecord, so no bases");739 }740 }741 742 return true;743}744 745bool ClangASTImporter::LayoutRecordType(746 const clang::RecordDecl *record_decl, uint64_t &bit_size,747 uint64_t &alignment,748 llvm::DenseMap<const clang::FieldDecl *, uint64_t> &field_offsets,749 llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>750 &base_offsets,751 llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>752 &vbase_offsets) {753 RecordDeclToLayoutMap::iterator pos =754 m_record_decl_to_layout_map.find(record_decl);755 base_offsets.clear();756 vbase_offsets.clear();757 if (pos != m_record_decl_to_layout_map.end()) {758 bit_size = pos->second.bit_size;759 alignment = pos->second.alignment;760 field_offsets.swap(pos->second.field_offsets);761 base_offsets.swap(pos->second.base_offsets);762 vbase_offsets.swap(pos->second.vbase_offsets);763 m_record_decl_to_layout_map.erase(pos);764 return true;765 }766 767 // It's possible that we calculated the layout in a different768 // ClangASTImporter instance. Try to import such layout if769 // our decl has an origin.770 if (auto origin = GetDeclOrigin(record_decl); origin.Valid())771 if (importRecordLayoutFromOrigin(record_decl, bit_size, alignment,772 field_offsets, base_offsets,773 vbase_offsets))774 return true;775 776 bit_size = 0;777 alignment = 0;778 field_offsets.clear();779 780 return false;781}782 783void ClangASTImporter::SetRecordLayout(clang::RecordDecl *decl,784 const LayoutInfo &layout) {785 m_record_decl_to_layout_map.insert(std::make_pair(decl, layout));786}787 788bool ClangASTImporter::CompleteTagDecl(clang::TagDecl *decl) {789 DeclOrigin decl_origin = GetDeclOrigin(decl);790 791 if (!decl_origin.Valid())792 return false;793 794 if (!TypeSystemClang::GetCompleteDecl(decl_origin.ctx, decl_origin.decl))795 return false;796 797 ImporterDelegateSP delegate_sp(798 GetDelegate(&decl->getASTContext(), decl_origin.ctx));799 800 ASTImporterDelegate::CxxModuleScope std_scope(*delegate_sp,801 &decl->getASTContext());802 if (delegate_sp)803 delegate_sp->ImportDefinitionTo(decl, decl_origin.decl);804 805 return true;806}807 808bool ClangASTImporter::CompleteTagDeclWithOrigin(clang::TagDecl *decl,809 clang::TagDecl *origin_decl) {810 clang::ASTContext *origin_ast_ctx = &origin_decl->getASTContext();811 812 if (!TypeSystemClang::GetCompleteDecl(origin_ast_ctx, origin_decl))813 return false;814 815 ImporterDelegateSP delegate_sp(816 GetDelegate(&decl->getASTContext(), origin_ast_ctx));817 818 if (delegate_sp)819 delegate_sp->ImportDefinitionTo(decl, origin_decl);820 821 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());822 823 context_md->setOrigin(decl, DeclOrigin(origin_ast_ctx, origin_decl));824 return true;825}826 827bool ClangASTImporter::CompleteObjCInterfaceDecl(828 clang::ObjCInterfaceDecl *interface_decl) {829 DeclOrigin decl_origin = GetDeclOrigin(interface_decl);830 831 if (!decl_origin.Valid())832 return false;833 834 if (!TypeSystemClang::GetCompleteDecl(decl_origin.ctx, decl_origin.decl))835 return false;836 837 ImporterDelegateSP delegate_sp(838 GetDelegate(&interface_decl->getASTContext(), decl_origin.ctx));839 840 if (delegate_sp)841 delegate_sp->ImportDefinitionTo(interface_decl, decl_origin.decl);842 843 if (ObjCInterfaceDecl *super_class = interface_decl->getSuperClass())844 RequireCompleteType(clang::QualType(super_class->getTypeForDecl(), 0));845 846 return true;847}848 849bool ClangASTImporter::CompleteAndFetchChildren(clang::QualType type) {850 if (!RequireCompleteType(type))851 return false;852 853 Log *log = GetLog(LLDBLog::Expressions);854 855 if (const TagType *tag_type = type->getAs<TagType>()) {856 TagDecl *tag_decl = tag_type->getDecl();857 858 DeclOrigin decl_origin = GetDeclOrigin(tag_decl);859 860 if (!decl_origin.Valid())861 return false;862 863 ImporterDelegateSP delegate_sp(864 GetDelegate(&tag_decl->getASTContext(), decl_origin.ctx));865 866 ASTImporterDelegate::CxxModuleScope std_scope(*delegate_sp,867 &tag_decl->getASTContext());868 869 TagDecl *origin_tag_decl = llvm::dyn_cast<TagDecl>(decl_origin.decl);870 871 for (Decl *origin_child_decl : origin_tag_decl->decls()) {872 llvm::Expected<Decl *> imported_or_err =873 delegate_sp->Import(origin_child_decl);874 if (!imported_or_err) {875 LLDB_LOG_ERROR(log, imported_or_err.takeError(),876 "Couldn't import decl: {0}");877 return false;878 }879 }880 881 if (RecordDecl *record_decl = dyn_cast<RecordDecl>(origin_tag_decl))882 record_decl->setHasLoadedFieldsFromExternalStorage(true);883 884 return true;885 }886 887 if (const ObjCObjectType *objc_object_type = type->getAs<ObjCObjectType>()) {888 if (ObjCInterfaceDecl *objc_interface_decl =889 objc_object_type->getInterface()) {890 DeclOrigin decl_origin = GetDeclOrigin(objc_interface_decl);891 892 if (!decl_origin.Valid())893 return false;894 895 ImporterDelegateSP delegate_sp(896 GetDelegate(&objc_interface_decl->getASTContext(), decl_origin.ctx));897 898 ObjCInterfaceDecl *origin_interface_decl =899 llvm::dyn_cast<ObjCInterfaceDecl>(decl_origin.decl);900 901 for (Decl *origin_child_decl : origin_interface_decl->decls()) {902 llvm::Expected<Decl *> imported_or_err =903 delegate_sp->Import(origin_child_decl);904 if (!imported_or_err) {905 LLDB_LOG_ERROR(log, imported_or_err.takeError(),906 "Couldn't import decl: {0}");907 return false;908 }909 }910 911 return true;912 }913 return false;914 }915 916 return true;917}918 919bool ClangASTImporter::RequireCompleteType(clang::QualType type) {920 if (type.isNull())921 return false;922 923 if (const TagType *tag_type = type->getAs<TagType>()) {924 TagDecl *tag_decl = tag_type->getDecl();925 926 if (tag_decl->getDefinition())927 return true;928 929 return CompleteTagDecl(tag_decl);930 }931 if (const ObjCObjectType *objc_object_type = type->getAs<ObjCObjectType>()) {932 if (ObjCInterfaceDecl *objc_interface_decl =933 objc_object_type->getInterface())934 return CompleteObjCInterfaceDecl(objc_interface_decl);935 return false;936 }937 if (const ArrayType *array_type = type->getAsArrayTypeUnsafe())938 return RequireCompleteType(array_type->getElementType());939 if (const AtomicType *atomic_type = type->getAs<AtomicType>())940 return RequireCompleteType(atomic_type->getPointeeType());941 942 return true;943}944 945std::optional<ClangASTMetadata>946ClangASTImporter::GetDeclMetadata(const clang::Decl *decl) {947 DeclOrigin decl_origin = GetDeclOrigin(decl);948 949 if (decl_origin.Valid()) {950 TypeSystemClang *ast = TypeSystemClang::GetASTContext(decl_origin.ctx);951 return ast->GetMetadata(decl_origin.decl);952 }953 TypeSystemClang *ast = TypeSystemClang::GetASTContext(&decl->getASTContext());954 return ast->GetMetadata(decl);955}956 957ClangASTImporter::DeclOrigin958ClangASTImporter::GetDeclOrigin(const clang::Decl *decl) {959 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());960 961 return context_md->getOrigin(decl);962}963 964void ClangASTImporter::SetDeclOrigin(const clang::Decl *decl,965 clang::Decl *original_decl) {966 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());967 context_md->setOrigin(968 decl, DeclOrigin(&original_decl->getASTContext(), original_decl));969}970 971void ClangASTImporter::RegisterNamespaceMap(const clang::NamespaceDecl *decl,972 NamespaceMapSP &namespace_map) {973 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());974 975 context_md->m_namespace_maps[decl] = namespace_map;976}977 978ClangASTImporter::NamespaceMapSP979ClangASTImporter::GetNamespaceMap(const clang::NamespaceDecl *decl) {980 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());981 982 NamespaceMetaMap &namespace_maps = context_md->m_namespace_maps;983 984 NamespaceMetaMap::iterator iter = namespace_maps.find(decl);985 986 if (iter != namespace_maps.end())987 return iter->second;988 return NamespaceMapSP();989}990 991void ClangASTImporter::BuildNamespaceMap(const clang::NamespaceDecl *decl) {992 assert(decl);993 ASTContextMetadataSP context_md = GetContextMetadata(&decl->getASTContext());994 995 const DeclContext *parent_context = decl->getDeclContext();996 const NamespaceDecl *parent_namespace =997 dyn_cast<NamespaceDecl>(parent_context);998 NamespaceMapSP parent_map;999 1000 if (parent_namespace)1001 parent_map = GetNamespaceMap(parent_namespace);1002 1003 NamespaceMapSP new_map;1004 1005 new_map = std::make_shared<NamespaceMap>();1006 1007 if (context_md->m_map_completer) {1008 std::string namespace_string = decl->getDeclName().getAsString();1009 1010 context_md->m_map_completer->CompleteNamespaceMap(1011 new_map, ConstString(namespace_string.c_str()), parent_map);1012 }1013 1014 context_md->m_namespace_maps[decl] = new_map;1015}1016 1017void ClangASTImporter::ForgetDestination(clang::ASTContext *dst_ast) {1018 Log *log = GetLog(LLDBLog::Expressions);1019 1020 LLDB_LOG(log,1021 " [ClangASTImporter] Forgetting destination (ASTContext*){0:x}",1022 dst_ast);1023 1024 m_metadata_map.erase(dst_ast);1025}1026 1027void ClangASTImporter::ForgetSource(clang::ASTContext *dst_ast,1028 clang::ASTContext *src_ast) {1029 ASTContextMetadataSP md = MaybeGetContextMetadata(dst_ast);1030 1031 Log *log = GetLog(LLDBLog::Expressions);1032 1033 LLDB_LOG(log,1034 " [ClangASTImporter] Forgetting source->dest "1035 "(ASTContext*){0:x}->(ASTContext*){1:x}",1036 src_ast, dst_ast);1037 1038 if (!md)1039 return;1040 1041 md->m_delegates.erase(src_ast);1042 md->removeOriginsWithContext(src_ast);1043}1044 1045ClangASTImporter::MapCompleter::~MapCompleter() = default;1046 1047llvm::Expected<Decl *>1048ClangASTImporter::ASTImporterDelegate::ImportImpl(Decl *From) {1049 // FIXME: The Minimal import mode of clang::ASTImporter does not correctly1050 // import Lambda definitions. Work around this for now by not importing1051 // lambdas at all. This is most likely encountered when importing decls from1052 // the `std` module (not from debug-info), where lambdas can be defined in1053 // inline function bodies. Those will be imported by LLDB.1054 if (const auto *CXX = llvm::dyn_cast<clang::CXXRecordDecl>(From))1055 if (CXX->isLambda())1056 return llvm::make_error<ASTImportError>(1057 ASTImportError::UnsupportedConstruct);1058 1059 if (m_std_handler) {1060 std::optional<Decl *> D = m_std_handler->Import(From);1061 if (D) {1062 // Make sure we don't use this decl later to map it back to it's original1063 // decl. The decl the CxxModuleHandler created has nothing to do with1064 // the one from debug info, and linking those two would just cause the1065 // ASTImporter to try 'updating' the module decl with the minimal one from1066 // the debug info.1067 m_decls_to_ignore.insert(*D);1068 return *D;1069 }1070 }1071 1072 // Check which ASTContext this declaration originally came from.1073 DeclOrigin origin = m_main.GetDeclOrigin(From);1074 1075 // Prevent infinite recursion when the origin tracking contains a cycle.1076 assert(origin.decl != From && "Origin points to itself?");1077 1078 // If it originally came from the target ASTContext then we can just1079 // pretend that the original is the one we imported. This can happen for1080 // example when inspecting a persistent declaration from the scratch1081 // ASTContext (which will provide the declaration when parsing the1082 // expression and then we later try to copy the declaration back to the1083 // scratch ASTContext to store the result).1084 // Without this check we would ask the ASTImporter to import a declaration1085 // into the same ASTContext where it came from (which doesn't make a lot of1086 // sense).1087 if (origin.Valid() && origin.ctx == &getToContext()) {1088 RegisterImportedDecl(From, origin.decl);1089 return origin.decl;1090 }1091 1092 // This declaration came originally from another ASTContext. Instead of1093 // copying our potentially incomplete 'From' Decl we instead go to the1094 // original ASTContext and copy the original to the target. This is not1095 // only faster than first completing our current decl and then copying it1096 // to the target, but it also prevents that indirectly copying the same1097 // declaration to the same target requires the ASTImporter to merge all1098 // the different decls that appear to come from different ASTContexts (even1099 // though all these different source ASTContexts just got a copy from1100 // one source AST).1101 if (origin.Valid()) {1102 auto R = m_main.CopyDecl(&getToContext(), origin.decl);1103 if (R) {1104 RegisterImportedDecl(From, R);1105 return R;1106 }1107 }1108 1109 // If we have a forcefully completed type, try to find an actual definition1110 // for it in other modules.1111 std::optional<ClangASTMetadata> md = m_main.GetDeclMetadata(From);1112 auto *td = dyn_cast<TagDecl>(From);1113 if (td && md && md->IsForcefullyCompleted()) {1114 Log *log = GetLog(LLDBLog::Expressions);1115 LLDB_LOG(log,1116 "[ClangASTImporter] Searching for a complete definition of {0} in "1117 "other modules",1118 td->getName());1119 Expected<DeclContext *> dc_or_err = ImportContext(td->getDeclContext());1120 if (!dc_or_err)1121 return dc_or_err.takeError();1122 Expected<DeclarationName> dn_or_err = Import(td->getDeclName());1123 if (!dn_or_err)1124 return dn_or_err.takeError();1125 DeclContext *dc = *dc_or_err;1126 DeclContext::lookup_result lr = dc->lookup(*dn_or_err);1127 for (clang::Decl *candidate : lr) {1128 if (candidate->getKind() == From->getKind()) {1129 RegisterImportedDecl(From, candidate);1130 m_decls_to_ignore.insert(candidate);1131 return candidate;1132 }1133 }1134 LLDB_LOG(log, "[ClangASTImporter] Complete definition not found");1135 }1136 1137 return ASTImporter::ImportImpl(From);1138}1139 1140void ClangASTImporter::ASTImporterDelegate::ImportDefinitionTo(1141 clang::Decl *to, clang::Decl *from) {1142 Log *log = GetLog(LLDBLog::Expressions);1143 1144 auto getDeclName = [](Decl const *decl) {1145 std::string name_string;1146 if (auto const *from_named_decl = dyn_cast<clang::NamedDecl>(decl)) {1147 llvm::raw_string_ostream name_stream(name_string);1148 from_named_decl->printName(name_stream);1149 }1150 1151 return name_string;1152 };1153 1154 if (log) {1155 if (auto *D = GetAlreadyImportedOrNull(from); D && D != to) {1156 LLDB_LOG(1157 log,1158 "[ClangASTImporter] ERROR: overwriting an already imported decl "1159 "'{0:x}' ('{1}') from '{2:x}' with '{3:x}'. Likely due to a name "1160 "conflict when importing '{1}'.",1161 D, getDeclName(from), from, to);1162 }1163 }1164 1165 // We might have a forward declaration from a shared library that we1166 // gave external lexical storage so that Clang asks us about the full1167 // definition when it needs it. In this case the ASTImporter isn't aware1168 // that the forward decl from the shared library is the actual import1169 // target but would create a second declaration that would then be defined.1170 // We want that 'to' is actually complete after this function so let's1171 // tell the ASTImporter that 'to' was imported from 'from'.1172 MapImported(from, to);1173 1174 if (llvm::Error err = ImportDefinition(from)) {1175 LLDB_LOG_ERROR(log, std::move(err),1176 "[ClangASTImporter] Error during importing definition: {0}");1177 return;1178 }1179 1180 if (clang::TagDecl *to_tag = dyn_cast<clang::TagDecl>(to)) {1181 if (clang::TagDecl *from_tag = dyn_cast<clang::TagDecl>(from)) {1182 to_tag->setCompleteDefinition(from_tag->isCompleteDefinition());1183 1184 if (Log *log_ast = GetLog(LLDBLog::AST)) {1185 LLDB_LOG(log_ast,1186 "==== [ClangASTImporter][TUDecl: {0:x}] Imported "1187 "({1}Decl*){2:x}, named {3} (from "1188 "(Decl*){4:x})",1189 static_cast<void *>(to->getTranslationUnitDecl()),1190 from->getDeclKindName(), static_cast<void *>(to),1191 getDeclName(from), static_cast<void *>(from));1192 1193 // Log the AST of the TU.1194 std::string ast_string;1195 llvm::raw_string_ostream ast_stream(ast_string);1196 to->getTranslationUnitDecl()->dump(ast_stream);1197 LLDB_LOG(log_ast, "{0}", ast_string);1198 }1199 }1200 }1201 1202 // If we're dealing with an Objective-C class, ensure that the inheritance1203 // has been set up correctly. The ASTImporter may not do this correctly if1204 // the class was originally sourced from symbols.1205 1206 if (ObjCInterfaceDecl *to_objc_interface = dyn_cast<ObjCInterfaceDecl>(to)) {1207 ObjCInterfaceDecl *to_superclass = to_objc_interface->getSuperClass();1208 1209 if (to_superclass)1210 return; // we're not going to override it if it's set1211 1212 ObjCInterfaceDecl *from_objc_interface = dyn_cast<ObjCInterfaceDecl>(from);1213 1214 if (!from_objc_interface)1215 return;1216 1217 ObjCInterfaceDecl *from_superclass = from_objc_interface->getSuperClass();1218 1219 if (!from_superclass)1220 return;1221 1222 llvm::Expected<Decl *> imported_from_superclass_decl =1223 Import(from_superclass);1224 1225 if (!imported_from_superclass_decl) {1226 LLDB_LOG_ERROR(log, imported_from_superclass_decl.takeError(),1227 "Couldn't import decl: {0}");1228 return;1229 }1230 1231 ObjCInterfaceDecl *imported_from_superclass =1232 dyn_cast<ObjCInterfaceDecl>(*imported_from_superclass_decl);1233 1234 if (!imported_from_superclass)1235 return;1236 1237 if (!to_objc_interface->hasDefinition())1238 to_objc_interface->startDefinition();1239 1240 to_objc_interface->setSuperClass(m_source_ctx->getTrivialTypeSourceInfo(1241 m_source_ctx->getObjCInterfaceType(imported_from_superclass)));1242 }1243}1244 1245/// Takes a CXXMethodDecl and completes the return type if necessary. This1246/// is currently only necessary for virtual functions with covariant return1247/// types where Clang's CodeGen expects that the underlying records are already1248/// completed.1249static void MaybeCompleteReturnType(ClangASTImporter &importer,1250 CXXMethodDecl *to_method) {1251 if (!to_method->isVirtual())1252 return;1253 QualType return_type = to_method->getReturnType();1254 if (!return_type->isPointerType() && !return_type->isReferenceType())1255 return;1256 1257 clang::RecordDecl *rd = return_type->getPointeeType()->getAsRecordDecl();1258 if (!rd)1259 return;1260 if (rd->getDefinition())1261 return;1262 1263 importer.CompleteTagDecl(rd);1264}1265 1266/// Recreate a module with its parents in \p to_source and return its id.1267static OptionalClangModuleID1268RemapModule(OptionalClangModuleID from_id,1269 ClangExternalASTSourceCallbacks &from_source,1270 ClangExternalASTSourceCallbacks &to_source) {1271 if (!from_id.HasValue())1272 return {};1273 clang::Module *module = from_source.getModule(from_id.GetValue());1274 OptionalClangModuleID parent = RemapModule(1275 from_source.GetIDForModule(module->Parent), from_source, to_source);1276 TypeSystemClang &to_ts = to_source.GetTypeSystem();1277 return to_ts.GetOrCreateClangModule(module->Name, parent, module->IsFramework,1278 module->IsExplicit);1279}1280 1281void ClangASTImporter::ASTImporterDelegate::Imported(clang::Decl *from,1282 clang::Decl *to) {1283 Log *log = GetLog(LLDBLog::Expressions);1284 1285 // Some decls shouldn't be tracked here because they were not created by1286 // copying 'from' to 'to'. Just exit early for those.1287 if (m_decls_to_ignore.count(to))1288 return;1289 1290 // Transfer module ownership information.1291 auto *from_source = llvm::dyn_cast_or_null<ClangExternalASTSourceCallbacks>(1292 getFromContext().getExternalSource());1293 // Can also be a ClangASTSourceProxy.1294 auto *to_source = llvm::dyn_cast_or_null<ClangExternalASTSourceCallbacks>(1295 getToContext().getExternalSource());1296 if (from_source && to_source) {1297 OptionalClangModuleID from_id(from->getOwningModuleID());1298 OptionalClangModuleID to_id =1299 RemapModule(from_id, *from_source, *to_source);1300 TypeSystemClang &to_ts = to_source->GetTypeSystem();1301 to_ts.SetOwningModule(to, to_id);1302 }1303 1304 lldb::user_id_t user_id = LLDB_INVALID_UID;1305 if (std::optional<ClangASTMetadata> metadata = m_main.GetDeclMetadata(from))1306 user_id = metadata->GetUserID();1307 1308 if (log) {1309 if (NamedDecl *from_named_decl = dyn_cast<clang::NamedDecl>(from)) {1310 std::string name_string;1311 llvm::raw_string_ostream name_stream(name_string);1312 from_named_decl->printName(name_stream);1313 1314 LLDB_LOG(1315 log,1316 " [ClangASTImporter] Imported ({0}Decl*){1:x}, named {2} (from "1317 "(Decl*){3:x}), metadata {4}",1318 from->getDeclKindName(), to, name_string, from, user_id);1319 } else {1320 LLDB_LOG(log,1321 " [ClangASTImporter] Imported ({0}Decl*){1:x} (from "1322 "(Decl*){2:x}), metadata {3}",1323 from->getDeclKindName(), to, from, user_id);1324 }1325 }1326 1327 ASTContextMetadataSP to_context_md =1328 m_main.GetContextMetadata(&to->getASTContext());1329 ASTContextMetadataSP from_context_md =1330 m_main.MaybeGetContextMetadata(m_source_ctx);1331 1332 if (from_context_md) {1333 DeclOrigin origin = from_context_md->getOrigin(from);1334 1335 if (origin.Valid()) {1336 if (origin.ctx != &to->getASTContext()) {1337 if (!to_context_md->hasOrigin(to) || user_id != LLDB_INVALID_UID)1338 to_context_md->setOrigin(to, origin);1339 1340 LLDB_LOG(log,1341 " [ClangASTImporter] Propagated origin "1342 "(Decl*){0:x}/(ASTContext*){1:x} from (ASTContext*){2:x} to "1343 "(ASTContext*){3:x}",1344 origin.decl, origin.ctx, &from->getASTContext(),1345 &to->getASTContext());1346 }1347 } else {1348 if (m_new_decl_listener)1349 m_new_decl_listener->NewDeclImported(from, to);1350 1351 if (!to_context_md->hasOrigin(to) || user_id != LLDB_INVALID_UID)1352 to_context_md->setOrigin(to, DeclOrigin(m_source_ctx, from));1353 1354 LLDB_LOG(log,1355 " [ClangASTImporter] Decl has no origin information in "1356 "(ASTContext*){0:x}",1357 &from->getASTContext());1358 }1359 1360 if (auto *to_namespace = dyn_cast<clang::NamespaceDecl>(to)) {1361 auto *from_namespace = cast<clang::NamespaceDecl>(from);1362 1363 NamespaceMetaMap &namespace_maps = from_context_md->m_namespace_maps;1364 1365 NamespaceMetaMap::iterator namespace_map_iter =1366 namespace_maps.find(from_namespace);1367 1368 if (namespace_map_iter != namespace_maps.end())1369 to_context_md->m_namespace_maps[to_namespace] =1370 namespace_map_iter->second;1371 }1372 } else {1373 to_context_md->setOrigin(to, DeclOrigin(m_source_ctx, from));1374 1375 LLDB_LOG(log,1376 " [ClangASTImporter] Sourced origin "1377 "(Decl*){0:x}/(ASTContext*){1:x} into (ASTContext*){2:x}",1378 from, m_source_ctx, &to->getASTContext());1379 }1380 1381 if (auto *to_namespace_decl = dyn_cast<NamespaceDecl>(to)) {1382 m_main.BuildNamespaceMap(to_namespace_decl);1383 to_namespace_decl->setHasExternalVisibleStorage();1384 }1385 1386 MarkDeclImported(from, to);1387}1388 1389void ClangASTImporter::ASTImporterDelegate::MarkDeclImported(Decl *from,1390 Decl *to) {1391 Log *log = GetLog(LLDBLog::Expressions);1392 1393 if (auto *to_tag_decl = dyn_cast<TagDecl>(to)) {1394 to_tag_decl->setHasExternalLexicalStorage();1395 to_tag_decl->getPrimaryContext()->setMustBuildLookupTable();1396 auto from_tag_decl = cast<TagDecl>(from);1397 1398 LLDB_LOG(1399 log,1400 " [ClangASTImporter] To is a TagDecl - attributes {0}{1} [{2}->{3}]",1401 (to_tag_decl->hasExternalLexicalStorage() ? " Lexical" : ""),1402 (to_tag_decl->hasExternalVisibleStorage() ? " Visible" : ""),1403 (from_tag_decl->isCompleteDefinition() ? "complete" : "incomplete"),1404 (to_tag_decl->isCompleteDefinition() ? "complete" : "incomplete"));1405 }1406 1407 if (auto *to_container_decl = dyn_cast<ObjCContainerDecl>(to)) {1408 to_container_decl->setHasExternalLexicalStorage();1409 to_container_decl->setHasExternalVisibleStorage();1410 1411 if (log) {1412 if (ObjCInterfaceDecl *to_interface_decl =1413 llvm::dyn_cast<ObjCInterfaceDecl>(to_container_decl)) {1414 LLDB_LOG(1415 log,1416 " [ClangASTImporter] To is an ObjCInterfaceDecl - attributes "1417 "{0}{1}{2}",1418 (to_interface_decl->hasExternalLexicalStorage() ? " Lexical" : ""),1419 (to_interface_decl->hasExternalVisibleStorage() ? " Visible" : ""),1420 (to_interface_decl->hasDefinition() ? " HasDefinition" : ""));1421 } else {1422 LLDB_LOG(1423 log, " [ClangASTImporter] To is an {0}Decl - attributes {1}{2}",1424 ((Decl *)to_container_decl)->getDeclKindName(),1425 (to_container_decl->hasExternalLexicalStorage() ? " Lexical" : ""),1426 (to_container_decl->hasExternalVisibleStorage() ? " Visible" : ""));1427 }1428 }1429 }1430 1431 if (clang::CXXMethodDecl *to_method = dyn_cast<CXXMethodDecl>(to))1432 MaybeCompleteReturnType(m_main, to_method);1433}1434 1435clang::Decl *1436ClangASTImporter::ASTImporterDelegate::GetOriginalDecl(clang::Decl *To) {1437 return m_main.GetDeclOrigin(To).decl;1438}1439