| 1222 | static bool isBoolElem() { return ExprTypeIsBool<ELEM>::value; } |
| 1223 | |
| 1224 | void genCode(CppiaCompiler *compiler, const JitVal &inDest, ExprType destType) HXCPP_OVERRIDE |
| 1225 | { |
| 1226 | // TODO - null check |
| 1227 | switch(FUNC) |
| 1228 | { |
| 1229 | // Array<ELEM> |
| 1230 | case afPush: |
| 1231 | { |
| 1232 | thisExpr->genCode(compiler, sJitTemp0, etObject); |
| 1233 | JumpId enough = compiler->compare( cmpI_LESS, sJitTemp0.star(jtInt, ArrayBase::lengthOffset()), |
| 1234 | sJitTemp0.star(jtInt, ArrayBase::allocOffset()) ); |
| 1235 | |
| 1236 | // result comes back in sJitTemp0 |
| 1237 | compiler->callNative( (void *)array_expand, sJitTemp0 ); |
| 1238 | compiler->comeFrom(enough); |
| 1239 | |
| 1240 | JitTemp arrayThis(compiler,jtPointer); |
| 1241 | compiler->move(arrayThis, sJitTemp0); |
| 1242 | |
| 1243 | ExprType elemType = (ExprType)ExprTypeOf<ELEM>::value; |
| 1244 | JitTemp tempVal(compiler,getJitType(elemType)); |
| 1245 | args[0]->genCode(compiler, tempVal, elemType); |
| 1246 | |
| 1247 | // sJitTemp1 = this |
| 1248 | compiler->move(sJitTemp1, arrayThis); |
| 1249 | // sJitTemp0 = length |
| 1250 | compiler->move(sJitTemp0, sJitTemp1.star(jtInt, ArrayBase::lengthOffset()) ); |
| 1251 | // this->length = length+1 |
| 1252 | compiler->add(sJitTemp1.star(jtInt, ArrayBase::lengthOffset()), sJitTemp0, (int)1 ); |
| 1253 | |
| 1254 | JitTemp length(compiler, jtInt); |
| 1255 | if (destType!=etVoid) |
| 1256 | compiler->add(length, sJitTemp0, (int)1 ); |
| 1257 | |
| 1258 | #ifdef HXCPP_GC_GENERATIONAL |
| 1259 | if (hx::ContainsPointers<ELEM>()) |
| 1260 | compiler->move(sJitTemp2, sJitTemp1.as(jtPointer)); |
| 1261 | #endif |
| 1262 | |
| 1263 | // sJitTemp1 = this->base |
| 1264 | compiler->move(sJitTemp1, sJitTemp1.star(jtPointer, ArrayBase::baseOffset()).as(jtPointer) ); |
| 1265 | |
| 1266 | if (sizeof(ELEM)==1) // uchar, bool |
| 1267 | { |
| 1268 | compiler->move( sJitTemp1.atReg(sJitTemp0).as(jtByte), tempVal ); |
| 1269 | } |
| 1270 | else if (elemType==etString) |
| 1271 | { |
| 1272 | compiler->mult( sJitTemp0, sJitTemp0.as(jtInt), (int)sizeof(String), false ); |
| 1273 | compiler->add( sJitTemp0, sJitTemp1.as(jtPointer), sJitTemp0); |
| 1274 | |
| 1275 | compiler->move( sJitTemp0.star(jtInt), tempVal.as(jtInt) ); |
| 1276 | compiler->move( sJitTemp0.star(jtPointer,StringOffset::Ptr), tempVal.as(jtPointer) + StringOffset::Ptr ); |
| 1277 | #ifdef HXCPP_GC_GENERATIONAL |
| 1278 | genWriteBarrier(compiler, sJitTemp2, tempVal.as(jtPointer) + StringOffset::Ptr ); |
| 1279 | #endif |
| 1280 | } |
| 1281 | else if (sizeof(ELEM)==2) |
nothing calls this directly
no test coverage detected