@@ -1095,6 +1095,9 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
10951095 auto valueTy = getLoweredTypeAndTypeInfo (IGF.IGM ,
10961096 substitutions.getReplacementTypes ()[0 ]);
10971097
1098+ // In Embedded Swift we don't have metadata and witness tables, so we can't
1099+ // just use TypeInfo's destroyArray, which needs metadata to emit a call to
1100+ // swift_arrayDestroy. Emit a loop to destroy elements directly instead.
10981101 if (IGF.IGM .Context .LangOpts .hasFeature (Feature::Embedded)) {
10991102 SILType elemTy = valueTy.first ;
11001103 const TypeInfo &elemTI = valueTy.second ;
@@ -1103,8 +1106,9 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11031106 IsTriviallyDestroyable)
11041107 return ;
11051108
1106- llvm::Value *firstElem = IGF.Builder .CreateBitCast (
1107- ptr, elemTI.getStorageType ()->getPointerTo ());
1109+ llvm::Value *firstElem =
1110+ IGF.Builder .CreatePtrToInt (IGF.Builder .CreateBitCast (
1111+ ptr, elemTI.getStorageType ()->getPointerTo ()), IGF.IGM .IntPtrTy );
11081112
11091113 auto *origBB = IGF.Builder .GetInsertBlock ();
11101114 auto *headerBB = IGF.createBasicBlock (" loop_header" );
@@ -1118,8 +1122,12 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11181122 IGF.Builder .CreateCondBr (cmp, loopBB, exitBB);
11191123
11201124 IGF.Builder .emitBlock (loopBB);
1121- auto *addr = IGF.Builder .CreateInBoundsGEP (elemTI.getStorageType (),
1122- firstElem, phi);
1125+
1126+ llvm::Value *offset =
1127+ IGF.Builder .CreateMul (phi, elemTI.getStaticStride (IGF.IGM ));
1128+ llvm::Value *added = IGF.Builder .CreateAdd (firstElem, offset);
1129+ llvm::Value *addr = IGF.Builder .CreateIntToPtr (
1130+ added, elemTI.getStorageType ()->getPointerTo ());
11231131
11241132 bool isOutlined = false ;
11251133 elemTI.destroy (IGF, elemTI.getAddressForPointer (addr), elemTy,
@@ -1168,6 +1176,9 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11681176 llvm::Value *src = args.claimNext ();
11691177 llvm::Value *count = args.claimNext ();
11701178
1179+ // In Embedded Swift we don't have metadata and witness tables, so we can't
1180+ // just use TypeInfo's initialize... and assign... APIs, which need
1181+ // metadata to emit calls. Emit a loop to process elements directly instead.
11711182 if (IGF.IGM .Context .LangOpts .hasFeature (Feature::Embedded)) {
11721183 auto tyPair = getLoweredTypeAndTypeInfo (
11731184 IGF.IGM , substitutions.getReplacementTypes ()[0 ]);
@@ -1183,10 +1194,14 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11831194 return ;
11841195 }
11851196
1186- llvm::Value *firstSrcElem = IGF.Builder .CreateBitCast (
1187- src, elemTI.getStorageType ()->getPointerTo ());
1188- llvm::Value *firstDestElem = IGF.Builder .CreateBitCast (
1189- dest, elemTI.getStorageType ()->getPointerTo ());
1197+ llvm::Value *firstSrcElem = IGF.Builder .CreatePtrToInt (
1198+ IGF.Builder .CreateBitCast (src,
1199+ elemTI.getStorageType ()->getPointerTo ()),
1200+ IGF.IGM .IntPtrTy );
1201+ llvm::Value *firstDestElem = IGF.Builder .CreatePtrToInt (
1202+ IGF.Builder .CreateBitCast (dest,
1203+ elemTI.getStorageType ()->getPointerTo ()),
1204+ IGF.IGM .IntPtrTy );
11901205
11911206 auto *origBB = IGF.Builder .GetInsertBlock ();
11921207 auto *headerBB = IGF.createBasicBlock (" loop_header" );
@@ -1214,10 +1229,16 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
12141229 break ;
12151230 }
12161231
1217- auto *srcElem = IGF.Builder .CreateInBoundsGEP (elemTI.getStorageType (),
1218- firstSrcElem, idx);
1219- auto *destElem = IGF.Builder .CreateInBoundsGEP (elemTI.getStorageType (),
1220- firstDestElem, idx);
1232+ llvm::Value *offset =
1233+ IGF.Builder .CreateMul (idx, elemTI.getStaticStride (IGF.IGM ));
1234+
1235+ llvm::Value *srcAdded = IGF.Builder .CreateAdd (firstSrcElem, offset);
1236+ auto *srcElem = IGF.Builder .CreateIntToPtr (
1237+ srcAdded, elemTI.getStorageType ()->getPointerTo ());
1238+ llvm::Value *dstAdded = IGF.Builder .CreateAdd (firstDestElem, offset);
1239+ auto *destElem = IGF.Builder .CreateIntToPtr (
1240+ dstAdded, elemTI.getStorageType ()->getPointerTo ());
1241+
12211242 Address destAddr = elemTI.getAddressForPointer (destElem);
12221243 Address srcAddr = elemTI.getAddressForPointer (srcElem);
12231244
0 commit comments