Skip to content

Commit c133e13

Browse files
authored
Merge pull request swiftlang#34916 from slavapestov/with-unsafe-continuation
Concurrency: Implement withUnsafe[Throwing]Continuation
2 parents 14ea0e5 + 9b3cd28 commit c133e13

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

43 files changed

+501
-188
lines changed

docs/ABI/Mangling.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -498,6 +498,7 @@ Types
498498
type ::= 'BO' // Builtin.UnknownObject (no longer a distinct type, but still used for AnyObject)
499499
type ::= 'Bo' // Builtin.NativeObject
500500
type ::= 'Bp' // Builtin.RawPointer
501+
type ::= 'Bc' // Builtin.RawUnsafeContinuation
501502
type ::= 'Bt' // Builtin.SILToken
502503
type ::= type 'Bv' NATURAL '_' // Builtin.Vec<n>x<type>
503504
type ::= 'Bw' // Builtin.Word

include/swift/AST/ASTContext.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -751,6 +751,7 @@ class ASTContext final {
751751
const CanType TheNativeObjectType; /// Builtin.NativeObject
752752
const CanType TheBridgeObjectType; /// Builtin.BridgeObject
753753
const CanType TheRawPointerType; /// Builtin.RawPointer
754+
const CanType TheRawUnsafeContinuationType; /// Builtin.RawUnsafeContinuation
754755
const CanType TheUnsafeValueBufferType; /// Builtin.UnsafeValueBuffer
755756
const CanType TheSILTokenType; /// Builtin.SILToken
756757
const CanType TheIntegerLiteralType; /// Builtin.IntegerLiteralType

include/swift/AST/Builtins.def

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -504,6 +504,20 @@ BUILTIN_SIL_OPERATION(DifferentiableFunction, "differentiableFunction", Special)
504504
/// linearFunction
505505
BUILTIN_SIL_OPERATION(LinearFunction, "linearFunction", Special)
506506

507+
/// withUnsafeContinuation<T> : (Builtin.RawUnsafeContinuation -> ()) async -> T
508+
///
509+
/// Unsafely capture the current continuation and pass it to the given
510+
/// function value. Returns a value of type T when the continuation is
511+
/// resumed.
512+
BUILTIN_SIL_OPERATION(WithUnsafeContinuation, "withUnsafeContinuation", Special)
513+
514+
/// withUnsafeThrowingContinuation<T> : (Builtin.RawUnsafeContinuation -> ()) async throws -> T
515+
///
516+
/// Unsafely capture the current continuation and pass it to the given
517+
/// function value. Returns a value of type T or throws an error when
518+
/// the continuation is resumed.
519+
BUILTIN_SIL_OPERATION(WithUnsafeThrowingContinuation, "withUnsafeThrowingContinuation", Special)
520+
507521
#undef BUILTIN_SIL_OPERATION
508522

509523
// BUILTIN_RUNTIME_CALL - A call into a runtime function.

include/swift/AST/TypeDifferenceVisitor.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,7 @@ class CanTypeDifferenceVisitor : public CanTypePairVisitor<Impl, bool> {
113113
}
114114
SINGLETON_TYPE(BuiltinIntegerLiteralType)
115115
SINGLETON_TYPE(BuiltinRawPointerType)
116+
SINGLETON_TYPE(BuiltinRawUnsafeContinuationType)
116117
SINGLETON_TYPE(BuiltinNativeObjectType)
117118
SINGLETON_TYPE(BuiltinBridgeObjectType)
118119
SINGLETON_TYPE(BuiltinUnsafeValueBufferType)

include/swift/AST/TypeMatcher.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,7 @@ class TypeMatcher {
105105
TRIVIAL_CASE(BuiltinIntegerLiteralType)
106106
TRIVIAL_CASE(BuiltinFloatType)
107107
TRIVIAL_CASE(BuiltinRawPointerType)
108+
TRIVIAL_CASE(BuiltinRawUnsafeContinuationType)
108109
TRIVIAL_CASE(BuiltinNativeObjectType)
109110
TRIVIAL_CASE(BuiltinBridgeObjectType)
110111
TRIVIAL_CASE(BuiltinUnsafeValueBufferType)

include/swift/AST/TypeNodes.def

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,7 @@ ABSTRACT_TYPE(Builtin, Type)
9797
TYPE_RANGE(AnyBuiltinInteger, BuiltinInteger, BuiltinIntegerLiteral)
9898
BUILTIN_TYPE(BuiltinFloat, BuiltinType)
9999
BUILTIN_TYPE(BuiltinRawPointer, BuiltinType)
100+
BUILTIN_TYPE(BuiltinRawUnsafeContinuation, BuiltinType)
100101
BUILTIN_TYPE(BuiltinNativeObject, BuiltinType)
101102
BUILTIN_TYPE(BuiltinBridgeObject, BuiltinType)
102103
BUILTIN_TYPE(BuiltinUnsafeValueBuffer, BuiltinType)

include/swift/AST/Types.h

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1391,6 +1391,20 @@ class BuiltinRawPointerType : public BuiltinType {
13911391
};
13921392
DEFINE_EMPTY_CAN_TYPE_WRAPPER(BuiltinRawPointerType, BuiltinType);
13931393

1394+
/// BuiltinRawContinuationType - The builtin raw unsafe continuation type.
1395+
/// This pointer is completely unmanaged, but is lowered with the same
1396+
/// spare bits as an opaque object-pointer type.
1397+
class BuiltinRawUnsafeContinuationType : public BuiltinType {
1398+
friend class ASTContext;
1399+
BuiltinRawUnsafeContinuationType(const ASTContext &C)
1400+
: BuiltinType(TypeKind::BuiltinRawUnsafeContinuation, C) {}
1401+
public:
1402+
static bool classof(const TypeBase *T) {
1403+
return T->getKind() == TypeKind::BuiltinRawUnsafeContinuation;
1404+
}
1405+
};
1406+
DEFINE_EMPTY_CAN_TYPE_WRAPPER(BuiltinRawUnsafeContinuationType, BuiltinType);
1407+
13941408
/// BuiltinNativeObjectType - The builtin opaque object-pointer type.
13951409
/// Useful for keeping an object alive when it is otherwise being
13961410
/// manipulated via an unsafe pointer type.

include/swift/SIL/SILBuilder.h

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1939,17 +1939,27 @@ class SILBuilder {
19391939
//===--------------------------------------------------------------------===//
19401940

19411941
GetAsyncContinuationInst *createGetAsyncContinuation(SILLocation Loc,
1942-
SILType ContinuationTy) {
1942+
CanType ResumeType,
1943+
bool Throws) {
1944+
auto ContinuationType = SILType::getPrimitiveObjectType(
1945+
getASTContext().TheRawUnsafeContinuationType);
19431946
return insert(new (getModule()) GetAsyncContinuationInst(getSILDebugLocation(Loc),
1944-
ContinuationTy));
1947+
ContinuationType,
1948+
ResumeType,
1949+
Throws));
19451950
}
19461951

19471952
GetAsyncContinuationAddrInst *createGetAsyncContinuationAddr(SILLocation Loc,
19481953
SILValue Operand,
1949-
SILType ContinuationTy) {
1954+
CanType ResumeType,
1955+
bool Throws) {
1956+
auto ContinuationType = SILType::getPrimitiveObjectType(
1957+
getASTContext().TheRawUnsafeContinuationType);
19501958
return insert(new (getModule()) GetAsyncContinuationAddrInst(getSILDebugLocation(Loc),
19511959
Operand,
1952-
ContinuationTy));
1960+
ContinuationType,
1961+
ResumeType,
1962+
Throws));
19531963
}
19541964

19551965
HopToExecutorInst *createHopToExecutor(SILLocation Loc, SILValue Actor) {

include/swift/SIL/SILCloner.h

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2961,7 +2961,8 @@ ::visitGetAsyncContinuationInst(GetAsyncContinuationInst *Inst) {
29612961
recordClonedInstruction(Inst,
29622962
getBuilder().createGetAsyncContinuation(
29632963
getOpLocation(Inst->getLoc()),
2964-
getOpType(Inst->getType())));
2964+
getOpASTType(Inst->getFormalResumeType()),
2965+
Inst->throws()));
29652966
}
29662967

29672968
template <typename ImplClass>
@@ -2972,7 +2973,8 @@ ::visitGetAsyncContinuationAddrInst(GetAsyncContinuationAddrInst *Inst) {
29722973
getBuilder().createGetAsyncContinuationAddr(
29732974
getOpLocation(Inst->getLoc()),
29742975
getOpValue(Inst->getOperand()),
2975-
getOpType(Inst->getType())));
2976+
getOpASTType(Inst->getFormalResumeType()),
2977+
Inst->throws()));
29762978
}
29772979

29782980
template <typename ImplClass>

include/swift/SIL/SILInstruction.h

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3244,15 +3244,22 @@ class GetAsyncContinuationInstBase
32443244
: public SingleValueInstruction
32453245
{
32463246
protected:
3247-
using SingleValueInstruction::SingleValueInstruction;
3248-
3247+
CanType ResumeType;
3248+
bool Throws;
3249+
3250+
GetAsyncContinuationInstBase(SILInstructionKind Kind, SILDebugLocation Loc,
3251+
SILType ContinuationType, CanType ResumeType,
3252+
bool Throws)
3253+
: SingleValueInstruction(Kind, Loc, ContinuationType),
3254+
ResumeType(ResumeType), Throws(Throws) {}
3255+
32493256
public:
32503257
/// Get the type of the value the async task receives on a resume.
3251-
CanType getFormalResumeType() const;
3258+
CanType getFormalResumeType() const { return ResumeType; }
32523259
SILType getLoweredResumeType() const;
32533260

32543261
/// True if the continuation can be used to resume the task by throwing an error.
3255-
bool throws() const;
3262+
bool throws() const { return Throws; }
32563263

32573264
static bool classof(const SILNode *I) {
32583265
return I->getKind() >= SILNodeKind::First_GetAsyncContinuationInstBase &&
@@ -3268,8 +3275,9 @@ class GetAsyncContinuationInst final
32683275
friend SILBuilder;
32693276

32703277
GetAsyncContinuationInst(SILDebugLocation Loc,
3271-
SILType ContinuationTy)
3272-
: InstructionBase(Loc, ContinuationTy)
3278+
SILType ContinuationType, CanType ResumeType,
3279+
bool Throws)
3280+
: InstructionBase(Loc, ContinuationType, ResumeType, Throws)
32733281
{}
32743282

32753283
public:
@@ -3289,9 +3297,10 @@ class GetAsyncContinuationAddrInst final
32893297
{
32903298
friend SILBuilder;
32913299
GetAsyncContinuationAddrInst(SILDebugLocation Loc,
3292-
SILValue Operand,
3293-
SILType ContinuationTy)
3294-
: UnaryInstructionBase(Loc, Operand, ContinuationTy)
3300+
SILValue ResumeBuf,
3301+
SILType ContinuationType, CanType ResumeType,
3302+
bool Throws)
3303+
: UnaryInstructionBase(Loc, ResumeBuf, ContinuationType, ResumeType, Throws)
32953304
{}
32963305
};
32973306

0 commit comments

Comments
 (0)