@@ -3045,35 +3045,47 @@ static void emitDelayedArguments(SILGenFunction &SGF,
30453045done:
30463046
30473047 if (defaultArgIsolation) {
3048- assert (SGF.F .isAsync ());
30493048 assert (!isolatedArgs.empty ());
30503049
3051- auto &firstArg = *std::get<0 >(isolatedArgs[0 ]);
3052- auto loc = firstArg.getDefaultArgLoc ();
3050+ // Only hop to the default arg isolation if the callee is async.
3051+ // If we're in a synchronous function, the isolation has to match,
3052+ // so no hop is required. This is enforced by the actor isolation
3053+ // checker.
3054+ //
3055+ // FIXME: Note that we don't end up in this situation for user-written
3056+ // synchronous functions, because the default argument is only considered
3057+ // isolated to the callee if the call crosses an isolation boundary. We
3058+ // do end up here for default argument generators and stored property
3059+ // initializers. An alternative (and better) approach is to formally model
3060+ // those generator functions as isolated.
3061+ if (SGF.F .isAsync ()) {
3062+ auto &firstArg = *std::get<0 >(isolatedArgs[0 ]);
3063+ auto loc = firstArg.getDefaultArgLoc ();
3064+
3065+ SILValue executor;
3066+ switch (*defaultArgIsolation) {
3067+ case ActorIsolation::GlobalActor:
3068+ executor = SGF.emitLoadGlobalActorExecutor (
3069+ defaultArgIsolation->getGlobalActor ());
3070+ break ;
30533071
3054- SILValue executor;
3055- switch (*defaultArgIsolation) {
3056- case ActorIsolation::GlobalActor:
3057- executor = SGF.emitLoadGlobalActorExecutor (
3058- defaultArgIsolation->getGlobalActor ());
3059- break ;
3072+ case ActorIsolation::ActorInstance:
3073+ llvm_unreachable (" default arg cannot be actor instance isolated" );
30603074
3061- case ActorIsolation::ActorInstance :
3062- llvm_unreachable (" default arg cannot be actor instance isolated " );
3075+ case ActorIsolation::Erased :
3076+ llvm_unreachable (" default arg cannot have erased isolation " );
30633077
3064- case ActorIsolation::Erased:
3065- llvm_unreachable (" default arg cannot have erased isolation" );
3078+ case ActorIsolation::Unspecified:
3079+ case ActorIsolation::Nonisolated:
3080+ case ActorIsolation::NonisolatedUnsafe:
3081+ llvm_unreachable (" Not isolated" );
3082+ }
30663083
3067- case ActorIsolation::Unspecified:
3068- case ActorIsolation::Nonisolated:
3069- case ActorIsolation::NonisolatedUnsafe:
3070- llvm_unreachable (" Not isolated" );
3084+ // Hop to the target isolation domain once to evaluate all
3085+ // default arguments.
3086+ SGF.emitHopToTargetExecutor (loc, executor);
30713087 }
30723088
3073- // Hop to the target isolation domain once to evaluate all
3074- // default arguments.
3075- SGF.emitHopToTargetExecutor (loc, executor);
3076-
30773089 size_t argsEmitted = 0 ;
30783090 for (auto &isolatedArg : isolatedArgs) {
30793091 auto &delayedArg = *std::get<0 >(isolatedArg);
0 commit comments