@@ -5728,6 +5728,8 @@ SILValue SILGenFunction::emitApplyWithRethrow(SILLocation loc, SILValue fn,
57285728 {
57295729 B.emitBlock (errorBB);
57305730
5731+ Scope scope (Cleanups, CleanupLocation (loc));
5732+
57315733 // Grab the inner error.
57325734 SILValue innerError;
57335735 bool hasInnerIndirectError = fnConv.hasIndirectSILErrorResults ();
@@ -5755,25 +5757,43 @@ SILValue SILGenFunction::emitApplyWithRethrow(SILLocation loc, SILValue fn,
57555757 outerError = innerError;
57565758 } else {
57575759 // The error requires some kind of translation.
5758-
5759- // Load the inner error, if it was returned indirectly.
5760- if (innerError->getType ().isAddress ()) {
5761- innerError = emitLoad (loc, innerError, getTypeLowering (innerErrorType),
5762- SGFContext (), IsTake).forward (*this );
5763- }
5760+ outerErrorType = outerErrorType.getObjectType ();
57645761
57655762 // If we need to convert the error type, do so now.
57665763 if (innerErrorType != outerErrorType) {
5767- auto conversion = Conversion::getOrigToSubst (
5768- AbstractionPattern (innerErrorType.getASTType ()),
5769- outerErrorType.getASTType (),
5770- outerErrorType);
5771- outerError = emitConvertedRValue (loc, conversion, SGFContext (),
5772- [innerError](SILGenFunction &SGF, SILLocation loc, SGFContext C) {
5773- return ManagedValue::forForwardedRValue (SGF, innerError);
5764+ assert (outerErrorType == SILType::getExceptionType (getASTContext ()));
5765+
5766+ ProtocolConformanceRef conformances[1 ] = {
5767+ getModule ().getSwiftModule ()->conformsToProtocol (
5768+ innerError->getType ().getASTType (),
5769+ getASTContext ().getErrorDecl ())
5770+ };
5771+
5772+ outerError = emitExistentialErasure (
5773+ loc,
5774+ innerErrorType.getASTType (),
5775+ getTypeLowering (innerErrorType),
5776+ getTypeLowering (outerErrorType),
5777+ getASTContext ().AllocateCopy (conformances),
5778+ SGFContext (),
5779+ [&](SGFContext C) -> ManagedValue {
5780+ if (innerError->getType ().isAddress ()) {
5781+ return emitLoad (loc, innerError,
5782+ getTypeLowering (innerErrorType), SGFContext (),
5783+ IsTake);
5784+ }
5785+
5786+ return ManagedValue::forForwardedRValue (*this , innerError);
57745787 }).forward (*this );
5788+ } else if (innerError->getType ().isAddress ()) {
5789+ // Load the inner error, if it was returned indirectly.
5790+ outerError = emitLoad (loc, innerError, getTypeLowering (innerErrorType),
5791+ SGFContext (), IsTake).forward (*this );
5792+ } else {
5793+ outerError = innerError;
57755794 }
57765795
5796+
57775797 // If the outer error is returned indirectly, copy from the converted
57785798 // inner error to the outer error slot.
57795799 if (IndirectErrorResult) {
0 commit comments