mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
Runtime/IRGen: Two-phase metadata initialization for resilient classes
Similar to the non-resilient case, except we also emit a 'relocation function'. The class descriptor now contains this relocation function if the class has resilient ancestry, and the relocation function calls the runtime's swift_relocateClassMetadata() entry point. The metadata completion function calls swift_initClassMetadata() and does layout, just like the non-resilient case. Fixes <rdar://problem/40810002>.
This commit is contained in:
@@ -3555,16 +3555,36 @@ IRGenModule::getAddrOfTypeMetadataInstantiationFunction(NominalTypeDecl *D,
|
||||
return entry;
|
||||
}
|
||||
|
||||
llvm::Type *argTys[] = {
|
||||
/// Type descriptor.
|
||||
TypeContextDescriptorPtrTy,
|
||||
/// Generic arguments.
|
||||
Int8PtrPtrTy,
|
||||
/// Generic metadata pattern.
|
||||
Int8PtrPtrTy
|
||||
};
|
||||
auto fnType = llvm::FunctionType::get(TypeMetadataPtrTy,
|
||||
argTys, /*isVarArg*/ false);
|
||||
// This function is used in two cases -- allocating generic type metadata,
|
||||
// and relocating non-generic resilient class metadata.
|
||||
llvm::FunctionType *fnType;
|
||||
|
||||
if (D->isGenericContext()) {
|
||||
// MetadataInstantiator in ABI/Metadata.h
|
||||
llvm::Type *argTys[] = {
|
||||
/// Type descriptor.
|
||||
TypeContextDescriptorPtrTy,
|
||||
/// Generic arguments.
|
||||
Int8PtrPtrTy,
|
||||
/// Generic metadata pattern.
|
||||
Int8PtrPtrTy
|
||||
};
|
||||
|
||||
fnType = llvm::FunctionType::get(TypeMetadataPtrTy, argTys,
|
||||
/*isVarArg*/ false);
|
||||
} else {
|
||||
assert(isa<ClassDecl>(D));
|
||||
|
||||
// MetadataRelocator in ABI/Metadata.h
|
||||
llvm::Type *argTys[] = {
|
||||
/// Type descriptor.
|
||||
TypeContextDescriptorPtrTy,
|
||||
};
|
||||
|
||||
fnType = llvm::FunctionType::get(TypeMetadataPtrTy, argTys,
|
||||
/*isVarArg*/ false);
|
||||
}
|
||||
|
||||
Signature signature(fnType, llvm::AttributeList(), DefaultCC);
|
||||
LinkInfo link = LinkInfo::get(*this, entity, forDefinition);
|
||||
entry = createFunction(*this, link, signature);
|
||||
|
||||
Reference in New Issue
Block a user