@@ -141,7 +141,8 @@ static ManagedValue emitBuiltinUnpin(SILGenFunction &SGF,
141
141
142
142
if (requireIsOptionalNativeObject (SGF, loc, subs[0 ].getReplacement ())) {
143
143
// Unpinning takes responsibility for the +1 handle.
144
- SGF.B .createStrongUnpin (loc, args[0 ].forward (SGF), SGF.B .getDefaultAtomicity ());
144
+ SGF.B .createStrongUnpin (loc, args[0 ].ensurePlusOne (SGF, loc).forward (SGF),
145
+ SGF.B .getDefaultAtomicity ());
145
146
}
146
147
147
148
return ManagedValue::forUnmanaged (SGF.emitEmptyTuple (loc));
@@ -293,7 +294,7 @@ static ManagedValue emitBuiltinInit(SILGenFunction &SGF,
293
294
294
295
TemporaryInitialization init (addr, CleanupHandle::invalid ());
295
296
SGF.emitExprInto (args[0 ], &init);
296
-
297
+
297
298
return ManagedValue::forUnmanaged (SGF.emitEmptyTuple (loc));
298
299
}
299
300
@@ -544,14 +545,16 @@ emitBuiltinCastReference(SILGenFunction &SGF,
544
545
auto &toTL = SGF.getTypeLowering (toTy);
545
546
assert (!fromTL.isTrivial () && !toTL.isTrivial () && " expected ref type" );
546
547
547
- if (!fromTL.isAddress () || !toTL.isAddress ()) {
548
- if (auto refCast = SGF.B .tryCreateUncheckedRefCast (loc, args[0 ].getValue (),
548
+ // TODO: Fix this API.
549
+ if (!fromTL.isAddress () || !toTL.isAddress ()) {
550
+ if (auto refCast = SGF.B .tryCreateUncheckedRefCast (loc, args[0 ],
549
551
toTL.getLoweredType ())) {
550
552
// Create a reference cast, forwarding the cleanup.
551
553
// The cast takes the source reference.
552
- return ManagedValue ( refCast, args[ 0 ]. getCleanup ()) ;
554
+ return refCast;
553
555
}
554
556
}
557
+
555
558
// We are either casting between address-only types, or cannot promote to a
556
559
// cast of reference values.
557
560
//
@@ -563,7 +566,7 @@ emitBuiltinCastReference(SILGenFunction &SGF,
563
566
// TODO: For now, we leave invalid casts in address form so that the runtime
564
567
// will trap. We could emit a noreturn call here instead which would provide
565
568
// more information to the optimizer.
566
- SILValue srcVal = args[0 ].forward (SGF);
569
+ SILValue srcVal = args[0 ].ensurePlusOne (SGF, loc). forward (SGF);
567
570
SILValue fromAddr;
568
571
if (!fromTL.isAddress ()) {
569
572
// Move the loadable value into a "source temp". Since the source and
@@ -636,16 +639,17 @@ static ManagedValue emitBuiltinReinterpretCast(SILGenFunction &SGF,
636
639
});
637
640
}
638
641
// Create the appropriate bitcast based on the source and dest types.
639
- auto &in = args[0 ];
640
- SILValue out = SGF.B .createUncheckedBitCast (loc, in.getValue (),
641
- toTL.getLoweredType ());
642
+ ManagedValue in = args[0 ];
643
+ SILType resultTy = toTL.getLoweredType ();
644
+ if (resultTy.isTrivial (SGF.getModule ()))
645
+ return SGF.B .createUncheckedTrivialBitCast (loc, in, resultTy);
642
646
643
- // If the cast reduces to unchecked_ref_cast, then the source and dest
644
- // have identical cleanup, so just forward the cleanup as an optimization.
645
- if (isa<UncheckedRefCastInst>(out))
646
- return ManagedValue (out, in.getCleanup ());
647
+ // If we can perform a ref cast, just return.
648
+ if (auto refCast = SGF.B .tryCreateUncheckedRefCast (loc, in, resultTy))
649
+ return refCast;
647
650
648
651
// Otherwise leave the original cleanup and retain the cast value.
652
+ SILValue out = SGF.B .createUncheckedBitwiseCast (loc, in.getValue (), resultTy);
649
653
return SGF.emitManagedRetain (loc, out, toTL);
650
654
}
651
655
0 commit comments