mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
AST: Remove AssociatedType
This commit is contained in:
@@ -23,51 +23,6 @@
|
||||
|
||||
namespace swift {
|
||||
|
||||
/// A type associated with a protocol.
|
||||
///
|
||||
/// This struct exists largely so that we can maybe eventually
|
||||
/// generalize it to an arbitrary path.
|
||||
class AssociatedType {
|
||||
AssociatedTypeDecl *Association;
|
||||
using AssociationInfo = llvm::DenseMapInfo<AssociatedTypeDecl*>;
|
||||
|
||||
struct SpecialValue {};
|
||||
explicit AssociatedType(SpecialValue _, AssociatedTypeDecl *specialValue)
|
||||
: Association(specialValue) {}
|
||||
|
||||
public:
|
||||
explicit AssociatedType(AssociatedTypeDecl *association)
|
||||
: Association(association) {
|
||||
assert(association);
|
||||
}
|
||||
|
||||
ProtocolDecl *getSourceProtocol() const {
|
||||
return Association->getProtocol();
|
||||
}
|
||||
|
||||
AssociatedTypeDecl *getAssociation() const {
|
||||
return Association;
|
||||
}
|
||||
|
||||
friend bool operator==(AssociatedType lhs, AssociatedType rhs) {
|
||||
return lhs.Association == rhs.Association;
|
||||
}
|
||||
friend bool operator!=(AssociatedType lhs, AssociatedType rhs) {
|
||||
return !(lhs == rhs);
|
||||
}
|
||||
|
||||
unsigned getHashValue() const {
|
||||
return llvm::hash_value(Association);
|
||||
}
|
||||
|
||||
static AssociatedType getEmptyKey() {
|
||||
return AssociatedType(SpecialValue(), AssociationInfo::getEmptyKey());
|
||||
}
|
||||
static AssociatedType getTombstoneKey() {
|
||||
return AssociatedType(SpecialValue(), AssociationInfo::getTombstoneKey());
|
||||
}
|
||||
};
|
||||
|
||||
/// A base conformance of a protocol.
|
||||
class BaseConformance {
|
||||
ProtocolDecl *Source;
|
||||
@@ -147,24 +102,6 @@ public:
|
||||
} // end namespace swift
|
||||
|
||||
namespace llvm {
|
||||
template <> struct DenseMapInfo<swift::AssociatedType> {
|
||||
static inline swift::AssociatedType getEmptyKey() {
|
||||
return swift::AssociatedType::getEmptyKey();
|
||||
}
|
||||
|
||||
static inline swift::AssociatedType getTombstoneKey() {
|
||||
return swift::AssociatedType::getTombstoneKey();
|
||||
}
|
||||
|
||||
static unsigned getHashValue(swift::AssociatedType val) {
|
||||
return val.getHashValue();
|
||||
}
|
||||
|
||||
static bool isEqual(swift::AssociatedType lhs, swift::AssociatedType rhs) {
|
||||
return lhs == rhs;
|
||||
}
|
||||
};
|
||||
|
||||
template <> struct DenseMapInfo<swift::AssociatedConformance> {
|
||||
static inline swift::AssociatedConformance getEmptyKey() {
|
||||
return swift::AssociatedConformance::getEmptyKey();
|
||||
|
||||
@@ -100,7 +100,7 @@ public:
|
||||
// If this is a new associated type (which does not override an
|
||||
// existing associated type), add it.
|
||||
if (associatedType->getOverriddenDecls().empty())
|
||||
asDerived().addAssociatedType(AssociatedType(associatedType));
|
||||
asDerived().addAssociatedType(associatedType);
|
||||
}
|
||||
|
||||
if (asDerived().shouldVisitRequirementSignatureOnly())
|
||||
|
||||
@@ -103,10 +103,10 @@ irgen::emitArchetypeTypeMetadataRef(IRGenFunction &IGF,
|
||||
auto parent = cast<ArchetypeType>(
|
||||
archetype->getGenericEnvironment()->mapTypeIntoContext(
|
||||
member->getBase())->getCanonicalType());
|
||||
AssociatedType association(member->getAssocType());
|
||||
auto *assocType = member->getAssocType();
|
||||
|
||||
MetadataResponse response =
|
||||
emitAssociatedTypeMetadataRef(IGF, parent, association, request);
|
||||
emitAssociatedTypeMetadataRef(IGF, parent, assocType, request);
|
||||
|
||||
setTypeMetadataName(IGF.IGM, response.getMetadata(), archetype);
|
||||
|
||||
@@ -321,11 +321,11 @@ llvm::Value *irgen::emitArchetypeWitnessTableRef(IRGenFunction &IGF,
|
||||
MetadataResponse
|
||||
irgen::emitAssociatedTypeMetadataRef(IRGenFunction &IGF,
|
||||
CanArchetypeType origin,
|
||||
AssociatedType association,
|
||||
AssociatedTypeDecl *assocType,
|
||||
DynamicMetadataRequest request) {
|
||||
// Find the conformance of the origin to the associated type's protocol.
|
||||
llvm::Value *wtable = emitArchetypeWitnessTableRef(IGF, origin,
|
||||
association.getSourceProtocol());
|
||||
assocType->getProtocol());
|
||||
|
||||
// Find the origin's type metadata.
|
||||
llvm::Value *originMetadata =
|
||||
@@ -333,7 +333,7 @@ irgen::emitAssociatedTypeMetadataRef(IRGenFunction &IGF,
|
||||
.getMetadata();
|
||||
|
||||
return emitAssociatedTypeMetadataRef(IGF, originMetadata, wtable,
|
||||
association, request);
|
||||
assocType, request);
|
||||
}
|
||||
|
||||
const TypeInfo *TypeConverter::convertArchetypeType(ArchetypeType *archetype) {
|
||||
|
||||
@@ -25,7 +25,7 @@ namespace llvm {
|
||||
}
|
||||
|
||||
namespace swift {
|
||||
class AssociatedType;
|
||||
class AssociatedTypeDecl;
|
||||
class ProtocolDecl;
|
||||
class SILType;
|
||||
|
||||
@@ -51,7 +51,7 @@ namespace irgen {
|
||||
/// Emit a metadata reference for an associated type of an archetype.
|
||||
MetadataResponse emitAssociatedTypeMetadataRef(IRGenFunction &IGF,
|
||||
CanArchetypeType origin,
|
||||
AssociatedType association,
|
||||
AssociatedTypeDecl *assocType,
|
||||
DynamicMetadataRequest request);
|
||||
|
||||
/// Emit a dynamic metatype lookup for the given archetype.
|
||||
|
||||
@@ -953,8 +953,7 @@ namespace {
|
||||
auto flags = Flags(Flags::Kind::AssociatedTypeAccessFunction);
|
||||
if (auto &schema = IGM.getOptions().PointerAuth
|
||||
.ProtocolAssociatedTypeAccessFunctions) {
|
||||
addDiscriminator(flags, schema,
|
||||
AssociatedType(entry.getAssociatedType()));
|
||||
addDiscriminator(flags, schema, entry.getAssociatedType());
|
||||
}
|
||||
|
||||
// Look for a default witness.
|
||||
|
||||
@@ -160,7 +160,7 @@ struct IRGenModule::PointerAuthCachesType {
|
||||
llvm::DenseMap<SILDeclRef, llvm::ConstantInt*> Decls;
|
||||
llvm::DenseMap<CanType, llvm::ConstantInt*> Types;
|
||||
llvm::DenseMap<CanType, llvm::ConstantInt*> YieldTypes;
|
||||
llvm::DenseMap<AssociatedType, llvm::ConstantInt*> AssociatedTypes;
|
||||
llvm::DenseMap<AssociatedTypeDecl *, llvm::ConstantInt*> AssociatedTypes;
|
||||
llvm::DenseMap<AssociatedConformance, llvm::ConstantInt*> AssociatedConformances;
|
||||
};
|
||||
|
||||
@@ -336,9 +336,9 @@ static llvm::ConstantInt *getDiscriminatorForString(IRGenModule &IGM,
|
||||
return getDiscriminatorForHash(IGM, rawHash);
|
||||
}
|
||||
|
||||
static std::string mangle(AssociatedType association) {
|
||||
return IRGenMangler(association.getAssociation()->getASTContext())
|
||||
.mangleAssociatedTypeAccessFunctionDiscriminator(association);
|
||||
static std::string mangle(AssociatedTypeDecl *assocType) {
|
||||
return IRGenMangler(assocType->getASTContext())
|
||||
.mangleAssociatedTypeAccessFunctionDiscriminator(assocType);
|
||||
}
|
||||
|
||||
static std::string mangle(const AssociatedConformance &association) {
|
||||
@@ -430,7 +430,7 @@ PointerAuthEntity::getDeclDiscriminator(IRGenModule &IGM) const {
|
||||
}
|
||||
|
||||
case Kind::AssociatedType: {
|
||||
auto association = Storage.get<AssociatedType>(StoredKind);
|
||||
auto association = Storage.get<AssociatedTypeDecl *>(StoredKind);
|
||||
llvm::ConstantInt *&cache =
|
||||
IGM.getPointerAuthCaches().AssociatedTypes[association];
|
||||
if (cache) return cache;
|
||||
|
||||
@@ -86,7 +86,7 @@ private:
|
||||
using Members = ExternalUnionMembers<void,
|
||||
Special,
|
||||
ValueWitness,
|
||||
AssociatedType,
|
||||
AssociatedTypeDecl *,
|
||||
AssociatedConformance,
|
||||
CanSILFunctionType,
|
||||
SILDeclRef,
|
||||
@@ -105,7 +105,7 @@ private:
|
||||
case Kind::SILDeclRef:
|
||||
return Members::indexOf<SILDeclRef>();
|
||||
case Kind::AssociatedType:
|
||||
return Members::indexOf<AssociatedType>();
|
||||
return Members::indexOf<AssociatedTypeDecl *>();
|
||||
case Kind::AssociatedConformance:
|
||||
return Members::indexOf<AssociatedConformance>();
|
||||
case Kind::SILFunction:
|
||||
@@ -139,9 +139,9 @@ public:
|
||||
assert(isValueWitnessFunction(witness));
|
||||
Storage.emplace<ValueWitness>(StoredKind, witness);
|
||||
}
|
||||
PointerAuthEntity(AssociatedType association)
|
||||
PointerAuthEntity(AssociatedTypeDecl *assocType)
|
||||
: StoredKind(Kind::AssociatedType) {
|
||||
Storage.emplaceAggregate<AssociatedType>(StoredKind, association);
|
||||
Storage.emplaceAggregate<AssociatedTypeDecl *>(StoredKind, assocType);
|
||||
}
|
||||
PointerAuthEntity(const AssociatedConformance &association)
|
||||
: StoredKind(Kind::AssociatedConformance) {
|
||||
|
||||
@@ -946,11 +946,11 @@ namespace {
|
||||
}
|
||||
}
|
||||
|
||||
void addAssociatedType(AssociatedType requirement) {
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
// In Embedded Swift witness tables don't have associated-types entries.
|
||||
if (requirement.getAssociation()->getASTContext().LangOpts.hasFeature(Feature::Embedded))
|
||||
if (assocType->getASTContext().LangOpts.hasFeature(Feature::Embedded))
|
||||
return;
|
||||
Entries.push_back(WitnessTableEntry::forAssociatedType(requirement));
|
||||
Entries.push_back(WitnessTableEntry::forAssociatedType(assocType));
|
||||
}
|
||||
|
||||
void addAssociatedConformance(const AssociatedConformance &req) {
|
||||
@@ -1330,8 +1330,8 @@ mapConformanceIntoContext(const RootProtocolConformance *conf) {
|
||||
|
||||
WitnessIndex ProtocolInfo::getAssociatedTypeIndex(
|
||||
IRGenModule &IGM,
|
||||
AssociatedType assocType) const {
|
||||
assert(!IGM.isResilient(assocType.getSourceProtocol(),
|
||||
AssociatedTypeDecl *assocType) const {
|
||||
assert(!IGM.isResilient(assocType->getProtocol(),
|
||||
ResilienceExpansion::Maximal) &&
|
||||
"Cannot ask for the associated type index of non-resilient protocol");
|
||||
for (auto &witness : getWitnessEntries()) {
|
||||
@@ -1707,7 +1707,7 @@ public:
|
||||
llvm_unreachable("cannot emit a witness table with placeholders in it");
|
||||
}
|
||||
|
||||
void addAssociatedType(AssociatedType requirement) {
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
auto &entry = SILEntries.front();
|
||||
SILEntries = SILEntries.slice(1);
|
||||
|
||||
@@ -1718,10 +1718,9 @@ public:
|
||||
#ifndef NDEBUG
|
||||
assert(entry.getKind() == SILWitnessTable::AssociatedType
|
||||
&& "sil witness table does not match protocol");
|
||||
assert(entry.getAssociatedTypeWitness().Requirement
|
||||
== requirement.getAssociation()
|
||||
assert(entry.getAssociatedTypeWitness().Requirement == assocType
|
||||
&& "sil witness table does not match protocol");
|
||||
auto piIndex = PI.getAssociatedTypeIndex(IGM, requirement);
|
||||
auto piIndex = PI.getAssociatedTypeIndex(IGM, assocType);
|
||||
assert((size_t)piIndex.getValue() ==
|
||||
Table.size() - WitnessTableFirstRequirementOffset &&
|
||||
"offset doesn't match ProtocolInfo layout");
|
||||
@@ -1729,23 +1728,22 @@ public:
|
||||
(void)entry;
|
||||
#endif
|
||||
|
||||
auto associate =
|
||||
Conformance.getTypeWitness(requirement.getAssociation());
|
||||
llvm::Constant *witness =
|
||||
auto typeWitness = Conformance.getTypeWitness(assocType);
|
||||
llvm::Constant *typeWitnessAddr =
|
||||
IGM.getAssociatedTypeWitness(
|
||||
associate,
|
||||
typeWitness,
|
||||
Conformance.getDeclContext()->getGenericSignatureOfContext(),
|
||||
/*inProtocolContext=*/false);
|
||||
witness = llvm::ConstantExpr::getBitCast(witness, IGM.Int8PtrTy);
|
||||
typeWitnessAddr = llvm::ConstantExpr::getBitCast(typeWitnessAddr, IGM.Int8PtrTy);
|
||||
|
||||
if (isRelative) {
|
||||
Table.addRelativeAddress(witness);
|
||||
Table.addRelativeAddress(typeWitnessAddr);
|
||||
return;
|
||||
}
|
||||
|
||||
auto &schema = IGM.getOptions().PointerAuth
|
||||
.ProtocolAssociatedTypeAccessFunctions;
|
||||
Table.addSignedPointer(witness, schema, requirement);
|
||||
Table.addSignedPointer(typeWitnessAddr, schema, assocType);
|
||||
}
|
||||
|
||||
void addAssociatedConformance(AssociatedConformance requirement) {
|
||||
@@ -3513,7 +3511,7 @@ MetadataResponse MetadataPath::followComponent(IRGenFunction &IGF,
|
||||
SubstitutionMap::getProtocolSubstitutions(sourceConformance))
|
||||
->getCanonicalType();
|
||||
if (auto archetypeType = dyn_cast<ArchetypeType>(baseSubstType)) {
|
||||
AssociatedType baseAssocType(depMemType->getAssocType());
|
||||
auto *baseAssocType = depMemType->getAssocType();
|
||||
|
||||
MetadataResponse response =
|
||||
emitAssociatedTypeMetadataRef(IGF, archetypeType, baseAssocType,
|
||||
@@ -4538,18 +4536,18 @@ MetadataResponse
|
||||
irgen::emitAssociatedTypeMetadataRef(IRGenFunction &IGF,
|
||||
llvm::Value *parentMetadata,
|
||||
llvm::Value *wtable,
|
||||
AssociatedType associatedType,
|
||||
AssociatedTypeDecl *assocType,
|
||||
DynamicMetadataRequest request) {
|
||||
auto &IGM = IGF.IGM;
|
||||
|
||||
// Extract the requirements base descriptor.
|
||||
auto reqBaseDescriptor =
|
||||
IGM.getAddrOfProtocolRequirementsBaseDescriptor(
|
||||
associatedType.getSourceProtocol());
|
||||
assocType->getProtocol());
|
||||
|
||||
// Extract the associated type descriptor.
|
||||
auto assocTypeDescriptor =
|
||||
IGM.getAddrOfAssociatedTypeDescriptor(associatedType.getAssociation());
|
||||
IGM.getAddrOfAssociatedTypeDescriptor(assocType);
|
||||
// Call swift_getAssociatedTypeWitness().
|
||||
auto call =
|
||||
IGF.IGM.IRGen.Opts.UseRelativeProtocolWitnessTables ?
|
||||
|
||||
@@ -29,7 +29,7 @@ namespace llvm {
|
||||
|
||||
namespace swift {
|
||||
class AssociatedConformance;
|
||||
class AssociatedType;
|
||||
class AssociatedTypeDecl;
|
||||
class CanType;
|
||||
class FuncDecl;
|
||||
enum class MetadataState : size_t;
|
||||
@@ -90,11 +90,11 @@ namespace irgen {
|
||||
///
|
||||
/// \param parentMetadata - the type metadata for T
|
||||
/// \param wtable - the witness table witnessing the conformance of T to P
|
||||
/// \param associatedType - the declaration of X; a member of P
|
||||
/// \param assocType - the declaration of X; a member of P
|
||||
MetadataResponse emitAssociatedTypeMetadataRef(IRGenFunction &IGF,
|
||||
llvm::Value *parentMetadata,
|
||||
llvm::Value *wtable,
|
||||
AssociatedType associatedType,
|
||||
AssociatedTypeDecl *assocType,
|
||||
DynamicMetadataRequest request);
|
||||
|
||||
// Return the offset one should do on a witness table pointer to retrieve the
|
||||
|
||||
@@ -435,10 +435,10 @@ public:
|
||||
}
|
||||
|
||||
std::string
|
||||
mangleAssociatedTypeAccessFunctionDiscriminator(AssociatedType association) {
|
||||
mangleAssociatedTypeAccessFunctionDiscriminator(AssociatedTypeDecl *assocDecl) {
|
||||
beginMangling();
|
||||
appendAnyGenericType(association.getSourceProtocol());
|
||||
appendIdentifier(association.getAssociation()->getNameStr());
|
||||
appendAnyGenericType(assocDecl->getProtocol());
|
||||
appendIdentifier(assocDecl->getNameStr());
|
||||
return finalize();
|
||||
}
|
||||
|
||||
|
||||
@@ -187,9 +187,8 @@ static void checkPointerAuthAssociatedTypeDiscriminator(IRGenModule &IGM, ArrayR
|
||||
auto &schema = IGM.getOptions().PointerAuth.ProtocolAssociatedTypeAccessFunctions;
|
||||
if (!schema.isEnabled()) return;
|
||||
|
||||
auto decl = dyn_cast_or_null<AssociatedTypeDecl>(lookupSimple(IGM.getSwiftModule(), declPath));
|
||||
assert(decl && "decl not found");
|
||||
auto discriminator = PointerAuthInfo::getOtherDiscriminator(IGM, schema, AssociatedType(decl));
|
||||
auto decl = cast<AssociatedTypeDecl>(lookupSimple(IGM.getSwiftModule(), declPath));
|
||||
auto discriminator = PointerAuthInfo::getOtherDiscriminator(IGM, schema, decl);
|
||||
assert(discriminator->getZExtValue() == expected && "discriminator value doesn't match");
|
||||
}
|
||||
|
||||
|
||||
@@ -92,7 +92,6 @@ namespace clang {
|
||||
namespace swift {
|
||||
class GenericSignature;
|
||||
class AssociatedConformance;
|
||||
class AssociatedType;
|
||||
class ASTContext;
|
||||
class BaseConformance;
|
||||
class BraceStmt;
|
||||
|
||||
@@ -124,9 +124,9 @@ public:
|
||||
return MethodEntry.Witness;
|
||||
}
|
||||
|
||||
static WitnessTableEntry forAssociatedType(AssociatedType ty) {
|
||||
static WitnessTableEntry forAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
WitnessTableEntry entry(WitnessKind::AssociatedTypeKind);
|
||||
entry.AssociatedTypeEntry = {ty.getAssociation()};
|
||||
entry.AssociatedTypeEntry = {assocType};
|
||||
return entry;
|
||||
}
|
||||
|
||||
@@ -134,9 +134,8 @@ public:
|
||||
return Kind == WitnessKind::AssociatedTypeKind;
|
||||
}
|
||||
|
||||
bool matchesAssociatedType(AssociatedType assocType) const {
|
||||
return isAssociatedType() &&
|
||||
AssociatedTypeEntry.Association == assocType.getAssociation();
|
||||
bool matchesAssociatedType(AssociatedTypeDecl *assocType) const {
|
||||
return isAssociatedType() && AssociatedTypeEntry.Association == assocType;
|
||||
}
|
||||
|
||||
AssociatedTypeDecl *getAssociatedType() const {
|
||||
@@ -293,7 +292,7 @@ public:
|
||||
/// Return the witness index for the type metadata access function
|
||||
/// for the given associated type.
|
||||
WitnessIndex getAssociatedTypeIndex(IRGenModule &IGM,
|
||||
AssociatedType assocType) const;
|
||||
AssociatedTypeDecl *assocType) const;
|
||||
|
||||
/// Return the witness index for the protocol witness table access
|
||||
/// function for the given associated protocol conformance.
|
||||
|
||||
@@ -852,8 +852,8 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void addAssociatedType(AssociatedType associatedType) {
|
||||
Visitor.addAssociatedTypeDescriptor(associatedType.getAssociation());
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
Visitor.addAssociatedTypeDescriptor(assocType);
|
||||
}
|
||||
|
||||
void addProtocolConformanceDescriptor() {
|
||||
|
||||
@@ -678,13 +678,12 @@ public:
|
||||
SILWitnessTable::MethodWitness{requirementRef, witnessFn});
|
||||
}
|
||||
|
||||
void addAssociatedType(AssociatedType requirement) {
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
// Find the substitution info for the witness type.
|
||||
auto td = requirement.getAssociation();
|
||||
Type witness = Conformance->getTypeWitness(td);
|
||||
Type witness = Conformance->getTypeWitness(assocType);
|
||||
|
||||
// Emit the record for the type itself.
|
||||
Entries.push_back(SILWitnessTable::AssociatedTypeWitness{td,
|
||||
Entries.push_back(SILWitnessTable::AssociatedTypeWitness{assocType,
|
||||
witness->getCanonicalType()});
|
||||
}
|
||||
|
||||
@@ -1028,7 +1027,7 @@ public:
|
||||
void addAssociatedConformance(AssociatedConformance conformance) {
|
||||
llvm_unreachable("associated conformances not supported in self-conformance");
|
||||
}
|
||||
void addAssociatedType(AssociatedType type) {
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
llvm_unreachable("associated types not supported in self-conformance");
|
||||
}
|
||||
void addPlaceholder(MissingMemberDecl *placeholder) {
|
||||
@@ -1106,14 +1105,14 @@ public:
|
||||
DefaultWitnesses.push_back(entry);
|
||||
}
|
||||
|
||||
void addAssociatedType(AssociatedType req) {
|
||||
Type witness = Proto->getDefaultTypeWitness(req.getAssociation());
|
||||
void addAssociatedType(AssociatedTypeDecl *assocType) {
|
||||
Type witness = Proto->getDefaultTypeWitness(assocType);
|
||||
if (!witness)
|
||||
return addMissingDefault();
|
||||
|
||||
Type witnessInContext = Proto->mapTypeIntoContext(witness);
|
||||
auto entry = SILWitnessTable::AssociatedTypeWitness{
|
||||
req.getAssociation(),
|
||||
assocType,
|
||||
witnessInContext->getCanonicalType()};
|
||||
DefaultWitnesses.push_back(entry);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user