@@ -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,
@@ -1157,6 +1165,9 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11571165 llvm::Value *src = args.claimNext ();
11581166 llvm::Value *count = args.claimNext ();
11591167
1168+ // In Embedded Swift we don't have metadata and witness tables, so we can't
1169+ // just use TypeInfo's initialize... and assign... APIs, which need
1170+ // metadata to emit calls. Emit a loop to process elements directly instead.
11601171 if (IGF.IGM .Context .LangOpts .hasFeature (Feature::Embedded)) {
11611172 auto tyPair = getLoweredTypeAndTypeInfo (
11621173 IGF.IGM , substitutions.getReplacementTypes ()[0 ]);
@@ -1172,10 +1183,14 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
11721183 return ;
11731184 }
11741185
1175- llvm::Value *firstSrcElem = IGF.Builder .CreateBitCast (
1176- src, elemTI.getStorageType ()->getPointerTo ());
1177- llvm::Value *firstDestElem = IGF.Builder .CreateBitCast (
1178- dest, elemTI.getStorageType ()->getPointerTo ());
1186+ llvm::Value *firstSrcElem = IGF.Builder .CreatePtrToInt (
1187+ IGF.Builder .CreateBitCast (src,
1188+ elemTI.getStorageType ()->getPointerTo ()),
1189+ IGF.IGM .IntPtrTy );
1190+ llvm::Value *firstDestElem = IGF.Builder .CreatePtrToInt (
1191+ IGF.Builder .CreateBitCast (dest,
1192+ elemTI.getStorageType ()->getPointerTo ()),
1193+ IGF.IGM .IntPtrTy );
11791194
11801195 auto *origBB = IGF.Builder .GetInsertBlock ();
11811196 auto *headerBB = IGF.createBasicBlock (" loop_header" );
@@ -1203,10 +1218,16 @@ void irgen::emitBuiltinCall(IRGenFunction &IGF, const BuiltinInfo &Builtin,
12031218 break ;
12041219 }
12051220
1206- auto *srcElem = IGF.Builder .CreateInBoundsGEP (elemTI.getStorageType (),
1207- firstSrcElem, idx);
1208- auto *destElem = IGF.Builder .CreateInBoundsGEP (elemTI.getStorageType (),
1209- firstDestElem, idx);
1221+ llvm::Value *offset =
1222+ IGF.Builder .CreateMul (idx, elemTI.getStaticStride (IGF.IGM ));
1223+
1224+ llvm::Value *srcAdded = IGF.Builder .CreateAdd (firstSrcElem, offset);
1225+ auto *srcElem = IGF.Builder .CreateIntToPtr (
1226+ srcAdded, elemTI.getStorageType ()->getPointerTo ());
1227+ llvm::Value *dstAdded = IGF.Builder .CreateAdd (firstDestElem, offset);
1228+ auto *destElem = IGF.Builder .CreateIntToPtr (
1229+ dstAdded, elemTI.getStorageType ()->getPointerTo ());
1230+
12101231 Address destAddr = elemTI.getAddressForPointer (destElem);
12111232 Address srcAddr = elemTI.getAddressForPointer (srcElem);
12121233
0 commit comments