@@ -591,6 +591,10 @@ namespace {
591
591
// / function type.
592
592
void expandCoroutineContinuationType ();
593
593
594
+ // / Initializes the result type for functions with @guaranteed_addr return
595
+ // / convention.
596
+ void expandGuaranteedAddressResult ();
597
+
594
598
// Expand the components for the async continuation entrypoint of the
595
599
// function type (the function to be called on returning).
596
600
void expandAsyncReturnType ();
@@ -694,6 +698,10 @@ void SignatureExpansion::expandResult(
694
698
695
699
auto fnConv = getSILFuncConventions ();
696
700
701
+ if (fnConv.hasGuaranteedAddressResult ()) {
702
+ return expandGuaranteedAddressResult ();
703
+ }
704
+
697
705
// Disable the use of sret if we have multiple indirect results.
698
706
if (fnConv.getNumIndirectSILResults () > 1 )
699
707
CanUseSRet = false ;
@@ -911,6 +919,11 @@ void SignatureExpansion::expandCoroutineContinuationParameters() {
911
919
}
912
920
}
913
921
922
+ void SignatureExpansion::expandGuaranteedAddressResult () {
923
+ CanUseSRet = false ;
924
+ ResultIRType = IGM.PtrTy ;
925
+ }
926
+
914
927
void SignatureExpansion::addAsyncParameters () {
915
928
// using TaskContinuationFunction =
916
929
// SWIFT_CC(swift)
@@ -3945,6 +3958,11 @@ void CallEmission::emitYieldsToExplosion(Explosion &out) {
3945
3958
}
3946
3959
}
3947
3960
3961
+ void CallEmission::emitGuaranteedAddressToExplosion (Explosion &out) {
3962
+ auto call = emitCallSite ();
3963
+ out.add (call);
3964
+ }
3965
+
3948
3966
// / Emit the result of this call to an explosion.
3949
3967
void CallEmission::emitToExplosion (Explosion &out, bool isOutlined) {
3950
3968
assert (state == State::Emitting);
@@ -3960,6 +3978,14 @@ void CallEmission::emitToExplosion(Explosion &out, bool isOutlined) {
3960
3978
3961
3979
SILFunctionConventions fnConv (getCallee ().getSubstFunctionType (),
3962
3980
IGF.getSILModule ());
3981
+
3982
+ if (fnConv.hasGuaranteedAddressResult ()) {
3983
+ assert (LastArgWritten == 0 &&
3984
+ " @guaranteed_addr along with indirect result?" );
3985
+ emitGuaranteedAddressToExplosion (out);
3986
+ return ;
3987
+ }
3988
+
3963
3989
SILType substResultType =
3964
3990
fnConv.getSILResultType (IGF.IGM .getMaximalTypeExpansionContext ());
3965
3991
@@ -7019,6 +7045,16 @@ void irgen::emitYieldOnceCoroutineResult(IRGenFunction &IGF, Explosion &result,
7019
7045
}
7020
7046
}
7021
7047
7048
+ void irgen::emitGuaranteedAddressResult (IRGenFunction &IGF, Explosion &result,
7049
+ SILType funcResultType,
7050
+ SILType returnResultType) {
7051
+ assert (funcResultType == returnResultType);
7052
+ assert (funcResultType.isAddress ());
7053
+ auto &Builder = IGF.Builder ;
7054
+ Builder.CreateRet (result.claimNext ());
7055
+ assert (result.empty ());
7056
+ }
7057
+
7022
7058
FunctionPointer
7023
7059
IRGenFunction::getFunctionPointerForResumeIntrinsic (llvm::Value *resume) {
7024
7060
auto *fnTy = llvm::FunctionType::get (
0 commit comments