Skip to content

Rid performTypeLocChecking of TypeLoc #33251

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Aug 4, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 7 additions & 19 deletions include/swift/Subsystems.h
Original file line number Diff line number Diff line change
Expand Up @@ -65,8 +65,9 @@ namespace swift {
struct TBDGenOptions;
class Token;
class TopLevelContext;
class Type;
class TypeCheckerOptions;
class TypeLoc;
class TypeRepr;
class UnifiedStatsReporter;

namespace Lowering {
Expand Down Expand Up @@ -140,28 +141,15 @@ namespace swift {
/// emitted.
void performWholeModuleTypeChecking(SourceFile &SF);

/// Recursively validate the specified type.
/// Resolve the given \c TypeRepr to a contextual type.
///
/// This is used when dealing with partial source files (e.g. SIL parsing,
/// code completion).
///
/// \returns false on success, true on error.
bool performTypeLocChecking(ASTContext &Ctx, TypeLoc &T,
DeclContext *DC,
bool ProduceDiagnostics = true);

/// Recursively validate the specified type.
///
/// This is used when dealing with partial source files (e.g. SIL parsing,
/// code completion).
///
/// \returns false on success, true on error.
bool performTypeLocChecking(ASTContext &Ctx, TypeLoc &T,
bool isSILMode,
bool isSILType,
GenericEnvironment *GenericEnv,
DeclContext *DC,
bool ProduceDiagnostics = true);
/// \returns A well-formed type on success, or an \c ErrorType.
Type performTypeResolution(TypeRepr *TyR, ASTContext &Ctx, bool isSILMode,
bool isSILType, GenericEnvironment *GenericEnv,
DeclContext *DC, bool ProduceDiagnostics = true);

/// Expose TypeChecker's handling of GenericParamList to SIL parsing.
GenericEnvironment *handleSILGenericParams(GenericParamList *genericParams,
Expand Down
15 changes: 13 additions & 2 deletions lib/IDE/CodeCompletion.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1613,9 +1613,20 @@ class CodeCompletionCallbacksImpl : public CodeCompletionCallbacks {
/// \returns true on success, false on failure.
bool typecheckParsedType() {
assert(ParsedTypeLoc.getTypeRepr() && "should have a TypeRepr");
if (!performTypeLocChecking(P.Context, ParsedTypeLoc,
CurDeclContext, false))
if (ParsedTypeLoc.wasValidated() && !ParsedTypeLoc.isError()) {
return true;
}

const auto ty = swift::performTypeResolution(
ParsedTypeLoc.getTypeRepr(), P.Context,
/*isSILMode=*/false,
/*isSILType=*/false, CurDeclContext->getGenericEnvironmentOfContext(),
CurDeclContext,
/*ProduceDiagnostics=*/false);
ParsedTypeLoc.setType(ty);
if (!ParsedTypeLoc.isError()) {
return true;
}

// It doesn't type check as a type, so see if it's a qualifying module name.
if (auto *ITR = dyn_cast<IdentTypeRepr>(ParsedTypeLoc.getTypeRepr())) {
Expand Down
14 changes: 8 additions & 6 deletions lib/IDE/ExprContextAnalysis.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -325,12 +325,14 @@ void swift::ide::collectPossibleReturnTypesFromContext(
candidates.push_back(ty);
return;
} else {
auto typeLoc = TypeLoc{CE->getExplicitResultTypeRepr()};
if (!swift::performTypeLocChecking(
DC->getASTContext(), typeLoc, /*isSILMode=*/false,
/*isSILType=*/false, DC->getGenericEnvironmentOfContext(),
const_cast<DeclContext *>(DC), /*diagnostics=*/false)) {
candidates.push_back(typeLoc.getType());
const auto type = swift::performTypeResolution(
CE->getExplicitResultTypeRepr(), DC->getASTContext(),
/*isSILMode=*/false, /*isSILType=*/false,
DC->getGenericEnvironmentOfContext(),
const_cast<DeclContext *>(DC), /*diagnostics=*/false);

if (!type->hasError()) {
candidates.push_back(type);
return;
}
}
Expand Down
74 changes: 40 additions & 34 deletions lib/SIL/Parser/ParseSIL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -173,8 +173,8 @@ namespace {
/// A callback to be invoked every time a type was deserialized.
std::function<void(Type)> ParsedTypeCallback;

Type performTypeLocChecking(TypeRepr *TyR, bool IsSILType,
GenericEnvironment *GenericEnv = nullptr);
Type performTypeResolution(TypeRepr *TyR, bool IsSILType,
GenericEnvironment *GenericEnv);

void convertRequirements(SILFunction *F, ArrayRef<RequirementRepr> From,
SmallVectorImpl<Requirement> &To);
Expand Down Expand Up @@ -867,9 +867,10 @@ void SILParser::convertRequirements(SILFunction *F,
IdentTypeReprLookup PerformLookup(P);
// Use parser lexical scopes to resolve references
// to the generic parameters.
auto ResolveToInterfaceType = [&](TypeRepr *Ty) -> Type {
Ty->walk(PerformLookup);
return performTypeLocChecking(Ty, /* IsSIL */ false)->mapTypeOutOfContext();
auto ResolveToInterfaceType = [&](TypeRepr *TyR) -> Type {
TyR->walk(PerformLookup);
return performTypeResolution(TyR, /*IsSILType=*/false, ContextGenericEnv)
->mapTypeOutOfContext();
};

for (auto &Req : From) {
Expand Down Expand Up @@ -1091,16 +1092,14 @@ static bool parseDeclSILOptional(bool *isTransparent,
return false;
}

Type SILParser::performTypeLocChecking(TypeRepr *T, bool IsSILType,
GenericEnvironment *GenericEnv) {
Type SILParser::performTypeResolution(TypeRepr *TyR, bool IsSILType,
GenericEnvironment *GenericEnv) {
if (GenericEnv == nullptr)
GenericEnv = ContextGenericEnv;

TypeLoc loc(T);
(void) swift::performTypeLocChecking(P.Context, loc,
/*isSILMode=*/true, IsSILType,
GenericEnv, &P.SF);
return loc.getType();
return swift::performTypeResolution(TyR, P.Context,
/*isSILMode=*/true, IsSILType, GenericEnv,
&P.SF);
}

/// Find the top-level ValueDecl or Module given a name.
Expand Down Expand Up @@ -1154,7 +1153,8 @@ static ValueDecl *lookupMember(Parser &P, Type Ty, DeclBaseName Name,
bool SILParser::parseASTType(CanType &result, GenericEnvironment *env) {
ParserResult<TypeRepr> parsedType = P.parseType();
if (parsedType.isNull()) return true;
auto resolvedType = performTypeLocChecking(parsedType.get(), /*IsSILType=*/ false, env);
const auto resolvedType =
performTypeResolution(parsedType.get(), /*isSILType=*/false, env);
if (resolvedType->hasError())
return true;

Expand Down Expand Up @@ -1243,8 +1243,10 @@ bool SILParser::parseSILType(SILType &Result,
ParsedGenericEnv = env;

// Apply attributes to the type.
auto *attrRepr = P.applyAttributeToType(TyR.get(), attrs, specifier, specifierLoc);
auto Ty = performTypeLocChecking(attrRepr, /*IsSILType=*/true, OuterGenericEnv);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to use the full call in order to propagate TypeResolutionFlags::SILType.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oops

auto *attrRepr =
P.applyAttributeToType(TyR.get(), attrs, specifier, specifierLoc);
const auto Ty =
performTypeResolution(attrRepr, /*IsSILType=*/true, OuterGenericEnv);
if (Ty->hasError())
return true;

Expand Down Expand Up @@ -1696,7 +1698,8 @@ bool SILParser::parseSubstitutions(SmallVectorImpl<ParsedSubstitution> &parsed,
if (defaultForProto)
bindProtocolSelfInTypeRepr(TyR.get(), defaultForProto);

auto Ty = performTypeLocChecking(TyR.get(), /*IsSILType=*/ false, GenericEnv);
const auto Ty =
performTypeResolution(TyR.get(), /*IsSILType=*/false, GenericEnv);
if (Ty->hasError())
return true;
parsed.push_back({Loc, Ty});
Expand Down Expand Up @@ -2105,7 +2108,8 @@ bool SILParser::parseSILDeclRef(SILDeclRef &Member, bool FnTypeRequired) {
}
}

auto Ty = performTypeLocChecking(TyR.get(), /*IsSILType=*/ false, genericEnv);
const auto Ty =
performTypeResolution(TyR.get(), /*IsSILType=*/false, genericEnv);
if (Ty->hasError())
return true;

Expand Down Expand Up @@ -6321,7 +6325,8 @@ ProtocolConformanceRef SILParser::parseProtocolConformanceHelper(
bindProtocolSelfInTypeRepr(TyR.get(), defaultForProto);
}

auto ConformingTy = performTypeLocChecking(TyR.get(), /*IsSILType=*/ false, witnessEnv);
const auto ConformingTy =
performTypeResolution(TyR.get(), /*IsSILType=*/false, witnessEnv);
if (ConformingTy->hasError())
return ProtocolConformanceRef();

Expand Down Expand Up @@ -6437,17 +6442,18 @@ static bool parseSILVTableEntry(
ParserResult<TypeRepr> TyR = P.parseType();
if (TyR.isNull())
return true;
TypeLoc Ty = TyR.get();

if (isDefaultWitnessTable)
bindProtocolSelfInTypeRepr(TyR.get(), proto);
if (swift::performTypeLocChecking(P.Context, Ty,
/*isSILMode=*/false,
/*isSILType=*/false,
witnessEnv,
&P.SF))

const auto Ty =
swift::performTypeResolution(TyR.get(), P.Context,
/*isSILMode=*/false,
/*isSILType=*/false, witnessEnv, &P.SF);
if (Ty->hasError())
return true;

assocOrSubject = Ty.getType()->getCanonicalType();
assocOrSubject = Ty->getCanonicalType();
}
if (!assocOrSubject)
return true;
Expand Down Expand Up @@ -6498,19 +6504,19 @@ static bool parseSILVTableEntry(
ParserResult<TypeRepr> TyR = P.parseType();
if (TyR.isNull())
return true;
TypeLoc Ty = TyR.get();

if (isDefaultWitnessTable)
bindProtocolSelfInTypeRepr(TyR.get(), proto);
if (swift::performTypeLocChecking(P.Context, Ty,
/*isSILMode=*/false,
/*isSILType=*/false,
witnessEnv,
&P.SF))

const auto Ty =
swift::performTypeResolution(TyR.get(), P.Context,
/*isSILMode=*/false,
/*isSILType=*/false, witnessEnv, &P.SF);
if (Ty->hasError())
return true;

witnessEntries.push_back(SILWitnessTable::AssociatedTypeWitness{
assoc, Ty.getType()->getCanonicalType()
});
witnessEntries.push_back(
SILWitnessTable::AssociatedTypeWitness{assoc, Ty->getCanonicalType()});
return false;
}

Expand Down
30 changes: 5 additions & 25 deletions lib/Sema/TypeChecker.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -358,23 +358,10 @@ bool swift::isAdditiveArithmeticConformanceDerivationEnabled(SourceFile &SF) {
return isDifferentiableProgrammingEnabled(SF);
}

bool swift::performTypeLocChecking(ASTContext &Ctx, TypeLoc &T,
DeclContext *DC,
bool ProduceDiagnostics) {
return performTypeLocChecking(
Ctx, T,
/*isSILMode=*/false,
/*isSILType=*/false,
/*GenericEnv=*/DC->getGenericEnvironmentOfContext(),
DC, ProduceDiagnostics);
}

bool swift::performTypeLocChecking(ASTContext &Ctx, TypeLoc &T,
bool isSILMode,
bool isSILType,
GenericEnvironment *GenericEnv,
DeclContext *DC,
bool ProduceDiagnostics) {
Type swift::performTypeResolution(TypeRepr *TyR, ASTContext &Ctx,
bool isSILMode, bool isSILType,
GenericEnvironment *GenericEnv,
DeclContext *DC, bool ProduceDiagnostics) {
TypeResolutionOptions options = None;
if (isSILMode) {
options |= TypeResolutionFlags::SILMode;
Expand All @@ -394,14 +381,7 @@ bool swift::performTypeLocChecking(ASTContext &Ctx, TypeLoc &T,
if (!ProduceDiagnostics)
suppression.emplace(Ctx.Diags);

// If we've already validated this type, don't do so again.
if (T.wasValidated()) {
return T.isError();
}

auto type = resolution.resolveType(T.getTypeRepr());
T.setType(type);
return type->hasError();
return resolution.resolveType(TyR);
}

/// Expose TypeChecker's handling of GenericParamList to SIL parsing.
Expand Down