case 0x444: // vandc (And, AV p148)
DIP("vandc v%d,v%d,v%d\n", vD_addr, vA_addr, vB_addr);
- DIP(" => not implemented\n");
- return False;
+ putVReg( vD_addr, binop(Iop_AndV128, mkexpr(vA),
+ unop(Iop_NotV128, mkexpr(vB))) );
+ break;
case 0x484: // vor (Or, AV p217)
DIP("vor v%d,v%d,v%d\n", vD_addr, vA_addr, vB_addr);
case 0x504: // vnor (Nor, AV p216)
DIP("vnor v%d,v%d,v%d\n", vD_addr, vA_addr, vB_addr);
- DIP(" => not implemented\n");
- return False;
+ putVReg( vD_addr,
+ unop(Iop_NotV128, binop(Iop_OrV128, mkexpr(vA), mkexpr(vB))) );
+ break;
default:
vex_printf("dis_av_logic(PPC32)(opc2=0x%x)\n", opc2);
UChar SIMM_8 = extend_s_5to8(SIMM_5);
+ IRTemp vA = newTemp(Ity_V128);
+ IRTemp vB = newTemp(Ity_V128);
+ IRTemp vC = newTemp(Ity_V128);
+ assign( vA, getVReg(vA_addr));
+ assign( vB, getVReg(vB_addr));
+ assign( vC, getVReg(vC_addr));
+
if (opc1 != 0x4) {
vex_printf("dis_av_permute(PPC32)(instr)\n");
return False;
switch (opc2) {
case 0x2A: // vsel (Conditional Select, AV p238)
DIP("vsel v%d,v%d,v%d,v%d\n", vD_addr, vA_addr, vB_addr, vC_addr);
- DIP(" => not implemented\n");
- return False;
+ /* vD = (vA & ~vC) | (vB & vC) */
+ putVReg( vD_addr, binop(Iop_OrV128,
+ binop(Iop_AndV128, mkexpr(vA), unop(Iop_NotV128, mkexpr(vC))),
+ binop(Iop_AndV128, mkexpr(vB), mkexpr(vC))) );
+ return True;
case 0x2B: // vperm (Permute, AV p218)
DIP("vperm v%d,v%d,v%d,v%d\n", vD_addr, vA_addr, vB_addr, vC_addr);
}
if (e->tag == Iex_Get) {
+ /* Guest state vectors are 16byte aligned, so don't need to worry here */
HReg dst = newVRegV(env);
addInstr(env,
PPC32Instr_AvLdSt( True/*load*/, 16, dst,
return;
}
if (ty == Ity_V128) {
+ /* Guest state vectors are 16byte aligned, so don't need to worry here */
HReg v_src = iselVecExpr(env, stmt->Ist.Put.data);
PPC32AMode* am_addr = PPC32AMode_IR(stmt->Ist.Put.offset, GuestStatePtr);
addInstr(env, PPC32Instr_AvLdSt(False/*store*/, 16, v_src, am_addr));