xref: /openbsd-src/gnu/llvm/lldb/source/Plugins/ExpressionParser/Clang/ASTUtils.h (revision f6aab3d83b51b91c24247ad2c2573574de475a82)
1061da546Spatrick //===-- ASTUtils.h ----------------------------------------------*- C++ -*-===//
2061da546Spatrick //
3061da546Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4061da546Spatrick // See https://llvm.org/LICENSE.txt for license information.
5061da546Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6061da546Spatrick //
7061da546Spatrick //===----------------------------------------------------------------------===//
8061da546Spatrick 
9dda28197Spatrick #ifndef LLDB_SOURCE_PLUGINS_EXPRESSIONPARSER_CLANG_ASTUTILS_H
10dda28197Spatrick #define LLDB_SOURCE_PLUGINS_EXPRESSIONPARSER_CLANG_ASTUTILS_H
11061da546Spatrick 
12dda28197Spatrick #include "clang/Basic/Module.h"
13061da546Spatrick #include "clang/Sema/Lookup.h"
14061da546Spatrick #include "clang/Sema/MultiplexExternalSemaSource.h"
15061da546Spatrick #include "clang/Sema/Sema.h"
16061da546Spatrick #include "clang/Sema/SemaConsumer.h"
17*f6aab3d8Srobert #include <optional>
18061da546Spatrick 
19061da546Spatrick namespace lldb_private {
20061da546Spatrick 
21061da546Spatrick /// Wraps an ExternalASTSource into an ExternalSemaSource. Doesn't take
22061da546Spatrick /// ownership of the provided source.
23061da546Spatrick class ExternalASTSourceWrapper : public clang::ExternalSemaSource {
24061da546Spatrick   ExternalASTSource *m_Source;
25061da546Spatrick 
26061da546Spatrick public:
ExternalASTSourceWrapper(ExternalASTSource * Source)27061da546Spatrick   ExternalASTSourceWrapper(ExternalASTSource *Source) : m_Source(Source) {
28061da546Spatrick     assert(m_Source && "Can't wrap nullptr ExternalASTSource");
29061da546Spatrick   }
30061da546Spatrick 
31061da546Spatrick   ~ExternalASTSourceWrapper() override;
32061da546Spatrick 
GetExternalDecl(uint32_t ID)33061da546Spatrick   clang::Decl *GetExternalDecl(uint32_t ID) override {
34061da546Spatrick     return m_Source->GetExternalDecl(ID);
35061da546Spatrick   }
36061da546Spatrick 
GetExternalSelector(uint32_t ID)37061da546Spatrick   clang::Selector GetExternalSelector(uint32_t ID) override {
38061da546Spatrick     return m_Source->GetExternalSelector(ID);
39061da546Spatrick   }
40061da546Spatrick 
GetNumExternalSelectors()41061da546Spatrick   uint32_t GetNumExternalSelectors() override {
42061da546Spatrick     return m_Source->GetNumExternalSelectors();
43061da546Spatrick   }
44061da546Spatrick 
GetExternalDeclStmt(uint64_t Offset)45061da546Spatrick   clang::Stmt *GetExternalDeclStmt(uint64_t Offset) override {
46061da546Spatrick     return m_Source->GetExternalDeclStmt(Offset);
47061da546Spatrick   }
48061da546Spatrick 
49061da546Spatrick   clang::CXXCtorInitializer **
GetExternalCXXCtorInitializers(uint64_t Offset)50061da546Spatrick   GetExternalCXXCtorInitializers(uint64_t Offset) override {
51061da546Spatrick     return m_Source->GetExternalCXXCtorInitializers(Offset);
52061da546Spatrick   }
53061da546Spatrick 
54061da546Spatrick   clang::CXXBaseSpecifier *
GetExternalCXXBaseSpecifiers(uint64_t Offset)55061da546Spatrick   GetExternalCXXBaseSpecifiers(uint64_t Offset) override {
56061da546Spatrick     return m_Source->GetExternalCXXBaseSpecifiers(Offset);
57061da546Spatrick   }
58061da546Spatrick 
updateOutOfDateIdentifier(clang::IdentifierInfo & II)59061da546Spatrick   void updateOutOfDateIdentifier(clang::IdentifierInfo &II) override {
60061da546Spatrick     m_Source->updateOutOfDateIdentifier(II);
61061da546Spatrick   }
62061da546Spatrick 
FindExternalVisibleDeclsByName(const clang::DeclContext * DC,clang::DeclarationName Name)63061da546Spatrick   bool FindExternalVisibleDeclsByName(const clang::DeclContext *DC,
64061da546Spatrick                                       clang::DeclarationName Name) override {
65061da546Spatrick     return m_Source->FindExternalVisibleDeclsByName(DC, Name);
66061da546Spatrick   }
67061da546Spatrick 
completeVisibleDeclsMap(const clang::DeclContext * DC)68061da546Spatrick   void completeVisibleDeclsMap(const clang::DeclContext *DC) override {
69061da546Spatrick     m_Source->completeVisibleDeclsMap(DC);
70061da546Spatrick   }
71061da546Spatrick 
getModule(unsigned ID)72061da546Spatrick   clang::Module *getModule(unsigned ID) override {
73061da546Spatrick     return m_Source->getModule(ID);
74061da546Spatrick   }
75061da546Spatrick 
76*f6aab3d8Srobert   std::optional<clang::ASTSourceDescriptor>
getSourceDescriptor(unsigned ID)77061da546Spatrick   getSourceDescriptor(unsigned ID) override {
78061da546Spatrick     return m_Source->getSourceDescriptor(ID);
79061da546Spatrick   }
80061da546Spatrick 
hasExternalDefinitions(const clang::Decl * D)81061da546Spatrick   ExtKind hasExternalDefinitions(const clang::Decl *D) override {
82061da546Spatrick     return m_Source->hasExternalDefinitions(D);
83061da546Spatrick   }
84061da546Spatrick 
FindExternalLexicalDecls(const clang::DeclContext * DC,llvm::function_ref<bool (clang::Decl::Kind)> IsKindWeWant,llvm::SmallVectorImpl<clang::Decl * > & Result)85061da546Spatrick   void FindExternalLexicalDecls(
86061da546Spatrick       const clang::DeclContext *DC,
87061da546Spatrick       llvm::function_ref<bool(clang::Decl::Kind)> IsKindWeWant,
88061da546Spatrick       llvm::SmallVectorImpl<clang::Decl *> &Result) override {
89061da546Spatrick     m_Source->FindExternalLexicalDecls(DC, IsKindWeWant, Result);
90061da546Spatrick   }
91061da546Spatrick 
92061da546Spatrick   void
FindFileRegionDecls(clang::FileID File,unsigned Offset,unsigned Length,llvm::SmallVectorImpl<clang::Decl * > & Decls)93061da546Spatrick   FindFileRegionDecls(clang::FileID File, unsigned Offset, unsigned Length,
94061da546Spatrick                       llvm::SmallVectorImpl<clang::Decl *> &Decls) override {
95061da546Spatrick     m_Source->FindFileRegionDecls(File, Offset, Length, Decls);
96061da546Spatrick   }
97061da546Spatrick 
CompleteRedeclChain(const clang::Decl * D)98061da546Spatrick   void CompleteRedeclChain(const clang::Decl *D) override {
99061da546Spatrick     m_Source->CompleteRedeclChain(D);
100061da546Spatrick   }
101061da546Spatrick 
CompleteType(clang::TagDecl * Tag)102061da546Spatrick   void CompleteType(clang::TagDecl *Tag) override {
103061da546Spatrick     m_Source->CompleteType(Tag);
104061da546Spatrick   }
105061da546Spatrick 
CompleteType(clang::ObjCInterfaceDecl * Class)106061da546Spatrick   void CompleteType(clang::ObjCInterfaceDecl *Class) override {
107061da546Spatrick     m_Source->CompleteType(Class);
108061da546Spatrick   }
109061da546Spatrick 
ReadComments()110061da546Spatrick   void ReadComments() override { m_Source->ReadComments(); }
111061da546Spatrick 
StartedDeserializing()112061da546Spatrick   void StartedDeserializing() override { m_Source->StartedDeserializing(); }
113061da546Spatrick 
FinishedDeserializing()114061da546Spatrick   void FinishedDeserializing() override { m_Source->FinishedDeserializing(); }
115061da546Spatrick 
StartTranslationUnit(clang::ASTConsumer * Consumer)116061da546Spatrick   void StartTranslationUnit(clang::ASTConsumer *Consumer) override {
117061da546Spatrick     m_Source->StartTranslationUnit(Consumer);
118061da546Spatrick   }
119061da546Spatrick 
120061da546Spatrick   void PrintStats() override;
121061da546Spatrick 
layoutRecordType(const clang::RecordDecl * Record,uint64_t & Size,uint64_t & Alignment,llvm::DenseMap<const clang::FieldDecl *,uint64_t> & FieldOffsets,llvm::DenseMap<const clang::CXXRecordDecl *,clang::CharUnits> & BaseOffsets,llvm::DenseMap<const clang::CXXRecordDecl *,clang::CharUnits> & VirtualBaseOffsets)122061da546Spatrick   bool layoutRecordType(
123061da546Spatrick       const clang::RecordDecl *Record, uint64_t &Size, uint64_t &Alignment,
124061da546Spatrick       llvm::DenseMap<const clang::FieldDecl *, uint64_t> &FieldOffsets,
125061da546Spatrick       llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
126061da546Spatrick           &BaseOffsets,
127061da546Spatrick       llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
128061da546Spatrick           &VirtualBaseOffsets) override {
129061da546Spatrick     return m_Source->layoutRecordType(Record, Size, Alignment, FieldOffsets,
130061da546Spatrick                                       BaseOffsets, VirtualBaseOffsets);
131061da546Spatrick   }
132061da546Spatrick };
133061da546Spatrick 
134061da546Spatrick /// Wraps an ASTConsumer into an SemaConsumer. Doesn't take ownership of the
135061da546Spatrick /// provided consumer. If the provided ASTConsumer is also a SemaConsumer,
136061da546Spatrick /// the wrapper will also forward SemaConsumer functions.
137061da546Spatrick class ASTConsumerForwarder : public clang::SemaConsumer {
138061da546Spatrick   clang::ASTConsumer *m_c;
139061da546Spatrick   clang::SemaConsumer *m_sc;
140061da546Spatrick 
141061da546Spatrick public:
ASTConsumerForwarder(clang::ASTConsumer * c)142061da546Spatrick   ASTConsumerForwarder(clang::ASTConsumer *c) : m_c(c) {
143061da546Spatrick     m_sc = llvm::dyn_cast<clang::SemaConsumer>(m_c);
144061da546Spatrick   }
145061da546Spatrick 
146061da546Spatrick   ~ASTConsumerForwarder() override;
147061da546Spatrick 
Initialize(clang::ASTContext & Context)148061da546Spatrick   void Initialize(clang::ASTContext &Context) override {
149061da546Spatrick     m_c->Initialize(Context);
150061da546Spatrick   }
151061da546Spatrick 
HandleTopLevelDecl(clang::DeclGroupRef D)152061da546Spatrick   bool HandleTopLevelDecl(clang::DeclGroupRef D) override {
153061da546Spatrick     return m_c->HandleTopLevelDecl(D);
154061da546Spatrick   }
155061da546Spatrick 
HandleInlineFunctionDefinition(clang::FunctionDecl * D)156061da546Spatrick   void HandleInlineFunctionDefinition(clang::FunctionDecl *D) override {
157061da546Spatrick     m_c->HandleInlineFunctionDefinition(D);
158061da546Spatrick   }
159061da546Spatrick 
HandleInterestingDecl(clang::DeclGroupRef D)160061da546Spatrick   void HandleInterestingDecl(clang::DeclGroupRef D) override {
161061da546Spatrick     m_c->HandleInterestingDecl(D);
162061da546Spatrick   }
163061da546Spatrick 
HandleTranslationUnit(clang::ASTContext & Ctx)164061da546Spatrick   void HandleTranslationUnit(clang::ASTContext &Ctx) override {
165061da546Spatrick     m_c->HandleTranslationUnit(Ctx);
166061da546Spatrick   }
167061da546Spatrick 
HandleTagDeclDefinition(clang::TagDecl * D)168061da546Spatrick   void HandleTagDeclDefinition(clang::TagDecl *D) override {
169061da546Spatrick     m_c->HandleTagDeclDefinition(D);
170061da546Spatrick   }
171061da546Spatrick 
HandleTagDeclRequiredDefinition(const clang::TagDecl * D)172061da546Spatrick   void HandleTagDeclRequiredDefinition(const clang::TagDecl *D) override {
173061da546Spatrick     m_c->HandleTagDeclRequiredDefinition(D);
174061da546Spatrick   }
175061da546Spatrick 
HandleCXXImplicitFunctionInstantiation(clang::FunctionDecl * D)176061da546Spatrick   void HandleCXXImplicitFunctionInstantiation(clang::FunctionDecl *D) override {
177061da546Spatrick     m_c->HandleCXXImplicitFunctionInstantiation(D);
178061da546Spatrick   }
179061da546Spatrick 
HandleTopLevelDeclInObjCContainer(clang::DeclGroupRef D)180061da546Spatrick   void HandleTopLevelDeclInObjCContainer(clang::DeclGroupRef D) override {
181061da546Spatrick     m_c->HandleTopLevelDeclInObjCContainer(D);
182061da546Spatrick   }
183061da546Spatrick 
HandleImplicitImportDecl(clang::ImportDecl * D)184061da546Spatrick   void HandleImplicitImportDecl(clang::ImportDecl *D) override {
185061da546Spatrick     m_c->HandleImplicitImportDecl(D);
186061da546Spatrick   }
187061da546Spatrick 
CompleteTentativeDefinition(clang::VarDecl * D)188061da546Spatrick   void CompleteTentativeDefinition(clang::VarDecl *D) override {
189061da546Spatrick     m_c->CompleteTentativeDefinition(D);
190061da546Spatrick   }
191061da546Spatrick 
AssignInheritanceModel(clang::CXXRecordDecl * RD)192061da546Spatrick   void AssignInheritanceModel(clang::CXXRecordDecl *RD) override {
193061da546Spatrick     m_c->AssignInheritanceModel(RD);
194061da546Spatrick   }
195061da546Spatrick 
HandleCXXStaticMemberVarInstantiation(clang::VarDecl * D)196061da546Spatrick   void HandleCXXStaticMemberVarInstantiation(clang::VarDecl *D) override {
197061da546Spatrick     m_c->HandleCXXStaticMemberVarInstantiation(D);
198061da546Spatrick   }
199061da546Spatrick 
HandleVTable(clang::CXXRecordDecl * RD)200061da546Spatrick   void HandleVTable(clang::CXXRecordDecl *RD) override {
201061da546Spatrick     m_c->HandleVTable(RD);
202061da546Spatrick   }
203061da546Spatrick 
GetASTMutationListener()204061da546Spatrick   clang::ASTMutationListener *GetASTMutationListener() override {
205061da546Spatrick     return m_c->GetASTMutationListener();
206061da546Spatrick   }
207061da546Spatrick 
GetASTDeserializationListener()208061da546Spatrick   clang::ASTDeserializationListener *GetASTDeserializationListener() override {
209061da546Spatrick     return m_c->GetASTDeserializationListener();
210061da546Spatrick   }
211061da546Spatrick 
212061da546Spatrick   void PrintStats() override;
213061da546Spatrick 
InitializeSema(clang::Sema & S)214061da546Spatrick   void InitializeSema(clang::Sema &S) override {
215061da546Spatrick     if (m_sc)
216061da546Spatrick       m_sc->InitializeSema(S);
217061da546Spatrick   }
218061da546Spatrick 
219061da546Spatrick   /// Inform the semantic consumer that Sema is no longer available.
ForgetSema()220061da546Spatrick   void ForgetSema() override {
221061da546Spatrick     if (m_sc)
222061da546Spatrick       m_sc->ForgetSema();
223061da546Spatrick   }
224061da546Spatrick 
shouldSkipFunctionBody(clang::Decl * D)225061da546Spatrick   bool shouldSkipFunctionBody(clang::Decl *D) override {
226061da546Spatrick     return m_c->shouldSkipFunctionBody(D);
227061da546Spatrick   }
228061da546Spatrick };
229061da546Spatrick 
230061da546Spatrick /// A ExternalSemaSource multiplexer that prioritizes its sources.
231061da546Spatrick ///
232061da546Spatrick /// This ExternalSemaSource will forward all requests to its attached sources.
233061da546Spatrick /// However, unlike a normal multiplexer it will not forward a request to all
234061da546Spatrick /// sources, but instead give priority to certain sources. If a source with a
235061da546Spatrick /// higher priority can fulfill a request, all sources with a lower priority
236061da546Spatrick /// will not receive the request.
237061da546Spatrick ///
238061da546Spatrick /// This class is mostly use to multiplex between sources of different
239061da546Spatrick /// 'quality', e.g. a C++ modules and debug information. The C++ module will
240061da546Spatrick /// provide more accurate replies to the requests, but might not be able to
241061da546Spatrick /// answer all requests. The debug information will be used as a fallback then
242061da546Spatrick /// to provide information that is not in the C++ module.
243061da546Spatrick class SemaSourceWithPriorities : public clang::ExternalSemaSource {
244061da546Spatrick 
245061da546Spatrick private:
246061da546Spatrick   /// The sources ordered in decreasing priority.
247061da546Spatrick   llvm::SmallVector<clang::ExternalSemaSource *, 2> Sources;
248061da546Spatrick 
249061da546Spatrick public:
250061da546Spatrick   /// Construct a SemaSourceWithPriorities with a 'high quality' source that
251061da546Spatrick   /// has the higher priority and a 'low quality' source that will be used
252061da546Spatrick   /// as a fallback.
SemaSourceWithPriorities(clang::ExternalSemaSource & high_quality_source,clang::ExternalSemaSource & low_quality_source)253061da546Spatrick   SemaSourceWithPriorities(clang::ExternalSemaSource &high_quality_source,
254061da546Spatrick                            clang::ExternalSemaSource &low_quality_source) {
255061da546Spatrick     Sources.push_back(&high_quality_source);
256061da546Spatrick     Sources.push_back(&low_quality_source);
257061da546Spatrick   }
258061da546Spatrick 
259061da546Spatrick   ~SemaSourceWithPriorities() override;
260061da546Spatrick 
addSource(clang::ExternalSemaSource & source)261061da546Spatrick   void addSource(clang::ExternalSemaSource &source) {
262061da546Spatrick     Sources.push_back(&source);
263061da546Spatrick   }
264061da546Spatrick 
265061da546Spatrick   //===--------------------------------------------------------------------===//
266061da546Spatrick   // ExternalASTSource.
267061da546Spatrick   //===--------------------------------------------------------------------===//
268061da546Spatrick 
GetExternalDecl(uint32_t ID)269061da546Spatrick   clang::Decl *GetExternalDecl(uint32_t ID) override {
270061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
271061da546Spatrick       if (clang::Decl *Result = Sources[i]->GetExternalDecl(ID))
272061da546Spatrick         return Result;
273061da546Spatrick     return nullptr;
274061da546Spatrick   }
275061da546Spatrick 
CompleteRedeclChain(const clang::Decl * D)276061da546Spatrick   void CompleteRedeclChain(const clang::Decl *D) override {
277061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
278061da546Spatrick       Sources[i]->CompleteRedeclChain(D);
279061da546Spatrick   }
280061da546Spatrick 
GetExternalSelector(uint32_t ID)281061da546Spatrick   clang::Selector GetExternalSelector(uint32_t ID) override {
282061da546Spatrick     clang::Selector Sel;
283061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i) {
284061da546Spatrick       Sel = Sources[i]->GetExternalSelector(ID);
285061da546Spatrick       if (!Sel.isNull())
286061da546Spatrick         return Sel;
287061da546Spatrick     }
288061da546Spatrick     return Sel;
289061da546Spatrick   }
290061da546Spatrick 
GetNumExternalSelectors()291061da546Spatrick   uint32_t GetNumExternalSelectors() override {
292061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
293061da546Spatrick       if (uint32_t total = Sources[i]->GetNumExternalSelectors())
294061da546Spatrick         return total;
295061da546Spatrick     return 0;
296061da546Spatrick   }
297061da546Spatrick 
GetExternalDeclStmt(uint64_t Offset)298061da546Spatrick   clang::Stmt *GetExternalDeclStmt(uint64_t Offset) override {
299061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
300061da546Spatrick       if (clang::Stmt *Result = Sources[i]->GetExternalDeclStmt(Offset))
301061da546Spatrick         return Result;
302061da546Spatrick     return nullptr;
303061da546Spatrick   }
304061da546Spatrick 
305061da546Spatrick   clang::CXXBaseSpecifier *
GetExternalCXXBaseSpecifiers(uint64_t Offset)306061da546Spatrick   GetExternalCXXBaseSpecifiers(uint64_t Offset) override {
307061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
308061da546Spatrick       if (clang::CXXBaseSpecifier *R =
309061da546Spatrick               Sources[i]->GetExternalCXXBaseSpecifiers(Offset))
310061da546Spatrick         return R;
311061da546Spatrick     return nullptr;
312061da546Spatrick   }
313061da546Spatrick 
314061da546Spatrick   clang::CXXCtorInitializer **
GetExternalCXXCtorInitializers(uint64_t Offset)315061da546Spatrick   GetExternalCXXCtorInitializers(uint64_t Offset) override {
316061da546Spatrick     for (auto *S : Sources)
317061da546Spatrick       if (auto *R = S->GetExternalCXXCtorInitializers(Offset))
318061da546Spatrick         return R;
319061da546Spatrick     return nullptr;
320061da546Spatrick   }
321061da546Spatrick 
hasExternalDefinitions(const clang::Decl * D)322061da546Spatrick   ExtKind hasExternalDefinitions(const clang::Decl *D) override {
323061da546Spatrick     for (const auto &S : Sources)
324061da546Spatrick       if (auto EK = S->hasExternalDefinitions(D))
325061da546Spatrick         if (EK != EK_ReplyHazy)
326061da546Spatrick           return EK;
327061da546Spatrick     return EK_ReplyHazy;
328061da546Spatrick   }
329061da546Spatrick 
FindExternalVisibleDeclsByName(const clang::DeclContext * DC,clang::DeclarationName Name)330061da546Spatrick   bool FindExternalVisibleDeclsByName(const clang::DeclContext *DC,
331061da546Spatrick                                       clang::DeclarationName Name) override {
332061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
333061da546Spatrick       if (Sources[i]->FindExternalVisibleDeclsByName(DC, Name))
334061da546Spatrick         return true;
335061da546Spatrick     return false;
336061da546Spatrick   }
337061da546Spatrick 
completeVisibleDeclsMap(const clang::DeclContext * DC)338061da546Spatrick   void completeVisibleDeclsMap(const clang::DeclContext *DC) override {
339061da546Spatrick     // FIXME: Only one source should be able to complete the decls map.
340061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
341061da546Spatrick       Sources[i]->completeVisibleDeclsMap(DC);
342061da546Spatrick   }
343061da546Spatrick 
FindExternalLexicalDecls(const clang::DeclContext * DC,llvm::function_ref<bool (clang::Decl::Kind)> IsKindWeWant,llvm::SmallVectorImpl<clang::Decl * > & Result)344061da546Spatrick   void FindExternalLexicalDecls(
345061da546Spatrick       const clang::DeclContext *DC,
346061da546Spatrick       llvm::function_ref<bool(clang::Decl::Kind)> IsKindWeWant,
347061da546Spatrick       llvm::SmallVectorImpl<clang::Decl *> &Result) override {
348061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i) {
349061da546Spatrick       Sources[i]->FindExternalLexicalDecls(DC, IsKindWeWant, Result);
350061da546Spatrick       if (!Result.empty())
351061da546Spatrick         return;
352061da546Spatrick     }
353061da546Spatrick   }
354061da546Spatrick 
355061da546Spatrick   void
FindFileRegionDecls(clang::FileID File,unsigned Offset,unsigned Length,llvm::SmallVectorImpl<clang::Decl * > & Decls)356061da546Spatrick   FindFileRegionDecls(clang::FileID File, unsigned Offset, unsigned Length,
357061da546Spatrick                       llvm::SmallVectorImpl<clang::Decl *> &Decls) override {
358061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
359061da546Spatrick       Sources[i]->FindFileRegionDecls(File, Offset, Length, Decls);
360061da546Spatrick   }
361061da546Spatrick 
CompleteType(clang::TagDecl * Tag)362061da546Spatrick   void CompleteType(clang::TagDecl *Tag) override {
363be691f3bSpatrick     for (clang::ExternalSemaSource *S : Sources) {
364be691f3bSpatrick       S->CompleteType(Tag);
365be691f3bSpatrick       // Stop after the first source completed the type.
366061da546Spatrick       if (Tag->isCompleteDefinition())
367061da546Spatrick         break;
368061da546Spatrick     }
369061da546Spatrick   }
370061da546Spatrick 
CompleteType(clang::ObjCInterfaceDecl * Class)371061da546Spatrick   void CompleteType(clang::ObjCInterfaceDecl *Class) override {
372061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
373061da546Spatrick       Sources[i]->CompleteType(Class);
374061da546Spatrick   }
375061da546Spatrick 
ReadComments()376061da546Spatrick   void ReadComments() override {
377061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
378061da546Spatrick       Sources[i]->ReadComments();
379061da546Spatrick   }
380061da546Spatrick 
StartedDeserializing()381061da546Spatrick   void StartedDeserializing() override {
382061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
383061da546Spatrick       Sources[i]->StartedDeserializing();
384061da546Spatrick   }
385061da546Spatrick 
FinishedDeserializing()386061da546Spatrick   void FinishedDeserializing() override {
387061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
388061da546Spatrick       Sources[i]->FinishedDeserializing();
389061da546Spatrick   }
390061da546Spatrick 
StartTranslationUnit(clang::ASTConsumer * Consumer)391061da546Spatrick   void StartTranslationUnit(clang::ASTConsumer *Consumer) override {
392061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
393061da546Spatrick       Sources[i]->StartTranslationUnit(Consumer);
394061da546Spatrick   }
395061da546Spatrick 
396061da546Spatrick   void PrintStats() override;
397061da546Spatrick 
getModule(unsigned ID)398061da546Spatrick   clang::Module *getModule(unsigned ID) override {
399061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
400061da546Spatrick       if (auto M = Sources[i]->getModule(ID))
401061da546Spatrick         return M;
402061da546Spatrick     return nullptr;
403061da546Spatrick   }
404061da546Spatrick 
layoutRecordType(const clang::RecordDecl * Record,uint64_t & Size,uint64_t & Alignment,llvm::DenseMap<const clang::FieldDecl *,uint64_t> & FieldOffsets,llvm::DenseMap<const clang::CXXRecordDecl *,clang::CharUnits> & BaseOffsets,llvm::DenseMap<const clang::CXXRecordDecl *,clang::CharUnits> & VirtualBaseOffsets)405061da546Spatrick   bool layoutRecordType(
406061da546Spatrick       const clang::RecordDecl *Record, uint64_t &Size, uint64_t &Alignment,
407061da546Spatrick       llvm::DenseMap<const clang::FieldDecl *, uint64_t> &FieldOffsets,
408061da546Spatrick       llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
409061da546Spatrick           &BaseOffsets,
410061da546Spatrick       llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
411061da546Spatrick           &VirtualBaseOffsets) override {
412061da546Spatrick     for (size_t i = 0; i < Sources.size(); ++i)
413061da546Spatrick       if (Sources[i]->layoutRecordType(Record, Size, Alignment, FieldOffsets,
414061da546Spatrick                                        BaseOffsets, VirtualBaseOffsets))
415061da546Spatrick         return true;
416061da546Spatrick     return false;
417061da546Spatrick   }
418061da546Spatrick 
getMemoryBufferSizes(MemoryBufferSizes & sizes)419061da546Spatrick   void getMemoryBufferSizes(MemoryBufferSizes &sizes) const override {
420061da546Spatrick     for (auto &Source : Sources)
421061da546Spatrick       Source->getMemoryBufferSizes(sizes);
422061da546Spatrick   }
423061da546Spatrick 
424061da546Spatrick   //===--------------------------------------------------------------------===//
425061da546Spatrick   // ExternalSemaSource.
426061da546Spatrick   //===--------------------------------------------------------------------===//
427061da546Spatrick 
InitializeSema(clang::Sema & S)428061da546Spatrick   void InitializeSema(clang::Sema &S) override {
429061da546Spatrick     for (auto &Source : Sources)
430061da546Spatrick       Source->InitializeSema(S);
431061da546Spatrick   }
432061da546Spatrick 
ForgetSema()433061da546Spatrick   void ForgetSema() override {
434061da546Spatrick     for (auto &Source : Sources)
435061da546Spatrick       Source->ForgetSema();
436061da546Spatrick   }
437061da546Spatrick 
ReadMethodPool(clang::Selector Sel)438061da546Spatrick   void ReadMethodPool(clang::Selector Sel) override {
439061da546Spatrick     for (auto &Source : Sources)
440061da546Spatrick       Source->ReadMethodPool(Sel);
441061da546Spatrick   }
442061da546Spatrick 
updateOutOfDateSelector(clang::Selector Sel)443061da546Spatrick   void updateOutOfDateSelector(clang::Selector Sel) override {
444061da546Spatrick     for (auto &Source : Sources)
445061da546Spatrick       Source->updateOutOfDateSelector(Sel);
446061da546Spatrick   }
447061da546Spatrick 
ReadKnownNamespaces(llvm::SmallVectorImpl<clang::NamespaceDecl * > & Namespaces)448061da546Spatrick   void ReadKnownNamespaces(
449061da546Spatrick       llvm::SmallVectorImpl<clang::NamespaceDecl *> &Namespaces) override {
450061da546Spatrick     for (auto &Source : Sources)
451061da546Spatrick       Source->ReadKnownNamespaces(Namespaces);
452061da546Spatrick   }
453061da546Spatrick 
ReadUndefinedButUsed(llvm::MapVector<clang::NamedDecl *,clang::SourceLocation> & Undefined)454061da546Spatrick   void ReadUndefinedButUsed(
455061da546Spatrick       llvm::MapVector<clang::NamedDecl *, clang::SourceLocation> &Undefined)
456061da546Spatrick       override {
457061da546Spatrick     for (auto &Source : Sources)
458061da546Spatrick       Source->ReadUndefinedButUsed(Undefined);
459061da546Spatrick   }
460061da546Spatrick 
ReadMismatchingDeleteExpressions(llvm::MapVector<clang::FieldDecl *,llvm::SmallVector<std::pair<clang::SourceLocation,bool>,4>> & Exprs)461061da546Spatrick   void ReadMismatchingDeleteExpressions(
462061da546Spatrick       llvm::MapVector<clang::FieldDecl *,
463061da546Spatrick                       llvm::SmallVector<std::pair<clang::SourceLocation, bool>,
464061da546Spatrick                                         4>> &Exprs) override {
465061da546Spatrick     for (auto &Source : Sources)
466061da546Spatrick       Source->ReadMismatchingDeleteExpressions(Exprs);
467061da546Spatrick   }
468061da546Spatrick 
LookupUnqualified(clang::LookupResult & R,clang::Scope * S)469061da546Spatrick   bool LookupUnqualified(clang::LookupResult &R, clang::Scope *S) override {
470061da546Spatrick     for (auto &Source : Sources) {
471061da546Spatrick       Source->LookupUnqualified(R, S);
472061da546Spatrick       if (!R.empty())
473061da546Spatrick         break;
474061da546Spatrick     }
475061da546Spatrick 
476061da546Spatrick     return !R.empty();
477061da546Spatrick   }
478061da546Spatrick 
ReadTentativeDefinitions(llvm::SmallVectorImpl<clang::VarDecl * > & Defs)479061da546Spatrick   void ReadTentativeDefinitions(
480061da546Spatrick       llvm::SmallVectorImpl<clang::VarDecl *> &Defs) override {
481061da546Spatrick     for (auto &Source : Sources)
482061da546Spatrick       Source->ReadTentativeDefinitions(Defs);
483061da546Spatrick   }
484061da546Spatrick 
ReadUnusedFileScopedDecls(llvm::SmallVectorImpl<const clang::DeclaratorDecl * > & Decls)485061da546Spatrick   void ReadUnusedFileScopedDecls(
486061da546Spatrick       llvm::SmallVectorImpl<const clang::DeclaratorDecl *> &Decls) override {
487061da546Spatrick     for (auto &Source : Sources)
488061da546Spatrick       Source->ReadUnusedFileScopedDecls(Decls);
489061da546Spatrick   }
490061da546Spatrick 
ReadDelegatingConstructors(llvm::SmallVectorImpl<clang::CXXConstructorDecl * > & Decls)491061da546Spatrick   void ReadDelegatingConstructors(
492061da546Spatrick       llvm::SmallVectorImpl<clang::CXXConstructorDecl *> &Decls) override {
493061da546Spatrick     for (auto &Source : Sources)
494061da546Spatrick       Source->ReadDelegatingConstructors(Decls);
495061da546Spatrick   }
496061da546Spatrick 
ReadExtVectorDecls(llvm::SmallVectorImpl<clang::TypedefNameDecl * > & Decls)497061da546Spatrick   void ReadExtVectorDecls(
498061da546Spatrick       llvm::SmallVectorImpl<clang::TypedefNameDecl *> &Decls) override {
499061da546Spatrick     for (auto &Source : Sources)
500061da546Spatrick       Source->ReadExtVectorDecls(Decls);
501061da546Spatrick   }
502061da546Spatrick 
ReadUnusedLocalTypedefNameCandidates(llvm::SmallSetVector<const clang::TypedefNameDecl *,4> & Decls)503061da546Spatrick   void ReadUnusedLocalTypedefNameCandidates(
504061da546Spatrick       llvm::SmallSetVector<const clang::TypedefNameDecl *, 4> &Decls) override {
505061da546Spatrick     for (auto &Source : Sources)
506061da546Spatrick       Source->ReadUnusedLocalTypedefNameCandidates(Decls);
507061da546Spatrick   }
508061da546Spatrick 
ReadReferencedSelectors(llvm::SmallVectorImpl<std::pair<clang::Selector,clang::SourceLocation>> & Sels)509061da546Spatrick   void ReadReferencedSelectors(
510061da546Spatrick       llvm::SmallVectorImpl<std::pair<clang::Selector, clang::SourceLocation>>
511061da546Spatrick           &Sels) override {
512061da546Spatrick     for (auto &Source : Sources)
513061da546Spatrick       Source->ReadReferencedSelectors(Sels);
514061da546Spatrick   }
515061da546Spatrick 
ReadWeakUndeclaredIdentifiers(llvm::SmallVectorImpl<std::pair<clang::IdentifierInfo *,clang::WeakInfo>> & WI)516061da546Spatrick   void ReadWeakUndeclaredIdentifiers(
517061da546Spatrick       llvm::SmallVectorImpl<std::pair<clang::IdentifierInfo *, clang::WeakInfo>>
518061da546Spatrick           &WI) override {
519061da546Spatrick     for (auto &Source : Sources)
520061da546Spatrick       Source->ReadWeakUndeclaredIdentifiers(WI);
521061da546Spatrick   }
522061da546Spatrick 
ReadUsedVTables(llvm::SmallVectorImpl<clang::ExternalVTableUse> & VTables)523061da546Spatrick   void ReadUsedVTables(
524061da546Spatrick       llvm::SmallVectorImpl<clang::ExternalVTableUse> &VTables) override {
525061da546Spatrick     for (auto &Source : Sources)
526061da546Spatrick       Source->ReadUsedVTables(VTables);
527061da546Spatrick   }
528061da546Spatrick 
ReadPendingInstantiations(llvm::SmallVectorImpl<std::pair<clang::ValueDecl *,clang::SourceLocation>> & Pending)529061da546Spatrick   void ReadPendingInstantiations(
530061da546Spatrick       llvm::SmallVectorImpl<
531061da546Spatrick           std::pair<clang::ValueDecl *, clang::SourceLocation>> &Pending)
532061da546Spatrick       override {
533061da546Spatrick     for (auto &Source : Sources)
534061da546Spatrick       Source->ReadPendingInstantiations(Pending);
535061da546Spatrick   }
536061da546Spatrick 
ReadLateParsedTemplates(llvm::MapVector<const clang::FunctionDecl *,std::unique_ptr<clang::LateParsedTemplate>> & LPTMap)537061da546Spatrick   void ReadLateParsedTemplates(
538061da546Spatrick       llvm::MapVector<const clang::FunctionDecl *,
539061da546Spatrick                       std::unique_ptr<clang::LateParsedTemplate>> &LPTMap)
540061da546Spatrick       override {
541061da546Spatrick     for (auto &Source : Sources)
542061da546Spatrick       Source->ReadLateParsedTemplates(LPTMap);
543061da546Spatrick   }
544061da546Spatrick 
545061da546Spatrick   clang::TypoCorrection
CorrectTypo(const clang::DeclarationNameInfo & Typo,int LookupKind,clang::Scope * S,clang::CXXScopeSpec * SS,clang::CorrectionCandidateCallback & CCC,clang::DeclContext * MemberContext,bool EnteringContext,const clang::ObjCObjectPointerType * OPT)546061da546Spatrick   CorrectTypo(const clang::DeclarationNameInfo &Typo, int LookupKind,
547061da546Spatrick               clang::Scope *S, clang::CXXScopeSpec *SS,
548061da546Spatrick               clang::CorrectionCandidateCallback &CCC,
549061da546Spatrick               clang::DeclContext *MemberContext, bool EnteringContext,
550061da546Spatrick               const clang::ObjCObjectPointerType *OPT) override {
551061da546Spatrick     for (auto &Source : Sources) {
552061da546Spatrick       if (clang::TypoCorrection C =
553061da546Spatrick               Source->CorrectTypo(Typo, LookupKind, S, SS, CCC,
554061da546Spatrick                                       MemberContext, EnteringContext, OPT))
555061da546Spatrick         return C;
556061da546Spatrick     }
557061da546Spatrick     return clang::TypoCorrection();
558061da546Spatrick   }
559061da546Spatrick 
MaybeDiagnoseMissingCompleteType(clang::SourceLocation Loc,clang::QualType T)560061da546Spatrick   bool MaybeDiagnoseMissingCompleteType(clang::SourceLocation Loc,
561061da546Spatrick                                         clang::QualType T) override {
562061da546Spatrick     for (auto &Source : Sources) {
563061da546Spatrick       if (Source->MaybeDiagnoseMissingCompleteType(Loc, T))
564061da546Spatrick         return true;
565061da546Spatrick     }
566061da546Spatrick     return false;
567061da546Spatrick   }
568061da546Spatrick };
569061da546Spatrick 
570061da546Spatrick } // namespace lldb_private
571dda28197Spatrick #endif // LLDB_SOURCE_PLUGINS_EXPRESSIONPARSER_CLANG_ASTUTILS_H
572