qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Qemu-devel] [PATCH 09/14] i386: do not call helper to compute ZF/SF


From: Paolo Bonzini
Subject: [Qemu-devel] [PATCH 09/14] i386: do not call helper to compute ZF/SF
Date: Sat, 6 Oct 2012 14:30:16 +0200

ZF, SF and PF can always be computed from CC_DST except in the
CC_OP_EFLAGS case (and CC_OP_DYNAMIC, which just resolves to CC_OP_EFLAGS
in gen_compute_eflags).  Use setcond to compute ZF and SF.

We could also use a table lookup to compute PF.

Signed-off-by: Paolo Bonzini <address@hidden>
---
 target-i386/translate.c | 28 ++++++++++++++++++++++------
 1 file modificato, 22 inserzioni(+), 6 rimozioni(-)

diff --git a/target-i386/translate.c b/target-i386/translate.c
index 09512c3..daa36c1 100644
--- a/target-i386/translate.c
+++ b/target-i386/translate.c
@@ -859,9 +859,17 @@ static void gen_compute_eflags_p(DisasContext *s, TCGv reg)
 /* compute eflags.S to reg */
 static void gen_compute_eflags_s(DisasContext *s, TCGv reg)
 {
-    gen_compute_eflags(s);
-    tcg_gen_shri_tl(reg, cpu_cc_src, 7);
-    tcg_gen_andi_tl(reg, reg, 1);
+    if (s->cc_op == CC_OP_DYNAMIC) {
+        gen_compute_eflags(s);
+    }
+    if (s->cc_op == CC_OP_EFLAGS) {
+        tcg_gen_shri_tl(reg, cpu_cc_src, 7);
+        tcg_gen_andi_tl(reg, reg, 1);
+    } else {
+        int size = (s->cc_op - CC_OP_ADDB) & 3;
+        gen_ext_tl(reg, cpu_cc_dst, size, true);
+        tcg_gen_setcondi_tl(TCG_COND_LT, reg, reg, 0);
+    }
 }
 
 /* compute eflags.O to reg */
@@ -875,9 +883,17 @@ static void gen_compute_eflags_o(DisasContext *s, TCGv reg)
 /* compute eflags.Z to reg */
 static void gen_compute_eflags_z(DisasContext *s, TCGv reg)
 {
-    gen_compute_eflags(s);
-    tcg_gen_shri_tl(reg, cpu_cc_src, 6);
-    tcg_gen_andi_tl(reg, reg, 1);
+    if (s->cc_op == CC_OP_DYNAMIC) {
+        gen_compute_eflags(s);
+    }
+    if (s->cc_op == CC_OP_EFLAGS) {
+        tcg_gen_shri_tl(reg, cpu_cc_src, 6);
+        tcg_gen_andi_tl(reg, reg, 1);
+    } else {
+        int size = (s->cc_op - CC_OP_ADDB) & 3;
+        gen_ext_tl(reg, cpu_cc_dst, size, false);
+        tcg_gen_setcondi_tl(TCG_COND_EQ, reg, cpu_cc_dst, 0);
+    }
 }
 
 static inline void gen_setcc_slow_T0(DisasContext *s, int jcc_op)
-- 
1.7.12.1





reply via email to

[Prev in Thread] Current Thread [Next in Thread]