Merge pull request #71739 from tshortli/module-serialization-remarks

Serialization: Skip invalid decls during module serialization
This commit is contained in:
Allan Shortlidge
2024-02-20 10:44:33 -08:00
committed by GitHub
9 changed files with 146 additions and 16 deletions

View File

@@ -18,6 +18,7 @@
#include "swift/AST/ASTVisitor.h"
#include "swift/AST/AutoDiff.h"
#include "swift/AST/DiagnosticsCommon.h"
#include "swift/AST/DiagnosticsSema.h"
#include "swift/AST/Expr.h"
#include "swift/AST/FileSystem.h"
#include "swift/AST/ForeignAsyncConvention.h"
@@ -3045,12 +3046,12 @@ class Serializer::DeclSerializer : public DeclVisitor<DeclSerializer> {
if (D->getResolvedMacro(const_cast<CustomAttr *>(theAttr)))
return;
auto typeID = S.addTypeRef(
D->getResolvedCustomAttrType(const_cast<CustomAttr *>(theAttr)));
if (!typeID && !S.allowCompilerErrors()) {
llvm::PrettyStackTraceString message("CustomAttr has no type");
abort();
}
auto attrType =
D->getResolvedCustomAttrType(const_cast<CustomAttr *>(theAttr));
if (S.skipTypeIfInvalid(attrType, theAttr->getTypeRepr()))
return;
auto typeID = S.addTypeRef(attrType);
CustomDeclAttrLayout::emitRecord(S.Out, S.ScratchRecord, abbrCode,
theAttr->isImplicit(),
typeID, theAttr->isArgUnsafe());
@@ -3656,27 +3657,37 @@ private:
}
case PatternKind::Named: {
auto named = cast<NamedPattern>(pattern);
auto ty = getPatternType();
if (S.skipTypeIfInvalid(ty, named->getLoc()))
break;
unsigned abbrCode = S.DeclTypeAbbrCodes[NamedPatternLayout::Code];
NamedPatternLayout::emitRecord(S.Out, S.ScratchRecord, abbrCode,
S.addDeclRef(named->getDecl()),
S.addTypeRef(getPatternType()));
S.addTypeRef(ty));
break;
}
case PatternKind::Any: {
auto ty = getPatternType();
if (S.skipTypeIfInvalid(ty, pattern->getLoc()))
break;
unsigned abbrCode = S.DeclTypeAbbrCodes[AnyPatternLayout::Code];
auto anyPattern = cast<AnyPattern>(pattern);
AnyPatternLayout::emitRecord(S.Out, S.ScratchRecord, abbrCode,
S.addTypeRef(getPatternType()),
S.addTypeRef(ty),
anyPattern->isAsyncLet());
break;
}
case PatternKind::Typed: {
auto typed = cast<TypedPattern>(pattern);
auto ty = getPatternType();
if (S.skipTypeIfInvalid(ty, typed->getTypeRepr()))
break;
unsigned abbrCode = S.DeclTypeAbbrCodes[TypedPatternLayout::Code];
TypedPatternLayout::emitRecord(S.Out, S.ScratchRecord, abbrCode,
S.addTypeRef(getPatternType()));
S.addTypeRef(ty));
writePattern(typed->getSubPattern());
break;
}
@@ -4996,13 +5007,8 @@ void Serializer::writeASTBlockEntity(const Decl *D) {
PrettyStackTraceDecl trace("serializing", D);
assert(DeclsToSerialize.hasRef(D));
if (D->isInvalid()) {
assert(allowCompilerErrors() &&
"cannot create a module with an invalid decl");
if (canSkipWhenInvalid(D))
return;
}
if (skipDeclIfInvalid(D))
return;
BitOffset initialOffset = Out.GetCurrentBitNo();
SWIFT_DEFER {
@@ -6780,6 +6786,11 @@ void Serializer::writeToStream(
S.writeInputBlock();
S.writeSIL(SILMod, options.SerializeAllSIL);
S.writeAST(DC);
if (S.hadError)
S.getASTContext().Diags.diagnose(SourceLoc(), diag::serialization_failed,
S.M);
if (!options.DisableCrossModuleIncrementalInfo && DepGraph) {
fine_grained_dependencies::writeFineGrainedDependencyGraph(
S.Out, *DepGraph, fine_grained_dependencies::Purpose::ForSwiftModule);
@@ -6793,6 +6804,48 @@ bool Serializer::allowCompilerErrors() const {
return getASTContext().LangOpts.AllowModuleWithCompilerErrors;
}
bool Serializer::skipDeclIfInvalid(const Decl *decl) {
if (!decl->isInvalid())
return false;
if (allowCompilerErrors())
return canSkipWhenInvalid(decl);
if (Options.EnableSerializationRemarks) {
getASTContext().Diags.diagnose(
decl->getLoc(), diag::serialization_skipped_invalid_decl, decl);
}
hadError = true;
return true;
}
bool Serializer::skipTypeIfInvalid(Type ty, TypeRepr *tyRepr) {
if ((ty && !ty->hasError()) || allowCompilerErrors())
return false;
if (Options.EnableSerializationRemarks) {
getASTContext().Diags.diagnose(
tyRepr->getLoc(), diag::serialization_skipped_invalid_type, tyRepr);
}
hadError = true;
return true;
}
bool Serializer::skipTypeIfInvalid(Type ty, SourceLoc loc) {
if ((ty && !ty->hasError()) || allowCompilerErrors())
return false;
if (Options.EnableSerializationRemarks) {
getASTContext().Diags.diagnose(
loc, diag::serialization_skipped_invalid_type_unknown_name);
}
hadError = true;
return true;
}
void serialization::writeToStream(
raw_ostream &os, ModuleOrSourceFile DC, const SILModule *M,
const SerializationOptions &options,