mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-08-08 10:13:56 -06:00
target-ppc: convert 405 MAC instructions to TCG
Signed-off-by: Aurelien Jarno <aurelien@aurel32.net> git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5591 c046a42c-6fe2-441c-8c8c-71466251a162
This commit is contained in:
parent
7463740644
commit
182608d44c
4 changed files with 72 additions and 140 deletions
|
@ -5214,8 +5214,11 @@ static always_inline void gen_405_mulladd_insn (DisasContext *ctx,
|
|||
int opc2, int opc3,
|
||||
int ra, int rb, int rt, int Rc)
|
||||
{
|
||||
tcg_gen_mov_tl(cpu_T[0], cpu_gpr[ra]);
|
||||
tcg_gen_mov_tl(cpu_T[1], cpu_gpr[rb]);
|
||||
TCGv t0, t1;
|
||||
|
||||
t0 = tcg_temp_local_new(TCG_TYPE_TL);
|
||||
t1 = tcg_temp_local_new(TCG_TYPE_TL);
|
||||
|
||||
switch (opc3 & 0x0D) {
|
||||
case 0x05:
|
||||
/* macchw - macchw. - macchwo - macchwo. */
|
||||
|
@ -5223,13 +5226,17 @@ static always_inline void gen_405_mulladd_insn (DisasContext *ctx,
|
|||
/* nmacchw - nmacchw. - nmacchwo - nmacchwo. */
|
||||
/* nmacchws - nmacchws. - nmacchwso - nmacchwso. */
|
||||
/* mulchw - mulchw. */
|
||||
gen_op_405_mulchw();
|
||||
tcg_gen_ext16s_tl(t0, cpu_gpr[ra]);
|
||||
tcg_gen_sari_tl(t1, cpu_gpr[rb], 16);
|
||||
tcg_gen_ext16s_tl(t1, t1);
|
||||
break;
|
||||
case 0x04:
|
||||
/* macchwu - macchwu. - macchwuo - macchwuo. */
|
||||
/* macchwsu - macchwsu. - macchwsuo - macchwsuo. */
|
||||
/* mulchwu - mulchwu. */
|
||||
gen_op_405_mulchwu();
|
||||
tcg_gen_ext16u_tl(t0, cpu_gpr[ra]);
|
||||
tcg_gen_shri_tl(t1, cpu_gpr[rb], 16);
|
||||
tcg_gen_ext16u_tl(t1, t1);
|
||||
break;
|
||||
case 0x01:
|
||||
/* machhw - machhw. - machhwo - machhwo. */
|
||||
|
@ -5237,13 +5244,19 @@ static always_inline void gen_405_mulladd_insn (DisasContext *ctx,
|
|||
/* nmachhw - nmachhw. - nmachhwo - nmachhwo. */
|
||||
/* nmachhws - nmachhws. - nmachhwso - nmachhwso. */
|
||||
/* mulhhw - mulhhw. */
|
||||
gen_op_405_mulhhw();
|
||||
tcg_gen_sari_tl(t0, cpu_gpr[ra], 16);
|
||||
tcg_gen_ext16s_tl(t0, t0);
|
||||
tcg_gen_sari_tl(t1, cpu_gpr[rb], 16);
|
||||
tcg_gen_ext16s_tl(t1, t1);
|
||||
break;
|
||||
case 0x00:
|
||||
/* machhwu - machhwu. - machhwuo - machhwuo. */
|
||||
/* machhwsu - machhwsu. - machhwsuo - machhwsuo. */
|
||||
/* mulhhwu - mulhhwu. */
|
||||
gen_op_405_mulhhwu();
|
||||
tcg_gen_shri_tl(t0, cpu_gpr[ra], 16);
|
||||
tcg_gen_ext16u_tl(t0, t0);
|
||||
tcg_gen_shri_tl(t1, cpu_gpr[rb], 16);
|
||||
tcg_gen_ext16u_tl(t1, t1);
|
||||
break;
|
||||
case 0x0D:
|
||||
/* maclhw - maclhw. - maclhwo - maclhwo. */
|
||||
|
@ -5251,43 +5264,70 @@ static always_inline void gen_405_mulladd_insn (DisasContext *ctx,
|
|||
/* nmaclhw - nmaclhw. - nmaclhwo - nmaclhwo. */
|
||||
/* nmaclhws - nmaclhws. - nmaclhwso - nmaclhwso. */
|
||||
/* mullhw - mullhw. */
|
||||
gen_op_405_mullhw();
|
||||
tcg_gen_ext16s_tl(t0, cpu_gpr[ra]);
|
||||
tcg_gen_ext16s_tl(t1, cpu_gpr[rb]);
|
||||
break;
|
||||
case 0x0C:
|
||||
/* maclhwu - maclhwu. - maclhwuo - maclhwuo. */
|
||||
/* maclhwsu - maclhwsu. - maclhwsuo - maclhwsuo. */
|
||||
/* mullhwu - mullhwu. */
|
||||
gen_op_405_mullhwu();
|
||||
tcg_gen_ext16u_tl(t0, cpu_gpr[ra]);
|
||||
tcg_gen_ext16u_tl(t1, cpu_gpr[rb]);
|
||||
break;
|
||||
}
|
||||
if (opc2 & 0x02) {
|
||||
/* nmultiply-and-accumulate (0x0E) */
|
||||
tcg_gen_neg_tl(cpu_T[0], cpu_T[0]);
|
||||
}
|
||||
if (opc2 & 0x04) {
|
||||
/* (n)multiply-and-accumulate (0x0C - 0x0E) */
|
||||
tcg_gen_mov_tl(cpu_T[2], cpu_gpr[rt]);
|
||||
tcg_gen_mov_tl(cpu_T[1], cpu_T[0]);
|
||||
gen_op_405_add_T0_T2();
|
||||
/* (n)multiply-and-accumulate (0x0C / 0x0E) */
|
||||
tcg_gen_mul_tl(t1, t0, t1);
|
||||
if (opc2 & 0x02) {
|
||||
/* nmultiply-and-accumulate (0x0E) */
|
||||
tcg_gen_sub_tl(t0, cpu_gpr[rt], t1);
|
||||
} else {
|
||||
/* multiply-and-accumulate (0x0C) */
|
||||
tcg_gen_add_tl(t0, cpu_gpr[rt], t1);
|
||||
}
|
||||
|
||||
if (opc3 & 0x12) {
|
||||
/* Check overflow and/or saturate */
|
||||
int l1 = gen_new_label();
|
||||
|
||||
if (opc3 & 0x10) {
|
||||
/* Start with XER OV disabled, the most likely case */
|
||||
tcg_gen_andi_tl(cpu_xer, cpu_xer, ~(1 << XER_OV));
|
||||
}
|
||||
if (opc3 & 0x01) {
|
||||
/* Signed */
|
||||
tcg_gen_xor_tl(t1, cpu_gpr[rt], t1);
|
||||
tcg_gen_brcondi_tl(TCG_COND_GE, t1, 0, l1);
|
||||
tcg_gen_xor_tl(t1, cpu_gpr[rt], t0);
|
||||
tcg_gen_brcondi_tl(TCG_COND_LT, t1, 0, l1);
|
||||
if (opc3 & 0x02) {
|
||||
/* Saturate */
|
||||
tcg_gen_sari_tl(t0, cpu_gpr[rt], 31);
|
||||
tcg_gen_xori_tl(t0, t0, 0x7fffffff);
|
||||
}
|
||||
} else {
|
||||
/* Unsigned */
|
||||
tcg_gen_brcond_tl(TCG_COND_GEU, t0, t1, l1);
|
||||
if (opc3 & 0x02) {
|
||||
/* Saturate */
|
||||
tcg_gen_movi_tl(t0, UINT32_MAX);
|
||||
}
|
||||
}
|
||||
if (opc3 & 0x10) {
|
||||
/* Check overflow */
|
||||
tcg_gen_ori_tl(cpu_xer, cpu_xer, (1 << XER_OV) | (1 << XER_SO));
|
||||
}
|
||||
gen_set_label(l1);
|
||||
tcg_gen_mov_tl(cpu_gpr[rt], t0);
|
||||
}
|
||||
} else {
|
||||
tcg_gen_mul_tl(cpu_gpr[rt], t0, t1);
|
||||
}
|
||||
if (opc3 & 0x10) {
|
||||
/* Check overflow */
|
||||
if (opc3 & 0x01)
|
||||
gen_op_check_addo();
|
||||
else
|
||||
gen_op_405_check_ovu();
|
||||
}
|
||||
if (opc3 & 0x02) {
|
||||
/* Saturate */
|
||||
if (opc3 & 0x01)
|
||||
gen_op_405_check_sat();
|
||||
else
|
||||
gen_op_405_check_satu();
|
||||
}
|
||||
tcg_gen_mov_tl(cpu_gpr[rt], cpu_T[0]);
|
||||
tcg_temp_free(t0);
|
||||
tcg_temp_free(t1);
|
||||
if (unlikely(Rc) != 0) {
|
||||
/* Update Rc0 */
|
||||
gen_set_Rc0(ctx, cpu_T[0]);
|
||||
gen_set_Rc0(ctx, cpu_gpr[rt]);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue