Skip to content

Commit 2ab5ea8

Browse files
committed
Define UnderlyingTypeRequest
Define a request for computing the interface type of the underlying type of a typealias. This can be used in place of the declared interface type of the alias itself when it is nested to preserve the fragile validation ordering issues that can cause.
1 parent 58459e7 commit 2ab5ea8

File tree

4 files changed

+47
-0
lines changed

4 files changed

+47
-0
lines changed

include/swift/AST/Decl.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2947,6 +2947,8 @@ class OpaqueTypeDecl : public GenericTypeDecl {
29472947
/// TypeAliasDecl's always have 'MetatypeType' type.
29482948
///
29492949
class TypeAliasDecl : public GenericTypeDecl {
2950+
friend class UnderlyingTypeRequest;
2951+
29502952
/// The location of the 'typealias' keyword
29512953
SourceLoc TypeAliasLoc;
29522954

include/swift/AST/TypeCheckRequests.h

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1181,6 +1181,28 @@ class GenericSignatureRequest :
11811181
void cacheResult(GenericSignature *value) const;
11821182
};
11831183

1184+
/// Compute the interface type of the underlying definition type of a typealias declaration.
1185+
class UnderlyingTypeRequest :
1186+
public SimpleRequest<UnderlyingTypeRequest,
1187+
Type(TypeAliasDecl *),
1188+
CacheKind::SeparatelyCached> {
1189+
public:
1190+
using SimpleRequest::SimpleRequest;
1191+
1192+
private:
1193+
friend SimpleRequest;
1194+
1195+
// Evaluation.
1196+
llvm::Expected<Type> evaluate(Evaluator &evaluator,
1197+
TypeAliasDecl *decl) const;
1198+
1199+
public:
1200+
// Caching.
1201+
bool isCached() const { return true; }
1202+
Optional<Type> getCachedResult() const;
1203+
void cacheResult(Type value) const;
1204+
};
1205+
11841206
// Allow AnyValue to compare two Type values, even though Type doesn't
11851207
// support ==.
11861208
template<>

include/swift/AST/TypeCheckerTypeIDZone.def

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -132,5 +132,7 @@ SWIFT_REQUEST(TypeChecker, SynthesizeAccessorRequest,
132132
SeparatelyCached, NoLocationInfo)
133133
SWIFT_REQUEST(TypeChecker, TypeCheckFunctionBodyUntilRequest,
134134
bool(AbstractFunctionDecl *, SourceLoc), Cached, NoLocationInfo)
135+
SWIFT_REQUEST(TypeChecker, UnderlyingTypeRequest, Type(TypeAliasDecl *),
136+
SeparatelyCached, NoLocationInfo)
135137
SWIFT_REQUEST(TypeChecker, USRGenerationRequest, std::string(const ValueDecl *),
136138
Cached, NoLocationInfo)

lib/AST/TypeCheckRequests.cpp

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -822,3 +822,24 @@ void GenericSignatureRequest::cacheResult(GenericSignature *value) const {
822822
auto *GC = std::get<0>(getStorage());
823823
GC->GenericSigAndBit.setPointerAndInt(value, true);
824824
}
825+
826+
//----------------------------------------------------------------------------//
827+
// IsImplicitlyUnwrappedOptionalRequest computation.
828+
//----------------------------------------------------------------------------//
829+
830+
Optional<Type>
831+
UnderlyingTypeRequest::getCachedResult() const {
832+
auto *typeAlias = std::get<0>(getStorage());
833+
if (auto type = typeAlias->UnderlyingTy.getType())
834+
return type;
835+
return None;
836+
}
837+
838+
void UnderlyingTypeRequest::cacheResult(Type value) const {
839+
auto *typeAlias = std::get<0>(getStorage());
840+
// lldb creates global typealiases containing archetypes
841+
// sometimes...
842+
if (value->hasArchetype() && typeAlias->isGenericContext())
843+
value = value->mapTypeOutOfContext();
844+
typeAlias->UnderlyingTy.setType(value);
845+
}

0 commit comments

Comments
 (0)