Skip to content

Continue plumbing resilience expansion through SIL type lowering #23004

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
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
3 changes: 2 additions & 1 deletion include/swift/SIL/OptimizationRemark.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,8 @@ struct Argument {
Argument(StringRef Key, unsigned long long N);

Argument(StringRef Key, SILFunction *F);
Argument(StringRef Key, SILType *Ty);
Argument(StringRef Key, SILType Ty);
Argument(StringRef Key, CanType Ty);
};

/// Shorthand to insert named-value pairs.
Expand Down
4 changes: 3 additions & 1 deletion include/swift/SIL/SILBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -918,8 +918,10 @@ class SILBuilder {
} \
Copy##Name##ValueInst *createCopy##Name##Value(SILLocation Loc, \
SILValue operand) { \
auto type = getFunction().getLoweredType( \
operand->getType().getASTType().getReferenceStorageReferent()); \
return insert(new (getModule()) \
Copy##Name##ValueInst(getSILDebugLocation(Loc), operand, getModule())); \
Copy##Name##ValueInst(getSILDebugLocation(Loc), operand, type)); \
}
#define SOMETIMES_LOADABLE_CHECKED_REF_STORAGE(Name, ...) \
NEVER_LOADABLE_CHECKED_REF_STORAGE(Name, "...") \
Expand Down
18 changes: 18 additions & 0 deletions include/swift/SIL/SILFunction.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,11 @@ class SILModule;
class SILFunctionBuilder;
class SILProfiler;

namespace Lowering {
class TypeLowering;
class AbstractionPattern;
}

enum IsBare_t { IsNotBare, IsBare };
enum IsTransparent_t { IsNotTransparent, IsTransparent };
enum Inline_t { InlineDefault, NoInline, AlwaysInline };
Expand Down Expand Up @@ -464,6 +469,19 @@ class SILFunction
: ResilienceExpansion::Maximal);
}

const Lowering::TypeLowering &
getTypeLowering(Lowering::AbstractionPattern orig, Type subst);

const Lowering::TypeLowering &getTypeLowering(Type t) const;

SILType getLoweredType(Lowering::AbstractionPattern orig, Type subst) const;

SILType getLoweredType(Type t) const;

SILType getLoweredLoadableType(Type t) const;

const Lowering::TypeLowering &getTypeLowering(SILType type) const;

/// Returns true if this function has a calling convention that has a self
/// argument.
bool hasSelfParam() const {
Expand Down
5 changes: 2 additions & 3 deletions include/swift/SIL/SILInstruction.h
Original file line number Diff line number Diff line change
Expand Up @@ -6332,9 +6332,8 @@ class Copy##Name##ValueInst \
SingleValueInstruction> { \
friend class SILBuilder; \
Copy##Name##ValueInst(SILDebugLocation DebugLoc, SILValue operand, \
SILModule &M) \
: UnaryInstructionBase(DebugLoc, operand, \
operand->getType().getReferentType(M)) {} \
SILType type) \
: UnaryInstructionBase(DebugLoc, operand, type) {} \
};
#include "swift/AST/ReferenceStorage.def"

Expand Down
5 changes: 4 additions & 1 deletion include/swift/SIL/SILModule.h
Original file line number Diff line number Diff line change
Expand Up @@ -598,7 +598,10 @@ class SILModule {

/// Can value operations (copies and destroys) on the given lowered type
/// be performed in this module?
bool isTypeABIAccessible(SILType type);
// FIXME: Expansion
bool isTypeABIAccessible(SILType type,
ResilienceExpansion forExpansion
= ResilienceExpansion::Minimal);

/// Can type metadata for the given formal type be fetched in
/// the given module?
Expand Down
10 changes: 0 additions & 10 deletions include/swift/SIL/SILType.h
Original file line number Diff line number Diff line change
Expand Up @@ -477,12 +477,6 @@ class SILType {
/// representation. Class existentials do not always qualify.
bool isHeapObjectReferenceType() const;

/// Return the SILType corresponding to the underlying type of the given
/// metatype type.
///
/// *NOTE* Only call on SILTypes for metatype types.
SILType getMetatypeInstanceType(SILModule& M) const;

/// Returns true if this SILType is an aggregate that contains \p Ty
bool aggregateContainsRecord(SILType Ty, SILModule &SILMod) const;

Expand All @@ -501,10 +495,6 @@ class SILType {

/// Returns true if this is the AnyObject SILType;
bool isAnyObject() const { return getASTType()->isAnyObject(); }

/// Returns the underlying referent SILType of an @sil_unowned or @sil_weak
/// Type.
SILType getReferentType(SILModule &M) const;

/// Returns a SILType with any archetypes mapped out of context.
SILType mapTypeOutOfContext() const;
Expand Down
11 changes: 7 additions & 4 deletions include/swift/SIL/TypeLowering.h
Original file line number Diff line number Diff line change
Expand Up @@ -769,13 +769,16 @@ class TypeConverter {
ResilienceExpansion::Minimal);

// Returns the lowered SIL type for a Swift type.
SILType getLoweredType(Type t) {
return getTypeLowering(t, ResilienceExpansion::Minimal).getLoweredType();
SILType getLoweredType(Type t, ResilienceExpansion forExpansion
= ResilienceExpansion::Minimal) {
return getTypeLowering(t, forExpansion).getLoweredType();
}

// Returns the lowered SIL type for a Swift type.
SILType getLoweredType(AbstractionPattern origType, Type substType) {
return getTypeLowering(origType, substType, ResilienceExpansion::Minimal)
SILType getLoweredType(AbstractionPattern origType, Type substType,
ResilienceExpansion forExpansion =
ResilienceExpansion::Minimal) {
return getTypeLowering(origType, substType, forExpansion)
.getLoweredType();
}

Expand Down
13 changes: 8 additions & 5 deletions include/swift/SILOptimizer/Utils/Devirtualize.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class Emitter;
/// \p Subs a container to be used for storing the set of subclasses
void getAllSubclasses(ClassHierarchyAnalysis *CHA,
ClassDecl *CD,
SILType ClassType,
CanType ClassType,
SILModule &M,
ClassHierarchyAnalysis::ClassList &Subs);

Expand All @@ -69,18 +69,19 @@ ApplySite tryDevirtualizeApply(ApplySite AI,
ClassHierarchyAnalysis *CHA,
OptRemark::Emitter *ORE = nullptr);
bool canDevirtualizeApply(FullApplySite AI, ClassHierarchyAnalysis *CHA);
bool isNominalTypeWithUnboundGenericParameters(SILType Ty, SILModule &M);
bool canDevirtualizeClassMethod(FullApplySite AI, SILType ClassInstanceType,
bool canDevirtualizeClassMethod(FullApplySite AI, ClassDecl *CD,
OptRemark::Emitter *ORE = nullptr,
bool isEffectivelyFinalMethod = false);
SILFunction *getTargetClassMethod(SILModule &M, SILType ClassOrMetatypeType,
SILFunction *getTargetClassMethod(SILModule &M, ClassDecl *CD,
MethodInst *MI);
CanType getSelfInstanceType(CanType ClassOrMetatypeType);

/// Devirtualize the given apply site, which is known to be devirtualizable.
///
/// The caller must call deleteDevirtualizedApply on the original apply site.
FullApplySite devirtualizeClassMethod(FullApplySite AI,
SILValue ClassInstance,
ClassDecl *CD,
OptRemark::Emitter *ORE);

/// Attempt to devirtualize the given apply site, which is known to be
Expand All @@ -89,7 +90,9 @@ FullApplySite devirtualizeClassMethod(FullApplySite AI,
/// If this succeeds, the caller must call deleteDevirtualizedApply on
/// the original apply site.
FullApplySite
tryDevirtualizeClassMethod(FullApplySite AI, SILValue ClassInstance,
tryDevirtualizeClassMethod(FullApplySite AI,
SILValue ClassInstance,
ClassDecl *CD,
OptRemark::Emitter *ORE,
bool isEffectivelyFinalMethod = false);

Expand Down
5 changes: 0 additions & 5 deletions include/swift/SILOptimizer/Utils/Local.h
Original file line number Diff line number Diff line change
Expand Up @@ -522,11 +522,6 @@ bool simplifyUsers(SingleValueInstruction *I);
/// without a significant increase to code size.
bool shouldExpand(SILModule &Module, SILType Ty);

/// Check if a given type is a simple type, i.e. a builtin
/// integer or floating point type or a struct/tuple whose members
/// are of simple types.
bool isSimpleType(SILType SILTy, SILModule& Module);

/// Check if the value of V is computed by means of a simple initialization.
/// Store the actual SILValue into \p Val and the reversed list of instructions
/// initializing it in \p Insns.
Expand Down
4 changes: 2 additions & 2 deletions lib/IRGen/GenType.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1456,7 +1456,7 @@ llvm::PointerType *IRGenModule::getStoragePointerTypeForLowered(CanType T) {
}

llvm::Type *IRGenModule::getStorageTypeForUnlowered(Type subst) {
return getStorageType(getSILTypes().getLoweredType(subst));
return getStorageType(getLoweredType(subst));
}

llvm::Type *IRGenModule::getStorageType(SILType T) {
Expand Down Expand Up @@ -1486,7 +1486,7 @@ IRGenModule::getTypeInfoForUnlowered(AbstractionPattern orig, Type subst) {
/// have yet undergone SIL type lowering.
const TypeInfo &
IRGenModule::getTypeInfoForUnlowered(AbstractionPattern orig, CanType subst) {
return getTypeInfo(getSILTypes().getLoweredType(orig, subst));
return getTypeInfo(getLoweredType(orig, subst));
}

/// Get the fragile type information for the given type, which is known
Expand Down
4 changes: 2 additions & 2 deletions lib/IRGen/LoadableByAddress.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2221,8 +2221,8 @@ static void rewriteFunction(StructLoweringState &pass,
retBuilder.createStore(regLoc, retOp, retArg,
getStoreInitOwnership(pass, retOp->getType()));
}
auto emptyTy = retBuilder.getModule().Types.getLoweredType(
TupleType::getEmpty(retBuilder.getModule().getASTContext()));
auto emptyTy = SILType::getPrimitiveObjectType(
retBuilder.getModule().getASTContext().TheEmptyTupleType);
auto newRetTuple = retBuilder.createTuple(regLoc, emptyTy, {});
retBuilder.createReturn(newRetTuple->getLoc(), newRetTuple);
instr->eraseFromParent();
Expand Down
5 changes: 3 additions & 2 deletions lib/ParseSIL/ParseSIL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4767,8 +4767,9 @@ bool SILParser::parseSILInstruction(SILBuilder &B) {
= OpenedArchetypeType::get(Val->getType().getASTType())
->getCanonicalType();

SILType LoweredTy = SILMod.Types.getLoweredType(
Lowering::AbstractionPattern(archetype), Ty)
auto &F = B.getFunction();
SILType LoweredTy = F.getLoweredType(
Lowering::AbstractionPattern(archetype), Ty)
.getAddressType();

// Collect conformances for the type.
Expand Down
2 changes: 1 addition & 1 deletion lib/SIL/DynamicCasts.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -798,7 +798,7 @@ namespace {

private:
const TypeLowering &getTypeLowering(SILType type) {
return M.Types.getTypeLowering(type);
return B.getFunction().getTypeLowering(type);
}

SILValue getOwnedScalar(Source source, const TypeLowering &srcTL) {
Expand Down
9 changes: 7 additions & 2 deletions lib/SIL/OptimizationRemark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -58,9 +58,14 @@ Argument::Argument(StringRef Key, SILFunction *F)
Loc = F->getLocation().getSourceLoc();
}

Argument::Argument(StringRef Key, SILType *Ty) : Key(Key) {
Argument::Argument(StringRef Key, SILType Ty) : Key(Key) {
llvm::raw_string_ostream OS(Val);
Ty->print(OS);
Ty.print(OS);
}

Argument::Argument(StringRef Key, CanType Ty) : Key(Key) {
llvm::raw_string_ostream OS(Val);
Ty.print(OS);
}

template <typename DerivedT> std::string Remark<DerivedT>::getMsg() const {
Expand Down
5 changes: 3 additions & 2 deletions lib/SIL/SIL.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -185,9 +185,10 @@ static bool isTypeMetadataForLayoutAccessible(SILModule &M, SILType type) {
/// that are ABI-private to their defining module. But if the type is not
/// ABI-private, we can always at least fetch its metadata and use the
/// value witness table stored there.
bool SILModule::isTypeABIAccessible(SILType type) {
bool SILModule::isTypeABIAccessible(SILType type,
ResilienceExpansion forExpansion) {
// Fixed-ABI types can have value operations done without metadata.
if (Types.getTypeLowering(type).isFixedABI())
if (Types.getTypeLowering(type, forExpansion).isFixedABI())
return true;

assert(!type.is<ReferenceStorageType>() &&
Expand Down
37 changes: 37 additions & 0 deletions lib/SIL/SILFunction.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -226,6 +226,43 @@ bool SILFunction::isNoReturnFunction() const {
.isNoReturnFunction();
}

const TypeLowering &
SILFunction::getTypeLowering(AbstractionPattern orig, Type subst) {
// FIXME: Expansion
return getModule().Types.getTypeLowering(orig, subst,
ResilienceExpansion::Minimal);
}

const TypeLowering &SILFunction::getTypeLowering(Type t) const {
// FIXME: Expansion
return getModule().Types.getTypeLowering(t, ResilienceExpansion::Minimal);
}

SILType
SILFunction::getLoweredType(AbstractionPattern orig, Type subst) const {
// FIXME: Expansion
return getModule().Types.getLoweredType(orig, subst,
ResilienceExpansion::Minimal);
}

SILType SILFunction::getLoweredType(Type t) const {
// FIXME: Expansion
return getModule().Types.getLoweredType(t,
ResilienceExpansion::Minimal);
}

SILType SILFunction::getLoweredLoadableType(Type t) const {
// FIXME: Expansion
return getModule().Types.getLoweredLoadableType(t,
ResilienceExpansion::Minimal);
}

const TypeLowering &SILFunction::getTypeLowering(SILType type) const {
// FIXME: Expansion
return getModule().Types.getTypeLowering(type,
ResilienceExpansion::Minimal);
}

SILBasicBlock *SILFunction::createBasicBlock() {
return new (getModule()) SILBasicBlock(this, nullptr, false);
}
Expand Down
6 changes: 3 additions & 3 deletions lib/SIL/SILOpenedArchetypesTracker.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -62,20 +62,20 @@ bool SILOpenedArchetypesTracker::registerUsedOpenedArchetypes(CanType Ty) {
return;

auto *CurF = const_cast<SILFunction *>(this->getFunction());
auto &SILMod = CurF->getModule();

// Create a placeholder representing a forward definition.
// Add the placeholder at the beginning of the entry block.
SingleValueInstruction *Placeholder;
if (!CurF->getEntryBlock()->empty()) {
SILBuilder B(CurF->getEntryBlock()->begin());
Placeholder =
B.createGlobalAddr(ArtificialUnreachableLocation(),
SILMod.Types.getLoweredType(archetypeTy));
SILType::getPrimitiveAddressType(archetypeTy));
} else {
SILBuilder B(CurF->getEntryBlock());
Placeholder =
B.createGlobalAddr(ArtificialUnreachableLocation(),
SILMod.Types.getLoweredType(archetypeTy));
SILType::getPrimitiveAddressType(archetypeTy));
}
// Make it available to SILBuilder, so that instructions using this
// archetype can be constructed.
Expand Down
24 changes: 3 additions & 21 deletions lib/SIL/SILType.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -216,17 +216,6 @@ bool SILType::isHeapObjectReferenceType() const {
return false;
}

SILType SILType::getMetatypeInstanceType(SILModule &M) const {
CanType MetatypeType = getASTType();
assert(MetatypeType->is<AnyMetatypeType>() &&
"This method should only be called on SILTypes with an underlying "
"metatype type.");
Type instanceType =
MetatypeType->castTo<AnyMetatypeType>()->getInstanceType();

return M.Types.getLoweredType(instanceType->getCanonicalType());
}

bool SILType::aggregateContainsRecord(SILType Record, SILModule &Mod) const {
assert(!hasArchetype() && "Agg should be proven to not be generic "
"before passed to this function.");
Expand Down Expand Up @@ -395,11 +384,6 @@ SILType::canUseExistentialRepresentation(SILModule &M,
llvm_unreachable("Unhandled ExistentialRepresentation in switch.");
}

SILType SILType::getReferentType(SILModule &M) const {
auto Ty = castTo<ReferenceStorageType>();
return M.Types.getLoweredType(Ty->getReferentType()->getCanonicalType());
}

SILType SILType::mapTypeOutOfContext() const {
return SILType::getPrimitiveType(getASTType()->mapTypeOutOfContext()
->getCanonicalType(),
Expand Down Expand Up @@ -556,8 +540,7 @@ bool SILType::hasAbstractionDifference(SILFunctionTypeRepresentation rep,
bool SILType::isLoweringOf(SILModule &Mod, CanType formalType) {
SILType loweredType = *this;

// Optional lowers its contained type. The difference between Optional
// and IUO is lowered away.
// Optional lowers its contained type.
SILType loweredObjectType = loweredType.getOptionalObjectType();
CanType formalObjectType = formalType.getOptionalObjectType();

Expand All @@ -567,10 +550,9 @@ bool SILType::isLoweringOf(SILModule &Mod, CanType formalType) {
}

// Metatypes preserve their instance type through lowering.
if (loweredType.is<MetatypeType>()) {
if (auto loweredMT = loweredType.getAs<MetatypeType>()) {
if (auto formalMT = dyn_cast<MetatypeType>(formalType)) {
return loweredType.getMetatypeInstanceType(Mod).isLoweringOf(
Mod, formalMT.getInstanceType());
return loweredMT.getInstanceType() == formalMT.getInstanceType();
}
}

Expand Down
Loading