diff options
Diffstat (limited to 'clang/lib/Serialization/ASTReaderDecl.cpp')
| -rw-r--r-- | clang/lib/Serialization/ASTReaderDecl.cpp | 35 |
1 files changed, 32 insertions, 3 deletions
diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp b/clang/lib/Serialization/ASTReaderDecl.cpp index 2fb882c1bec..e0304d22fe5 100644 --- a/clang/lib/Serialization/ASTReaderDecl.cpp +++ b/clang/lib/Serialization/ASTReaderDecl.cpp @@ -3626,12 +3626,37 @@ Decl *ASTReader::ReadDeclRecord(DeclID ID) { // AST consumer might need to know about, queue it. // We don't pass it to the consumer immediately because we may be in recursive // loading, and some declarations may still be initializing. - if (isConsumerInterestedIn(Context, D, Reader.hasPendingBody())) - InterestingDecls.push_back(D); + PotentiallyInterestingDecls.push_back( + InterestingDecl(D, Reader.hasPendingBody())); return D; } +void ASTReader::PassInterestingDeclsToConsumer() { + assert(Consumer); + + if (PassingDeclsToConsumer) + return; + + // Guard variable to avoid recursively redoing the process of passing + // decls to consumer. + SaveAndRestore<bool> GuardPassingDeclsToConsumer(PassingDeclsToConsumer, + true); + + // Ensure that we've loaded all potentially-interesting declarations + // that need to be eagerly loaded. + for (auto ID : EagerlyDeserializedDecls) + GetDecl(ID); + EagerlyDeserializedDecls.clear(); + + while (!PotentiallyInterestingDecls.empty()) { + InterestingDecl D = PotentiallyInterestingDecls.front(); + PotentiallyInterestingDecls.pop_front(); + if (isConsumerInterestedIn(Context, D.getDecl(), D.hasPendingBody())) + PassInterestingDeclToConsumer(D.getDecl()); + } +} + void ASTReader::loadDeclUpdateRecords(serialization::DeclID ID, Decl *D) { // The declaration may have been modified by files later in the chain. // If this is the case, read the record containing the updates from each file @@ -3642,6 +3667,9 @@ void ASTReader::loadDeclUpdateRecords(serialization::DeclID ID, Decl *D) { auto UpdateOffsets = std::move(UpdI->second); DeclUpdateOffsets.erase(UpdI); + // FIXME: This call to isConsumerInterestedIn is not safe because + // we could be deserializing declarations at the moment. We should + // delay calling this in the same way as done in D30793. bool WasInteresting = isConsumerInterestedIn(Context, D, false); for (auto &FileAndOffset : UpdateOffsets) { ModuleFile *F = FileAndOffset.first; @@ -3663,7 +3691,8 @@ void ASTReader::loadDeclUpdateRecords(serialization::DeclID ID, Decl *D) { // we need to hand it off to the consumer. if (!WasInteresting && isConsumerInterestedIn(Context, D, Reader.hasPendingBody())) { - InterestingDecls.push_back(D); + PotentiallyInterestingDecls.push_back( + InterestingDecl(D, Reader.hasPendingBody())); WasInteresting = true; } } |

