Skip to content

Commit 5dc060e

Browse files
committed
Define ResolveTypeRequest
1 parent ab908f0 commit 5dc060e

File tree

13 files changed

+97
-38
lines changed

13 files changed

+97
-38
lines changed

include/swift/AST/DiagnosticsCommon.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -152,6 +152,9 @@ WARNING(warn_property_wrapper_module_scope,none,
152152
"wrapper %0; please qualify the reference with %1",
153153
(DeclNameRef, Identifier))
154154

155+
NOTE(circular_type_resolution_note,none,
156+
"while resolving type %0", (TypeRepr *))
157+
155158
//------------------------------------------------------------------------------
156159
// MARK: Cross-import overlay loading diagnostics
157160
//------------------------------------------------------------------------------

include/swift/AST/TypeCheckRequests.h

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ class TrailingWhereClause;
5050
class TypeAliasDecl;
5151
class TypeLoc;
5252
class Witness;
53+
class TypeResolution;
5354
struct TypeWitnessAndDecl;
5455
class ValueDecl;
5556
enum class OpaqueReadOwnership: uint8_t;
@@ -2406,6 +2407,28 @@ class HasImplementationOnlyImportsRequest
24062407
bool isCached() const { return true; }
24072408
};
24082409

2410+
class ResolveTypeRequest
2411+
: public SimpleRequest<ResolveTypeRequest,
2412+
Type(TypeResolution *, TypeRepr *),
2413+
RequestFlags::Uncached> {
2414+
public:
2415+
using SimpleRequest::SimpleRequest;
2416+
2417+
public:
2418+
// Cycle handling.
2419+
void noteCycleStep(DiagnosticEngine &diags) const;
2420+
2421+
private:
2422+
friend SimpleRequest;
2423+
2424+
// Evaluation.
2425+
Type evaluate(Evaluator &evaluator, TypeResolution *resolution,
2426+
TypeRepr *repr) const;
2427+
};
2428+
2429+
void simple_display(llvm::raw_ostream &out, const TypeResolution *resolution);
2430+
SourceLoc extractNearestSourceLoc(const TypeRepr *repr);
2431+
24092432
// Allow AnyValue to compare two Type values, even though Type doesn't
24102433
// support ==.
24112434
template<>

include/swift/AST/TypeCheckerTypeIDZone.def

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,8 @@ SWIFT_REQUEST(TypeChecker, ResolveImplicitMemberRequest,
226226
SWIFT_REQUEST(TypeChecker, ResolveTypeEraserTypeRequest,
227227
Type(ProtocolDecl *, TypeEraserAttr *),
228228
SeparatelyCached, NoLocationInfo)
229+
SWIFT_REQUEST(TypeChecker, ResolveTypeRequest,
230+
Type (TypeResolution *, TypeRepr *), Uncached, NoLocationInfo)
229231
SWIFT_REQUEST(TypeChecker, SPIGroupsRequest,
230232
llvm::ArrayRef<Identifier>(Decl *),
231233
Cached, NoLocationInfo)

lib/AST/TypeCheckRequests.cpp

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1501,3 +1501,23 @@ void swift::simple_display(llvm::raw_ostream &out,
15011501
out << "implicit import of ";
15021502
simple_display(out, import.Module);
15031503
}
1504+
1505+
//----------------------------------------------------------------------------//
1506+
// ResolveTypeRequest computation.
1507+
//----------------------------------------------------------------------------//
1508+
1509+
void ResolveTypeRequest::noteCycleStep(DiagnosticEngine &diags) const {
1510+
auto *repr = std::get<1>(getStorage());
1511+
diags.diagnose(repr->getLoc(), diag::circular_type_resolution_note, repr);
1512+
}
1513+
1514+
void swift::simple_display(llvm::raw_ostream &out,
1515+
const TypeResolution *resolution) {
1516+
out << "while resolving type ";
1517+
}
1518+
1519+
SourceLoc swift::extractNearestSourceLoc(const TypeRepr *repr) {
1520+
if (!repr)
1521+
return SourceLoc();
1522+
return repr->getLoc();
1523+
}

lib/Sema/TypeCheckType.cpp

Lines changed: 30 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,6 @@
2121
#include "TypeCheckType.h"
2222
#include "TypoCorrection.h"
2323

24-
#include "swift/Strings.h"
2524
#include "swift/AST/ASTDemangler.h"
2625
#include "swift/AST/ASTVisitor.h"
2726
#include "swift/AST/ASTWalker.h"
@@ -35,12 +34,14 @@
3534
#include "swift/AST/PrettyStackTrace.h"
3635
#include "swift/AST/ProtocolConformance.h"
3736
#include "swift/AST/SourceFile.h"
37+
#include "swift/AST/TypeCheckRequests.h"
3838
#include "swift/AST/TypeLoc.h"
3939
#include "swift/AST/TypeResolutionStage.h"
4040
#include "swift/Basic/SourceManager.h"
4141
#include "swift/Basic/Statistic.h"
4242
#include "swift/Basic/StringExtras.h"
4343
#include "swift/ClangImporter/ClangImporter.h"
44+
#include "swift/Strings.h"
4445
#include "llvm/ADT/APInt.h"
4546
#include "llvm/ADT/SmallPtrSet.h"
4647
#include "llvm/ADT/SmallString.h"
@@ -1748,7 +1749,7 @@ bool TypeChecker::validateType(TypeLoc &Loc, TypeResolution resolution) {
17481749
if (auto *Stats = resolution.getASTContext().Stats)
17491750
Stats->getFrontendCounters().NumTypesValidated++;
17501751

1751-
Type type = resolution.resolveType(Loc.getTypeRepr());
1752+
auto type = resolution.resolveType(Loc.getTypeRepr());
17521753
Loc.setType(type);
17531754

17541755
return type->hasError();
@@ -1871,34 +1872,39 @@ namespace {
18711872

18721873
Type TypeResolution::resolveType(TypeRepr *TyR) {
18731874
auto &ctx = getASTContext();
1874-
FrontendStatsTracer StatsTracer(ctx.Stats,
1875-
"resolve-type", TyR);
1876-
PrettyStackTraceTypeRepr stackTrace(ctx, "resolving", TyR);
1877-
1878-
TypeResolver typeResolver(*this);
1879-
1880-
auto result = typeResolver.resolveType(TyR, getOptions());
1875+
auto Ty =
1876+
evaluateOrDefault(ctx.evaluator, ResolveTypeRequest{this, TyR}, Type());
1877+
if (!Ty)
1878+
return ErrorType::get(ctx);
1879+
return Ty;
1880+
}
18811881

1882-
if (result) {
1883-
// If we resolved down to an error, make sure to mark the typeRepr as invalid
1884-
// so we don't produce a redundant diagnostic.
1885-
if (result->hasError()) {
1886-
TyR->setInvalid();
1887-
return result;
1888-
}
1882+
Type ResolveTypeRequest::evaluate(Evaluator &evaluator,
1883+
TypeResolution *resolution,
1884+
TypeRepr *TyR) const {
1885+
const auto options = resolution->getOptions();
1886+
auto &ctx = resolution->getASTContext();
1887+
auto result =
1888+
TypeResolver(*resolution).resolveType(TyR, resolution->getOptions());
18891889

1890-
auto loc = TyR->getLoc();
1890+
// If we resolved down to an error, make sure to mark the typeRepr as invalid
1891+
// so we don't produce a redundant diagnostic.
1892+
if (result->hasError()) {
1893+
TyR->setInvalid();
1894+
return result;
1895+
}
18911896

1892-
if (options.contains(TypeResolutionFlags::SILType)
1893-
&& !result->isLegalSILType()) {
1894-
ctx.Diags.diagnose(loc, diag::illegal_sil_type, result);
1895-
return ErrorType::get(ctx);
1896-
}
1897+
auto loc = TyR->getLoc();
18971898

1898-
if (validateAutoClosureAttributeUse(ctx.Diags, TyR, result, options))
1899-
return ErrorType::get(ctx);
1899+
if (options.contains(TypeResolutionFlags::SILType)
1900+
&& !result->isLegalSILType()) {
1901+
ctx.Diags.diagnose(loc, diag::illegal_sil_type, result);
1902+
return ErrorType::get(ctx);
19001903
}
19011904

1905+
if (validateAutoClosureAttributeUse(ctx.Diags, TyR, result, options))
1906+
return ErrorType::get(ctx);
1907+
19021908
return result;
19031909
}
19041910

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
// RUN: %target-typecheck-verify-swift
22

3-
typealias A = B // expected-error {{type alias 'A' references itself}} expected-note {{through reference here}}
4-
typealias C = D // expected-note {{through reference here}} expected-note {{through reference here}}
5-
typealias D = (A, Int) // expected-note {{through reference here}} expected-note {{through reference here}}
6-
typealias B = C // expected-note {{through reference here}} expected-note {{through reference here}}
3+
typealias A = B // expected-error {{type alias 'A' references itself}} expected-note {{while resolving type 'B'}} expected-note {{through reference here}}
4+
typealias C = D // expected-note {{through reference here}} expected-note {{while resolving type 'D'}} expected-note {{through reference here}}
5+
typealias D = (A, Int) // expected-note {{through reference here}} expected-note {{while resolving type '(A, Int)'}} expected-note {{through reference here}}
6+
typealias B = C // expected-note {{through reference here}} expected-note {{while resolving type 'C'}} expected-note {{through reference here}}

test/Generics/generic_types.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -231,7 +231,8 @@ class Bottom<T : Bottom<Top>> {}
231231
// expected-error@-1 {{generic class 'Bottom' references itself}}
232232
// expected-note@-2 {{type declared here}}
233233
// expected-error@-3 {{circular reference}}
234-
// expected-note@-4 {{through reference here}}
234+
// expected-note@-4 {{while resolving type 'Bottom<Top>'}}
235+
// expected-note@-5 {{through reference here}}
235236

236237
// Invalid inheritance clause
237238

test/Sema/circular_decl_checking.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ class X {
6666
// <rdar://problem/17144076> recursive typealias causes a segfault in the type checker
6767
struct SomeStruct<A> {
6868
typealias A = A // this is OK now -- the underlying type is the generic parameter 'A'
69-
typealias B = B // expected-error {{type alias 'B' references itself}}
69+
typealias B = B // expected-error {{type alias 'B' references itself}} expected-note {{while resolving type 'B'}}
7070
}
7171

7272
// <rdar://problem/27680407> Infinite recursion when using fully-qualified associatedtype name that has not been defined with typealias

test/Sema/diag_typealias.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,4 @@
22

33
struct S {}
44

5-
typealias S = S // expected-error {{type alias 'S' references itself}} expected-note {{through reference here}}
5+
typealias S = S // expected-error {{type alias 'S' references itself}} expected-note {{while resolving type 'S'}} expected-note {{through reference here}}

test/decl/circularity.swift

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,8 @@ class C1 {
7171
class C2: C1, P {
7272
override func run(a: A) {}
7373
// expected-error@-1 {{circular reference}}
74-
// expected-note@-2 2{{through reference here}}
74+
// expected-note@-2 {{while resolving type 'A'}}
75+
// expected-note@-3 2{{through reference here}}
7576
}
7677

7778
// Another crash to the above
@@ -98,7 +99,8 @@ class C4 {
9899

99100
class D4 : C4, P1 { // expected-note 2 {{through reference here}}
100101
required init(x: X) { // expected-error {{circular reference}}
101-
// expected-note@-1 2{{through reference here}}
102+
// expected-note@-1 {{while resolving type 'X'}}
103+
// expected-note@-2 2{{through reference here}}
102104
super.init(x: x)
103105
}
104106
}

0 commit comments

Comments
 (0)