xref: /openbmc/qemu/target/i386/tcg/translate.c (revision c1dadb8462ff5021218f2c1aa015594952f441ca)
1 /*
2  *  i386 translation
3  *
4  *  Copyright (c) 2003 Fabrice Bellard
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
18  */
19 #include "qemu/osdep.h"
20 
21 #include "qemu/host-utils.h"
22 #include "cpu.h"
23 #include "disas/disas.h"
24 #include "exec/exec-all.h"
25 #include "tcg/tcg-op.h"
26 #include "tcg/tcg-op-gvec.h"
27 #include "exec/cpu_ldst.h"
28 #include "exec/translator.h"
29 
30 #include "exec/helper-proto.h"
31 #include "exec/helper-gen.h"
32 #include "helper-tcg.h"
33 
34 #include "exec/log.h"
35 
36 #define PREFIX_REPZ   0x01
37 #define PREFIX_REPNZ  0x02
38 #define PREFIX_LOCK   0x04
39 #define PREFIX_DATA   0x08
40 #define PREFIX_ADR    0x10
41 #define PREFIX_VEX    0x20
42 #define PREFIX_REX    0x40
43 
44 #ifdef TARGET_X86_64
45 # define ctztl  ctz64
46 # define clztl  clz64
47 #else
48 # define ctztl  ctz32
49 # define clztl  clz32
50 #endif
51 
52 /* For a switch indexed by MODRM, match all memory operands for a given OP.  */
53 #define CASE_MODRM_MEM_OP(OP) \
54     case (0 << 6) | (OP << 3) | 0 ... (0 << 6) | (OP << 3) | 7: \
55     case (1 << 6) | (OP << 3) | 0 ... (1 << 6) | (OP << 3) | 7: \
56     case (2 << 6) | (OP << 3) | 0 ... (2 << 6) | (OP << 3) | 7
57 
58 #define CASE_MODRM_OP(OP) \
59     case (0 << 6) | (OP << 3) | 0 ... (0 << 6) | (OP << 3) | 7: \
60     case (1 << 6) | (OP << 3) | 0 ... (1 << 6) | (OP << 3) | 7: \
61     case (2 << 6) | (OP << 3) | 0 ... (2 << 6) | (OP << 3) | 7: \
62     case (3 << 6) | (OP << 3) | 0 ... (3 << 6) | (OP << 3) | 7
63 
64 //#define MACRO_TEST   1
65 
66 /* global register indexes */
67 static TCGv cpu_cc_dst, cpu_cc_src, cpu_cc_src2;
68 static TCGv cpu_eip;
69 static TCGv_i32 cpu_cc_op;
70 static TCGv cpu_regs[CPU_NB_REGS];
71 static TCGv cpu_seg_base[6];
72 static TCGv_i64 cpu_bndl[4];
73 static TCGv_i64 cpu_bndu[4];
74 
75 #include "exec/gen-icount.h"
76 
77 typedef struct DisasContext {
78     DisasContextBase base;
79 
80     target_ulong pc;       /* pc = eip + cs_base */
81     target_ulong cs_base;  /* base of CS segment */
82     target_ulong pc_save;
83 
84     MemOp aflag;
85     MemOp dflag;
86 
87     int8_t override; /* -1 if no override, else R_CS, R_DS, etc */
88     uint8_t prefix;
89 
90     bool has_modrm;
91     uint8_t modrm;
92 
93 #ifndef CONFIG_USER_ONLY
94     uint8_t cpl;   /* code priv level */
95     uint8_t iopl;  /* i/o priv level */
96 #endif
97     uint8_t vex_l;  /* vex vector length */
98     uint8_t vex_v;  /* vex vvvv register, without 1's complement.  */
99     uint8_t popl_esp_hack; /* for correct popl with esp base handling */
100     uint8_t rip_offset; /* only used in x86_64, but left for simplicity */
101 
102 #ifdef TARGET_X86_64
103     uint8_t rex_r;
104     uint8_t rex_x;
105     uint8_t rex_b;
106 #endif
107     bool vex_w; /* used by AVX even on 32-bit processors */
108     bool jmp_opt; /* use direct block chaining for direct jumps */
109     bool repz_opt; /* optimize jumps within repz instructions */
110     bool cc_op_dirty;
111 
112     CCOp cc_op;  /* current CC operation */
113     int mem_index; /* select memory access functions */
114     uint32_t flags; /* all execution flags */
115     int cpuid_features;
116     int cpuid_ext_features;
117     int cpuid_ext2_features;
118     int cpuid_ext3_features;
119     int cpuid_7_0_ebx_features;
120     int cpuid_7_0_ecx_features;
121     int cpuid_xsave_features;
122 
123     /* TCG local temps */
124     TCGv cc_srcT;
125     TCGv A0;
126     TCGv T0;
127     TCGv T1;
128 
129     /* TCG local register indexes (only used inside old micro ops) */
130     TCGv tmp0;
131     TCGv tmp4;
132     TCGv_i32 tmp2_i32;
133     TCGv_i32 tmp3_i32;
134     TCGv_i64 tmp1_i64;
135 
136     sigjmp_buf jmpbuf;
137     TCGOp *prev_insn_end;
138 } DisasContext;
139 
140 #define DISAS_EOB_ONLY         DISAS_TARGET_0
141 #define DISAS_EOB_NEXT         DISAS_TARGET_1
142 #define DISAS_EOB_INHIBIT_IRQ  DISAS_TARGET_2
143 #define DISAS_JUMP             DISAS_TARGET_3
144 
145 /* The environment in which user-only runs is constrained. */
146 #ifdef CONFIG_USER_ONLY
147 #define PE(S)     true
148 #define CPL(S)    3
149 #define IOPL(S)   0
150 #define SVME(S)   false
151 #define GUEST(S)  false
152 #else
153 #define PE(S)     (((S)->flags & HF_PE_MASK) != 0)
154 #define CPL(S)    ((S)->cpl)
155 #define IOPL(S)   ((S)->iopl)
156 #define SVME(S)   (((S)->flags & HF_SVME_MASK) != 0)
157 #define GUEST(S)  (((S)->flags & HF_GUEST_MASK) != 0)
158 #endif
159 #if defined(CONFIG_USER_ONLY) && defined(TARGET_X86_64)
160 #define VM86(S)   false
161 #define CODE32(S) true
162 #define SS32(S)   true
163 #define ADDSEG(S) false
164 #else
165 #define VM86(S)   (((S)->flags & HF_VM_MASK) != 0)
166 #define CODE32(S) (((S)->flags & HF_CS32_MASK) != 0)
167 #define SS32(S)   (((S)->flags & HF_SS32_MASK) != 0)
168 #define ADDSEG(S) (((S)->flags & HF_ADDSEG_MASK) != 0)
169 #endif
170 #if !defined(TARGET_X86_64)
171 #define CODE64(S) false
172 #define LMA(S)    false
173 #elif defined(CONFIG_USER_ONLY)
174 #define CODE64(S) true
175 #define LMA(S)    true
176 #else
177 #define CODE64(S) (((S)->flags & HF_CS64_MASK) != 0)
178 #define LMA(S)    (((S)->flags & HF_LMA_MASK) != 0)
179 #endif
180 
181 #ifdef TARGET_X86_64
182 #define REX_PREFIX(S)  (((S)->prefix & PREFIX_REX) != 0)
183 #define REX_W(S)       ((S)->vex_w)
184 #define REX_R(S)       ((S)->rex_r + 0)
185 #define REX_X(S)       ((S)->rex_x + 0)
186 #define REX_B(S)       ((S)->rex_b + 0)
187 #else
188 #define REX_PREFIX(S)  false
189 #define REX_W(S)       false
190 #define REX_R(S)       0
191 #define REX_X(S)       0
192 #define REX_B(S)       0
193 #endif
194 
195 /*
196  * Many sysemu-only helpers are not reachable for user-only.
197  * Define stub generators here, so that we need not either sprinkle
198  * ifdefs through the translator, nor provide the helper function.
199  */
200 #define STUB_HELPER(NAME, ...) \
201     static inline void gen_helper_##NAME(__VA_ARGS__) \
202     { qemu_build_not_reached(); }
203 
204 #ifdef CONFIG_USER_ONLY
205 STUB_HELPER(clgi, TCGv_env env)
206 STUB_HELPER(flush_page, TCGv_env env, TCGv addr)
207 STUB_HELPER(hlt, TCGv_env env, TCGv_i32 pc_ofs)
208 STUB_HELPER(inb, TCGv ret, TCGv_env env, TCGv_i32 port)
209 STUB_HELPER(inw, TCGv ret, TCGv_env env, TCGv_i32 port)
210 STUB_HELPER(inl, TCGv ret, TCGv_env env, TCGv_i32 port)
211 STUB_HELPER(monitor, TCGv_env env, TCGv addr)
212 STUB_HELPER(mwait, TCGv_env env, TCGv_i32 pc_ofs)
213 STUB_HELPER(outb, TCGv_env env, TCGv_i32 port, TCGv_i32 val)
214 STUB_HELPER(outw, TCGv_env env, TCGv_i32 port, TCGv_i32 val)
215 STUB_HELPER(outl, TCGv_env env, TCGv_i32 port, TCGv_i32 val)
216 STUB_HELPER(rdmsr, TCGv_env env)
217 STUB_HELPER(read_crN, TCGv ret, TCGv_env env, TCGv_i32 reg)
218 STUB_HELPER(get_dr, TCGv ret, TCGv_env env, TCGv_i32 reg)
219 STUB_HELPER(set_dr, TCGv_env env, TCGv_i32 reg, TCGv val)
220 STUB_HELPER(stgi, TCGv_env env)
221 STUB_HELPER(svm_check_intercept, TCGv_env env, TCGv_i32 type)
222 STUB_HELPER(vmload, TCGv_env env, TCGv_i32 aflag)
223 STUB_HELPER(vmmcall, TCGv_env env)
224 STUB_HELPER(vmrun, TCGv_env env, TCGv_i32 aflag, TCGv_i32 pc_ofs)
225 STUB_HELPER(vmsave, TCGv_env env, TCGv_i32 aflag)
226 STUB_HELPER(write_crN, TCGv_env env, TCGv_i32 reg, TCGv val)
227 STUB_HELPER(wrmsr, TCGv_env env)
228 #endif
229 
230 static void gen_eob(DisasContext *s);
231 static void gen_jr(DisasContext *s);
232 static void gen_jmp_rel(DisasContext *s, MemOp ot, int diff, int tb_num);
233 static void gen_jmp_rel_csize(DisasContext *s, int diff, int tb_num);
234 static void gen_op(DisasContext *s1, int op, MemOp ot, int d);
235 static void gen_exception_gpf(DisasContext *s);
236 
237 /* i386 arith/logic operations */
238 enum {
239     OP_ADDL,
240     OP_ORL,
241     OP_ADCL,
242     OP_SBBL,
243     OP_ANDL,
244     OP_SUBL,
245     OP_XORL,
246     OP_CMPL,
247 };
248 
249 /* i386 shift ops */
250 enum {
251     OP_ROL,
252     OP_ROR,
253     OP_RCL,
254     OP_RCR,
255     OP_SHL,
256     OP_SHR,
257     OP_SHL1, /* undocumented */
258     OP_SAR = 7,
259 };
260 
261 enum {
262     JCC_O,
263     JCC_B,
264     JCC_Z,
265     JCC_BE,
266     JCC_S,
267     JCC_P,
268     JCC_L,
269     JCC_LE,
270 };
271 
272 enum {
273     /* I386 int registers */
274     OR_EAX,   /* MUST be even numbered */
275     OR_ECX,
276     OR_EDX,
277     OR_EBX,
278     OR_ESP,
279     OR_EBP,
280     OR_ESI,
281     OR_EDI,
282 
283     OR_TMP0 = 16,    /* temporary operand register */
284     OR_TMP1,
285     OR_A0, /* temporary register used when doing address evaluation */
286 };
287 
288 enum {
289     USES_CC_DST  = 1,
290     USES_CC_SRC  = 2,
291     USES_CC_SRC2 = 4,
292     USES_CC_SRCT = 8,
293 };
294 
295 /* Bit set if the global variable is live after setting CC_OP to X.  */
296 static const uint8_t cc_op_live[CC_OP_NB] = {
297     [CC_OP_DYNAMIC] = USES_CC_DST | USES_CC_SRC | USES_CC_SRC2,
298     [CC_OP_EFLAGS] = USES_CC_SRC,
299     [CC_OP_MULB ... CC_OP_MULQ] = USES_CC_DST | USES_CC_SRC,
300     [CC_OP_ADDB ... CC_OP_ADDQ] = USES_CC_DST | USES_CC_SRC,
301     [CC_OP_ADCB ... CC_OP_ADCQ] = USES_CC_DST | USES_CC_SRC | USES_CC_SRC2,
302     [CC_OP_SUBB ... CC_OP_SUBQ] = USES_CC_DST | USES_CC_SRC | USES_CC_SRCT,
303     [CC_OP_SBBB ... CC_OP_SBBQ] = USES_CC_DST | USES_CC_SRC | USES_CC_SRC2,
304     [CC_OP_LOGICB ... CC_OP_LOGICQ] = USES_CC_DST,
305     [CC_OP_INCB ... CC_OP_INCQ] = USES_CC_DST | USES_CC_SRC,
306     [CC_OP_DECB ... CC_OP_DECQ] = USES_CC_DST | USES_CC_SRC,
307     [CC_OP_SHLB ... CC_OP_SHLQ] = USES_CC_DST | USES_CC_SRC,
308     [CC_OP_SARB ... CC_OP_SARQ] = USES_CC_DST | USES_CC_SRC,
309     [CC_OP_BMILGB ... CC_OP_BMILGQ] = USES_CC_DST | USES_CC_SRC,
310     [CC_OP_ADCX] = USES_CC_DST | USES_CC_SRC,
311     [CC_OP_ADOX] = USES_CC_SRC | USES_CC_SRC2,
312     [CC_OP_ADCOX] = USES_CC_DST | USES_CC_SRC | USES_CC_SRC2,
313     [CC_OP_CLR] = 0,
314     [CC_OP_POPCNT] = USES_CC_SRC,
315 };
316 
317 static void set_cc_op(DisasContext *s, CCOp op)
318 {
319     int dead;
320 
321     if (s->cc_op == op) {
322         return;
323     }
324 
325     /* Discard CC computation that will no longer be used.  */
326     dead = cc_op_live[s->cc_op] & ~cc_op_live[op];
327     if (dead & USES_CC_DST) {
328         tcg_gen_discard_tl(cpu_cc_dst);
329     }
330     if (dead & USES_CC_SRC) {
331         tcg_gen_discard_tl(cpu_cc_src);
332     }
333     if (dead & USES_CC_SRC2) {
334         tcg_gen_discard_tl(cpu_cc_src2);
335     }
336     if (dead & USES_CC_SRCT) {
337         tcg_gen_discard_tl(s->cc_srcT);
338     }
339 
340     if (op == CC_OP_DYNAMIC) {
341         /* The DYNAMIC setting is translator only, and should never be
342            stored.  Thus we always consider it clean.  */
343         s->cc_op_dirty = false;
344     } else {
345         /* Discard any computed CC_OP value (see shifts).  */
346         if (s->cc_op == CC_OP_DYNAMIC) {
347             tcg_gen_discard_i32(cpu_cc_op);
348         }
349         s->cc_op_dirty = true;
350     }
351     s->cc_op = op;
352 }
353 
354 static void gen_update_cc_op(DisasContext *s)
355 {
356     if (s->cc_op_dirty) {
357         tcg_gen_movi_i32(cpu_cc_op, s->cc_op);
358         s->cc_op_dirty = false;
359     }
360 }
361 
362 #ifdef TARGET_X86_64
363 
364 #define NB_OP_SIZES 4
365 
366 #else /* !TARGET_X86_64 */
367 
368 #define NB_OP_SIZES 3
369 
370 #endif /* !TARGET_X86_64 */
371 
372 #if HOST_BIG_ENDIAN
373 #define REG_B_OFFSET (sizeof(target_ulong) - 1)
374 #define REG_H_OFFSET (sizeof(target_ulong) - 2)
375 #define REG_W_OFFSET (sizeof(target_ulong) - 2)
376 #define REG_L_OFFSET (sizeof(target_ulong) - 4)
377 #define REG_LH_OFFSET (sizeof(target_ulong) - 8)
378 #else
379 #define REG_B_OFFSET 0
380 #define REG_H_OFFSET 1
381 #define REG_W_OFFSET 0
382 #define REG_L_OFFSET 0
383 #define REG_LH_OFFSET 4
384 #endif
385 
386 /* In instruction encodings for byte register accesses the
387  * register number usually indicates "low 8 bits of register N";
388  * however there are some special cases where N 4..7 indicates
389  * [AH, CH, DH, BH], ie "bits 15..8 of register N-4". Return
390  * true for this special case, false otherwise.
391  */
392 static inline bool byte_reg_is_xH(DisasContext *s, int reg)
393 {
394     /* Any time the REX prefix is present, byte registers are uniform */
395     if (reg < 4 || REX_PREFIX(s)) {
396         return false;
397     }
398     return true;
399 }
400 
401 /* Select the size of a push/pop operation.  */
402 static inline MemOp mo_pushpop(DisasContext *s, MemOp ot)
403 {
404     if (CODE64(s)) {
405         return ot == MO_16 ? MO_16 : MO_64;
406     } else {
407         return ot;
408     }
409 }
410 
411 /* Select the size of the stack pointer.  */
412 static inline MemOp mo_stacksize(DisasContext *s)
413 {
414     return CODE64(s) ? MO_64 : SS32(s) ? MO_32 : MO_16;
415 }
416 
417 /* Select only size 64 else 32.  Used for SSE operand sizes.  */
418 static inline MemOp mo_64_32(MemOp ot)
419 {
420 #ifdef TARGET_X86_64
421     return ot == MO_64 ? MO_64 : MO_32;
422 #else
423     return MO_32;
424 #endif
425 }
426 
427 /* Select size 8 if lsb of B is clear, else OT.  Used for decoding
428    byte vs word opcodes.  */
429 static inline MemOp mo_b_d(int b, MemOp ot)
430 {
431     return b & 1 ? ot : MO_8;
432 }
433 
434 /* Select size 8 if lsb of B is clear, else OT capped at 32.
435    Used for decoding operand size of port opcodes.  */
436 static inline MemOp mo_b_d32(int b, MemOp ot)
437 {
438     return b & 1 ? (ot == MO_16 ? MO_16 : MO_32) : MO_8;
439 }
440 
441 static void gen_op_mov_reg_v(DisasContext *s, MemOp ot, int reg, TCGv t0)
442 {
443     switch(ot) {
444     case MO_8:
445         if (!byte_reg_is_xH(s, reg)) {
446             tcg_gen_deposit_tl(cpu_regs[reg], cpu_regs[reg], t0, 0, 8);
447         } else {
448             tcg_gen_deposit_tl(cpu_regs[reg - 4], cpu_regs[reg - 4], t0, 8, 8);
449         }
450         break;
451     case MO_16:
452         tcg_gen_deposit_tl(cpu_regs[reg], cpu_regs[reg], t0, 0, 16);
453         break;
454     case MO_32:
455         /* For x86_64, this sets the higher half of register to zero.
456            For i386, this is equivalent to a mov. */
457         tcg_gen_ext32u_tl(cpu_regs[reg], t0);
458         break;
459 #ifdef TARGET_X86_64
460     case MO_64:
461         tcg_gen_mov_tl(cpu_regs[reg], t0);
462         break;
463 #endif
464     default:
465         tcg_abort();
466     }
467 }
468 
469 static inline
470 void gen_op_mov_v_reg(DisasContext *s, MemOp ot, TCGv t0, int reg)
471 {
472     if (ot == MO_8 && byte_reg_is_xH(s, reg)) {
473         tcg_gen_extract_tl(t0, cpu_regs[reg - 4], 8, 8);
474     } else {
475         tcg_gen_mov_tl(t0, cpu_regs[reg]);
476     }
477 }
478 
479 static void gen_add_A0_im(DisasContext *s, int val)
480 {
481     tcg_gen_addi_tl(s->A0, s->A0, val);
482     if (!CODE64(s)) {
483         tcg_gen_ext32u_tl(s->A0, s->A0);
484     }
485 }
486 
487 static inline void gen_op_jmp_v(DisasContext *s, TCGv dest)
488 {
489     tcg_gen_mov_tl(cpu_eip, dest);
490     s->pc_save = -1;
491 }
492 
493 static inline
494 void gen_op_add_reg_im(DisasContext *s, MemOp size, int reg, int32_t val)
495 {
496     tcg_gen_addi_tl(s->tmp0, cpu_regs[reg], val);
497     gen_op_mov_reg_v(s, size, reg, s->tmp0);
498 }
499 
500 static inline void gen_op_add_reg_T0(DisasContext *s, MemOp size, int reg)
501 {
502     tcg_gen_add_tl(s->tmp0, cpu_regs[reg], s->T0);
503     gen_op_mov_reg_v(s, size, reg, s->tmp0);
504 }
505 
506 static inline void gen_op_ld_v(DisasContext *s, int idx, TCGv t0, TCGv a0)
507 {
508     tcg_gen_qemu_ld_tl(t0, a0, s->mem_index, idx | MO_LE);
509 }
510 
511 static inline void gen_op_st_v(DisasContext *s, int idx, TCGv t0, TCGv a0)
512 {
513     tcg_gen_qemu_st_tl(t0, a0, s->mem_index, idx | MO_LE);
514 }
515 
516 static inline void gen_op_st_rm_T0_A0(DisasContext *s, int idx, int d)
517 {
518     if (d == OR_TMP0) {
519         gen_op_st_v(s, idx, s->T0, s->A0);
520     } else {
521         gen_op_mov_reg_v(s, idx, d, s->T0);
522     }
523 }
524 
525 static void gen_update_eip_cur(DisasContext *s)
526 {
527     assert(s->pc_save != -1);
528     if (TARGET_TB_PCREL) {
529         tcg_gen_addi_tl(cpu_eip, cpu_eip, s->base.pc_next - s->pc_save);
530     } else {
531         tcg_gen_movi_tl(cpu_eip, s->base.pc_next - s->cs_base);
532     }
533     s->pc_save = s->base.pc_next;
534 }
535 
536 static void gen_update_eip_next(DisasContext *s)
537 {
538     assert(s->pc_save != -1);
539     if (TARGET_TB_PCREL) {
540         tcg_gen_addi_tl(cpu_eip, cpu_eip, s->pc - s->pc_save);
541     } else {
542         tcg_gen_movi_tl(cpu_eip, s->pc - s->cs_base);
543     }
544     s->pc_save = s->pc;
545 }
546 
547 static int cur_insn_len(DisasContext *s)
548 {
549     return s->pc - s->base.pc_next;
550 }
551 
552 static TCGv_i32 cur_insn_len_i32(DisasContext *s)
553 {
554     return tcg_constant_i32(cur_insn_len(s));
555 }
556 
557 static TCGv_i32 eip_next_i32(DisasContext *s)
558 {
559     assert(s->pc_save != -1);
560     /*
561      * This function has two users: lcall_real (always 16-bit mode), and
562      * iret_protected (16, 32, or 64-bit mode).  IRET only uses the value
563      * when EFLAGS.NT is set, which is illegal in 64-bit mode, which is
564      * why passing a 32-bit value isn't broken.  To avoid using this where
565      * we shouldn't, return -1 in 64-bit mode so that execution goes into
566      * the weeds quickly.
567      */
568     if (CODE64(s)) {
569         return tcg_constant_i32(-1);
570     }
571     if (TARGET_TB_PCREL) {
572         TCGv_i32 ret = tcg_temp_new_i32();
573         tcg_gen_trunc_tl_i32(ret, cpu_eip);
574         tcg_gen_addi_i32(ret, ret, s->pc - s->pc_save);
575         return ret;
576     } else {
577         return tcg_constant_i32(s->pc - s->cs_base);
578     }
579 }
580 
581 static TCGv eip_next_tl(DisasContext *s)
582 {
583     assert(s->pc_save != -1);
584     if (TARGET_TB_PCREL) {
585         TCGv ret = tcg_temp_new();
586         tcg_gen_addi_tl(ret, cpu_eip, s->pc - s->pc_save);
587         return ret;
588     } else {
589         return tcg_constant_tl(s->pc - s->cs_base);
590     }
591 }
592 
593 static TCGv eip_cur_tl(DisasContext *s)
594 {
595     assert(s->pc_save != -1);
596     if (TARGET_TB_PCREL) {
597         TCGv ret = tcg_temp_new();
598         tcg_gen_addi_tl(ret, cpu_eip, s->base.pc_next - s->pc_save);
599         return ret;
600     } else {
601         return tcg_constant_tl(s->base.pc_next - s->cs_base);
602     }
603 }
604 
605 /* Compute SEG:REG into A0.  SEG is selected from the override segment
606    (OVR_SEG) and the default segment (DEF_SEG).  OVR_SEG may be -1 to
607    indicate no override.  */
608 static void gen_lea_v_seg(DisasContext *s, MemOp aflag, TCGv a0,
609                           int def_seg, int ovr_seg)
610 {
611     switch (aflag) {
612 #ifdef TARGET_X86_64
613     case MO_64:
614         if (ovr_seg < 0) {
615             tcg_gen_mov_tl(s->A0, a0);
616             return;
617         }
618         break;
619 #endif
620     case MO_32:
621         /* 32 bit address */
622         if (ovr_seg < 0 && ADDSEG(s)) {
623             ovr_seg = def_seg;
624         }
625         if (ovr_seg < 0) {
626             tcg_gen_ext32u_tl(s->A0, a0);
627             return;
628         }
629         break;
630     case MO_16:
631         /* 16 bit address */
632         tcg_gen_ext16u_tl(s->A0, a0);
633         a0 = s->A0;
634         if (ovr_seg < 0) {
635             if (ADDSEG(s)) {
636                 ovr_seg = def_seg;
637             } else {
638                 return;
639             }
640         }
641         break;
642     default:
643         tcg_abort();
644     }
645 
646     if (ovr_seg >= 0) {
647         TCGv seg = cpu_seg_base[ovr_seg];
648 
649         if (aflag == MO_64) {
650             tcg_gen_add_tl(s->A0, a0, seg);
651         } else if (CODE64(s)) {
652             tcg_gen_ext32u_tl(s->A0, a0);
653             tcg_gen_add_tl(s->A0, s->A0, seg);
654         } else {
655             tcg_gen_add_tl(s->A0, a0, seg);
656             tcg_gen_ext32u_tl(s->A0, s->A0);
657         }
658     }
659 }
660 
661 static inline void gen_string_movl_A0_ESI(DisasContext *s)
662 {
663     gen_lea_v_seg(s, s->aflag, cpu_regs[R_ESI], R_DS, s->override);
664 }
665 
666 static inline void gen_string_movl_A0_EDI(DisasContext *s)
667 {
668     gen_lea_v_seg(s, s->aflag, cpu_regs[R_EDI], R_ES, -1);
669 }
670 
671 static inline void gen_op_movl_T0_Dshift(DisasContext *s, MemOp ot)
672 {
673     tcg_gen_ld32s_tl(s->T0, cpu_env, offsetof(CPUX86State, df));
674     tcg_gen_shli_tl(s->T0, s->T0, ot);
675 };
676 
677 static TCGv gen_ext_tl(TCGv dst, TCGv src, MemOp size, bool sign)
678 {
679     switch (size) {
680     case MO_8:
681         if (sign) {
682             tcg_gen_ext8s_tl(dst, src);
683         } else {
684             tcg_gen_ext8u_tl(dst, src);
685         }
686         return dst;
687     case MO_16:
688         if (sign) {
689             tcg_gen_ext16s_tl(dst, src);
690         } else {
691             tcg_gen_ext16u_tl(dst, src);
692         }
693         return dst;
694 #ifdef TARGET_X86_64
695     case MO_32:
696         if (sign) {
697             tcg_gen_ext32s_tl(dst, src);
698         } else {
699             tcg_gen_ext32u_tl(dst, src);
700         }
701         return dst;
702 #endif
703     default:
704         return src;
705     }
706 }
707 
708 static void gen_extu(MemOp ot, TCGv reg)
709 {
710     gen_ext_tl(reg, reg, ot, false);
711 }
712 
713 static void gen_exts(MemOp ot, TCGv reg)
714 {
715     gen_ext_tl(reg, reg, ot, true);
716 }
717 
718 static void gen_op_j_ecx(DisasContext *s, TCGCond cond, TCGLabel *label1)
719 {
720     tcg_gen_mov_tl(s->tmp0, cpu_regs[R_ECX]);
721     gen_extu(s->aflag, s->tmp0);
722     tcg_gen_brcondi_tl(cond, s->tmp0, 0, label1);
723 }
724 
725 static inline void gen_op_jz_ecx(DisasContext *s, TCGLabel *label1)
726 {
727     gen_op_j_ecx(s, TCG_COND_EQ, label1);
728 }
729 
730 static inline void gen_op_jnz_ecx(DisasContext *s, TCGLabel *label1)
731 {
732     gen_op_j_ecx(s, TCG_COND_NE, label1);
733 }
734 
735 static void gen_helper_in_func(MemOp ot, TCGv v, TCGv_i32 n)
736 {
737     switch (ot) {
738     case MO_8:
739         gen_helper_inb(v, cpu_env, n);
740         break;
741     case MO_16:
742         gen_helper_inw(v, cpu_env, n);
743         break;
744     case MO_32:
745         gen_helper_inl(v, cpu_env, n);
746         break;
747     default:
748         tcg_abort();
749     }
750 }
751 
752 static void gen_helper_out_func(MemOp ot, TCGv_i32 v, TCGv_i32 n)
753 {
754     switch (ot) {
755     case MO_8:
756         gen_helper_outb(cpu_env, v, n);
757         break;
758     case MO_16:
759         gen_helper_outw(cpu_env, v, n);
760         break;
761     case MO_32:
762         gen_helper_outl(cpu_env, v, n);
763         break;
764     default:
765         tcg_abort();
766     }
767 }
768 
769 /*
770  * Validate that access to [port, port + 1<<ot) is allowed.
771  * Raise #GP, or VMM exit if not.
772  */
773 static bool gen_check_io(DisasContext *s, MemOp ot, TCGv_i32 port,
774                          uint32_t svm_flags)
775 {
776 #ifdef CONFIG_USER_ONLY
777     /*
778      * We do not implement the ioperm(2) syscall, so the TSS check
779      * will always fail.
780      */
781     gen_exception_gpf(s);
782     return false;
783 #else
784     if (PE(s) && (CPL(s) > IOPL(s) || VM86(s))) {
785         gen_helper_check_io(cpu_env, port, tcg_constant_i32(1 << ot));
786     }
787     if (GUEST(s)) {
788         gen_update_cc_op(s);
789         gen_update_eip_cur(s);
790         if (s->prefix & (PREFIX_REPZ | PREFIX_REPNZ)) {
791             svm_flags |= SVM_IOIO_REP_MASK;
792         }
793         svm_flags |= 1 << (SVM_IOIO_SIZE_SHIFT + ot);
794         gen_helper_svm_check_io(cpu_env, port,
795                                 tcg_constant_i32(svm_flags),
796                                 cur_insn_len_i32(s));
797     }
798     return true;
799 #endif
800 }
801 
802 static void gen_movs(DisasContext *s, MemOp ot)
803 {
804     gen_string_movl_A0_ESI(s);
805     gen_op_ld_v(s, ot, s->T0, s->A0);
806     gen_string_movl_A0_EDI(s);
807     gen_op_st_v(s, ot, s->T0, s->A0);
808     gen_op_movl_T0_Dshift(s, ot);
809     gen_op_add_reg_T0(s, s->aflag, R_ESI);
810     gen_op_add_reg_T0(s, s->aflag, R_EDI);
811 }
812 
813 static void gen_op_update1_cc(DisasContext *s)
814 {
815     tcg_gen_mov_tl(cpu_cc_dst, s->T0);
816 }
817 
818 static void gen_op_update2_cc(DisasContext *s)
819 {
820     tcg_gen_mov_tl(cpu_cc_src, s->T1);
821     tcg_gen_mov_tl(cpu_cc_dst, s->T0);
822 }
823 
824 static void gen_op_update3_cc(DisasContext *s, TCGv reg)
825 {
826     tcg_gen_mov_tl(cpu_cc_src2, reg);
827     tcg_gen_mov_tl(cpu_cc_src, s->T1);
828     tcg_gen_mov_tl(cpu_cc_dst, s->T0);
829 }
830 
831 static inline void gen_op_testl_T0_T1_cc(DisasContext *s)
832 {
833     tcg_gen_and_tl(cpu_cc_dst, s->T0, s->T1);
834 }
835 
836 static void gen_op_update_neg_cc(DisasContext *s)
837 {
838     tcg_gen_mov_tl(cpu_cc_dst, s->T0);
839     tcg_gen_neg_tl(cpu_cc_src, s->T0);
840     tcg_gen_movi_tl(s->cc_srcT, 0);
841 }
842 
843 /* compute all eflags to cc_src */
844 static void gen_compute_eflags(DisasContext *s)
845 {
846     TCGv zero, dst, src1, src2;
847     int live, dead;
848 
849     if (s->cc_op == CC_OP_EFLAGS) {
850         return;
851     }
852     if (s->cc_op == CC_OP_CLR) {
853         tcg_gen_movi_tl(cpu_cc_src, CC_Z | CC_P);
854         set_cc_op(s, CC_OP_EFLAGS);
855         return;
856     }
857 
858     zero = NULL;
859     dst = cpu_cc_dst;
860     src1 = cpu_cc_src;
861     src2 = cpu_cc_src2;
862 
863     /* Take care to not read values that are not live.  */
864     live = cc_op_live[s->cc_op] & ~USES_CC_SRCT;
865     dead = live ^ (USES_CC_DST | USES_CC_SRC | USES_CC_SRC2);
866     if (dead) {
867         zero = tcg_const_tl(0);
868         if (dead & USES_CC_DST) {
869             dst = zero;
870         }
871         if (dead & USES_CC_SRC) {
872             src1 = zero;
873         }
874         if (dead & USES_CC_SRC2) {
875             src2 = zero;
876         }
877     }
878 
879     gen_update_cc_op(s);
880     gen_helper_cc_compute_all(cpu_cc_src, dst, src1, src2, cpu_cc_op);
881     set_cc_op(s, CC_OP_EFLAGS);
882 
883     if (dead) {
884         tcg_temp_free(zero);
885     }
886 }
887 
888 typedef struct CCPrepare {
889     TCGCond cond;
890     TCGv reg;
891     TCGv reg2;
892     target_ulong imm;
893     target_ulong mask;
894     bool use_reg2;
895     bool no_setcond;
896 } CCPrepare;
897 
898 /* compute eflags.C to reg */
899 static CCPrepare gen_prepare_eflags_c(DisasContext *s, TCGv reg)
900 {
901     TCGv t0, t1;
902     int size, shift;
903 
904     switch (s->cc_op) {
905     case CC_OP_SUBB ... CC_OP_SUBQ:
906         /* (DATA_TYPE)CC_SRCT < (DATA_TYPE)CC_SRC */
907         size = s->cc_op - CC_OP_SUBB;
908         t1 = gen_ext_tl(s->tmp0, cpu_cc_src, size, false);
909         /* If no temporary was used, be careful not to alias t1 and t0.  */
910         t0 = t1 == cpu_cc_src ? s->tmp0 : reg;
911         tcg_gen_mov_tl(t0, s->cc_srcT);
912         gen_extu(size, t0);
913         goto add_sub;
914 
915     case CC_OP_ADDB ... CC_OP_ADDQ:
916         /* (DATA_TYPE)CC_DST < (DATA_TYPE)CC_SRC */
917         size = s->cc_op - CC_OP_ADDB;
918         t1 = gen_ext_tl(s->tmp0, cpu_cc_src, size, false);
919         t0 = gen_ext_tl(reg, cpu_cc_dst, size, false);
920     add_sub:
921         return (CCPrepare) { .cond = TCG_COND_LTU, .reg = t0,
922                              .reg2 = t1, .mask = -1, .use_reg2 = true };
923 
924     case CC_OP_LOGICB ... CC_OP_LOGICQ:
925     case CC_OP_CLR:
926     case CC_OP_POPCNT:
927         return (CCPrepare) { .cond = TCG_COND_NEVER, .mask = -1 };
928 
929     case CC_OP_INCB ... CC_OP_INCQ:
930     case CC_OP_DECB ... CC_OP_DECQ:
931         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
932                              .mask = -1, .no_setcond = true };
933 
934     case CC_OP_SHLB ... CC_OP_SHLQ:
935         /* (CC_SRC >> (DATA_BITS - 1)) & 1 */
936         size = s->cc_op - CC_OP_SHLB;
937         shift = (8 << size) - 1;
938         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
939                              .mask = (target_ulong)1 << shift };
940 
941     case CC_OP_MULB ... CC_OP_MULQ:
942         return (CCPrepare) { .cond = TCG_COND_NE,
943                              .reg = cpu_cc_src, .mask = -1 };
944 
945     case CC_OP_BMILGB ... CC_OP_BMILGQ:
946         size = s->cc_op - CC_OP_BMILGB;
947         t0 = gen_ext_tl(reg, cpu_cc_src, size, false);
948         return (CCPrepare) { .cond = TCG_COND_EQ, .reg = t0, .mask = -1 };
949 
950     case CC_OP_ADCX:
951     case CC_OP_ADCOX:
952         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_dst,
953                              .mask = -1, .no_setcond = true };
954 
955     case CC_OP_EFLAGS:
956     case CC_OP_SARB ... CC_OP_SARQ:
957         /* CC_SRC & 1 */
958         return (CCPrepare) { .cond = TCG_COND_NE,
959                              .reg = cpu_cc_src, .mask = CC_C };
960 
961     default:
962        /* The need to compute only C from CC_OP_DYNAMIC is important
963           in efficiently implementing e.g. INC at the start of a TB.  */
964        gen_update_cc_op(s);
965        gen_helper_cc_compute_c(reg, cpu_cc_dst, cpu_cc_src,
966                                cpu_cc_src2, cpu_cc_op);
967        return (CCPrepare) { .cond = TCG_COND_NE, .reg = reg,
968                             .mask = -1, .no_setcond = true };
969     }
970 }
971 
972 /* compute eflags.P to reg */
973 static CCPrepare gen_prepare_eflags_p(DisasContext *s, TCGv reg)
974 {
975     gen_compute_eflags(s);
976     return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
977                          .mask = CC_P };
978 }
979 
980 /* compute eflags.S to reg */
981 static CCPrepare gen_prepare_eflags_s(DisasContext *s, TCGv reg)
982 {
983     switch (s->cc_op) {
984     case CC_OP_DYNAMIC:
985         gen_compute_eflags(s);
986         /* FALLTHRU */
987     case CC_OP_EFLAGS:
988     case CC_OP_ADCX:
989     case CC_OP_ADOX:
990     case CC_OP_ADCOX:
991         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
992                              .mask = CC_S };
993     case CC_OP_CLR:
994     case CC_OP_POPCNT:
995         return (CCPrepare) { .cond = TCG_COND_NEVER, .mask = -1 };
996     default:
997         {
998             MemOp size = (s->cc_op - CC_OP_ADDB) & 3;
999             TCGv t0 = gen_ext_tl(reg, cpu_cc_dst, size, true);
1000             return (CCPrepare) { .cond = TCG_COND_LT, .reg = t0, .mask = -1 };
1001         }
1002     }
1003 }
1004 
1005 /* compute eflags.O to reg */
1006 static CCPrepare gen_prepare_eflags_o(DisasContext *s, TCGv reg)
1007 {
1008     switch (s->cc_op) {
1009     case CC_OP_ADOX:
1010     case CC_OP_ADCOX:
1011         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src2,
1012                              .mask = -1, .no_setcond = true };
1013     case CC_OP_CLR:
1014     case CC_OP_POPCNT:
1015         return (CCPrepare) { .cond = TCG_COND_NEVER, .mask = -1 };
1016     default:
1017         gen_compute_eflags(s);
1018         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
1019                              .mask = CC_O };
1020     }
1021 }
1022 
1023 /* compute eflags.Z to reg */
1024 static CCPrepare gen_prepare_eflags_z(DisasContext *s, TCGv reg)
1025 {
1026     switch (s->cc_op) {
1027     case CC_OP_DYNAMIC:
1028         gen_compute_eflags(s);
1029         /* FALLTHRU */
1030     case CC_OP_EFLAGS:
1031     case CC_OP_ADCX:
1032     case CC_OP_ADOX:
1033     case CC_OP_ADCOX:
1034         return (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
1035                              .mask = CC_Z };
1036     case CC_OP_CLR:
1037         return (CCPrepare) { .cond = TCG_COND_ALWAYS, .mask = -1 };
1038     case CC_OP_POPCNT:
1039         return (CCPrepare) { .cond = TCG_COND_EQ, .reg = cpu_cc_src,
1040                              .mask = -1 };
1041     default:
1042         {
1043             MemOp size = (s->cc_op - CC_OP_ADDB) & 3;
1044             TCGv t0 = gen_ext_tl(reg, cpu_cc_dst, size, false);
1045             return (CCPrepare) { .cond = TCG_COND_EQ, .reg = t0, .mask = -1 };
1046         }
1047     }
1048 }
1049 
1050 /* perform a conditional store into register 'reg' according to jump opcode
1051    value 'b'. In the fast case, T0 is guaranted not to be used. */
1052 static CCPrepare gen_prepare_cc(DisasContext *s, int b, TCGv reg)
1053 {
1054     int inv, jcc_op, cond;
1055     MemOp size;
1056     CCPrepare cc;
1057     TCGv t0;
1058 
1059     inv = b & 1;
1060     jcc_op = (b >> 1) & 7;
1061 
1062     switch (s->cc_op) {
1063     case CC_OP_SUBB ... CC_OP_SUBQ:
1064         /* We optimize relational operators for the cmp/jcc case.  */
1065         size = s->cc_op - CC_OP_SUBB;
1066         switch (jcc_op) {
1067         case JCC_BE:
1068             tcg_gen_mov_tl(s->tmp4, s->cc_srcT);
1069             gen_extu(size, s->tmp4);
1070             t0 = gen_ext_tl(s->tmp0, cpu_cc_src, size, false);
1071             cc = (CCPrepare) { .cond = TCG_COND_LEU, .reg = s->tmp4,
1072                                .reg2 = t0, .mask = -1, .use_reg2 = true };
1073             break;
1074 
1075         case JCC_L:
1076             cond = TCG_COND_LT;
1077             goto fast_jcc_l;
1078         case JCC_LE:
1079             cond = TCG_COND_LE;
1080         fast_jcc_l:
1081             tcg_gen_mov_tl(s->tmp4, s->cc_srcT);
1082             gen_exts(size, s->tmp4);
1083             t0 = gen_ext_tl(s->tmp0, cpu_cc_src, size, true);
1084             cc = (CCPrepare) { .cond = cond, .reg = s->tmp4,
1085                                .reg2 = t0, .mask = -1, .use_reg2 = true };
1086             break;
1087 
1088         default:
1089             goto slow_jcc;
1090         }
1091         break;
1092 
1093     default:
1094     slow_jcc:
1095         /* This actually generates good code for JC, JZ and JS.  */
1096         switch (jcc_op) {
1097         case JCC_O:
1098             cc = gen_prepare_eflags_o(s, reg);
1099             break;
1100         case JCC_B:
1101             cc = gen_prepare_eflags_c(s, reg);
1102             break;
1103         case JCC_Z:
1104             cc = gen_prepare_eflags_z(s, reg);
1105             break;
1106         case JCC_BE:
1107             gen_compute_eflags(s);
1108             cc = (CCPrepare) { .cond = TCG_COND_NE, .reg = cpu_cc_src,
1109                                .mask = CC_Z | CC_C };
1110             break;
1111         case JCC_S:
1112             cc = gen_prepare_eflags_s(s, reg);
1113             break;
1114         case JCC_P:
1115             cc = gen_prepare_eflags_p(s, reg);
1116             break;
1117         case JCC_L:
1118             gen_compute_eflags(s);
1119             if (reg == cpu_cc_src) {
1120                 reg = s->tmp0;
1121             }
1122             tcg_gen_shri_tl(reg, cpu_cc_src, 4); /* CC_O -> CC_S */
1123             tcg_gen_xor_tl(reg, reg, cpu_cc_src);
1124             cc = (CCPrepare) { .cond = TCG_COND_NE, .reg = reg,
1125                                .mask = CC_S };
1126             break;
1127         default:
1128         case JCC_LE:
1129             gen_compute_eflags(s);
1130             if (reg == cpu_cc_src) {
1131                 reg = s->tmp0;
1132             }
1133             tcg_gen_shri_tl(reg, cpu_cc_src, 4); /* CC_O -> CC_S */
1134             tcg_gen_xor_tl(reg, reg, cpu_cc_src);
1135             cc = (CCPrepare) { .cond = TCG_COND_NE, .reg = reg,
1136                                .mask = CC_S | CC_Z };
1137             break;
1138         }
1139         break;
1140     }
1141 
1142     if (inv) {
1143         cc.cond = tcg_invert_cond(cc.cond);
1144     }
1145     return cc;
1146 }
1147 
1148 static void gen_setcc1(DisasContext *s, int b, TCGv reg)
1149 {
1150     CCPrepare cc = gen_prepare_cc(s, b, reg);
1151 
1152     if (cc.no_setcond) {
1153         if (cc.cond == TCG_COND_EQ) {
1154             tcg_gen_xori_tl(reg, cc.reg, 1);
1155         } else {
1156             tcg_gen_mov_tl(reg, cc.reg);
1157         }
1158         return;
1159     }
1160 
1161     if (cc.cond == TCG_COND_NE && !cc.use_reg2 && cc.imm == 0 &&
1162         cc.mask != 0 && (cc.mask & (cc.mask - 1)) == 0) {
1163         tcg_gen_shri_tl(reg, cc.reg, ctztl(cc.mask));
1164         tcg_gen_andi_tl(reg, reg, 1);
1165         return;
1166     }
1167     if (cc.mask != -1) {
1168         tcg_gen_andi_tl(reg, cc.reg, cc.mask);
1169         cc.reg = reg;
1170     }
1171     if (cc.use_reg2) {
1172         tcg_gen_setcond_tl(cc.cond, reg, cc.reg, cc.reg2);
1173     } else {
1174         tcg_gen_setcondi_tl(cc.cond, reg, cc.reg, cc.imm);
1175     }
1176 }
1177 
1178 static inline void gen_compute_eflags_c(DisasContext *s, TCGv reg)
1179 {
1180     gen_setcc1(s, JCC_B << 1, reg);
1181 }
1182 
1183 /* generate a conditional jump to label 'l1' according to jump opcode
1184    value 'b'. In the fast case, T0 is guaranted not to be used. */
1185 static inline void gen_jcc1_noeob(DisasContext *s, int b, TCGLabel *l1)
1186 {
1187     CCPrepare cc = gen_prepare_cc(s, b, s->T0);
1188 
1189     if (cc.mask != -1) {
1190         tcg_gen_andi_tl(s->T0, cc.reg, cc.mask);
1191         cc.reg = s->T0;
1192     }
1193     if (cc.use_reg2) {
1194         tcg_gen_brcond_tl(cc.cond, cc.reg, cc.reg2, l1);
1195     } else {
1196         tcg_gen_brcondi_tl(cc.cond, cc.reg, cc.imm, l1);
1197     }
1198 }
1199 
1200 /* Generate a conditional jump to label 'l1' according to jump opcode
1201    value 'b'. In the fast case, T0 is guaranted not to be used.
1202    A translation block must end soon.  */
1203 static inline void gen_jcc1(DisasContext *s, int b, TCGLabel *l1)
1204 {
1205     CCPrepare cc = gen_prepare_cc(s, b, s->T0);
1206 
1207     gen_update_cc_op(s);
1208     if (cc.mask != -1) {
1209         tcg_gen_andi_tl(s->T0, cc.reg, cc.mask);
1210         cc.reg = s->T0;
1211     }
1212     set_cc_op(s, CC_OP_DYNAMIC);
1213     if (cc.use_reg2) {
1214         tcg_gen_brcond_tl(cc.cond, cc.reg, cc.reg2, l1);
1215     } else {
1216         tcg_gen_brcondi_tl(cc.cond, cc.reg, cc.imm, l1);
1217     }
1218 }
1219 
1220 /* XXX: does not work with gdbstub "ice" single step - not a
1221    serious problem */
1222 static TCGLabel *gen_jz_ecx_string(DisasContext *s)
1223 {
1224     TCGLabel *l1 = gen_new_label();
1225     TCGLabel *l2 = gen_new_label();
1226     gen_op_jnz_ecx(s, l1);
1227     gen_set_label(l2);
1228     gen_jmp_rel_csize(s, 0, 1);
1229     gen_set_label(l1);
1230     return l2;
1231 }
1232 
1233 static void gen_stos(DisasContext *s, MemOp ot)
1234 {
1235     gen_op_mov_v_reg(s, MO_32, s->T0, R_EAX);
1236     gen_string_movl_A0_EDI(s);
1237     gen_op_st_v(s, ot, s->T0, s->A0);
1238     gen_op_movl_T0_Dshift(s, ot);
1239     gen_op_add_reg_T0(s, s->aflag, R_EDI);
1240 }
1241 
1242 static void gen_lods(DisasContext *s, MemOp ot)
1243 {
1244     gen_string_movl_A0_ESI(s);
1245     gen_op_ld_v(s, ot, s->T0, s->A0);
1246     gen_op_mov_reg_v(s, ot, R_EAX, s->T0);
1247     gen_op_movl_T0_Dshift(s, ot);
1248     gen_op_add_reg_T0(s, s->aflag, R_ESI);
1249 }
1250 
1251 static void gen_scas(DisasContext *s, MemOp ot)
1252 {
1253     gen_string_movl_A0_EDI(s);
1254     gen_op_ld_v(s, ot, s->T1, s->A0);
1255     gen_op(s, OP_CMPL, ot, R_EAX);
1256     gen_op_movl_T0_Dshift(s, ot);
1257     gen_op_add_reg_T0(s, s->aflag, R_EDI);
1258 }
1259 
1260 static void gen_cmps(DisasContext *s, MemOp ot)
1261 {
1262     gen_string_movl_A0_EDI(s);
1263     gen_op_ld_v(s, ot, s->T1, s->A0);
1264     gen_string_movl_A0_ESI(s);
1265     gen_op(s, OP_CMPL, ot, OR_TMP0);
1266     gen_op_movl_T0_Dshift(s, ot);
1267     gen_op_add_reg_T0(s, s->aflag, R_ESI);
1268     gen_op_add_reg_T0(s, s->aflag, R_EDI);
1269 }
1270 
1271 static void gen_bpt_io(DisasContext *s, TCGv_i32 t_port, int ot)
1272 {
1273     if (s->flags & HF_IOBPT_MASK) {
1274 #ifdef CONFIG_USER_ONLY
1275         /* user-mode cpu should not be in IOBPT mode */
1276         g_assert_not_reached();
1277 #else
1278         TCGv_i32 t_size = tcg_constant_i32(1 << ot);
1279         TCGv t_next = eip_next_tl(s);
1280         gen_helper_bpt_io(cpu_env, t_port, t_size, t_next);
1281 #endif /* CONFIG_USER_ONLY */
1282     }
1283 }
1284 
1285 static void gen_ins(DisasContext *s, MemOp ot)
1286 {
1287     gen_string_movl_A0_EDI(s);
1288     /* Note: we must do this dummy write first to be restartable in
1289        case of page fault. */
1290     tcg_gen_movi_tl(s->T0, 0);
1291     gen_op_st_v(s, ot, s->T0, s->A0);
1292     tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
1293     tcg_gen_andi_i32(s->tmp2_i32, s->tmp2_i32, 0xffff);
1294     gen_helper_in_func(ot, s->T0, s->tmp2_i32);
1295     gen_op_st_v(s, ot, s->T0, s->A0);
1296     gen_op_movl_T0_Dshift(s, ot);
1297     gen_op_add_reg_T0(s, s->aflag, R_EDI);
1298     gen_bpt_io(s, s->tmp2_i32, ot);
1299 }
1300 
1301 static void gen_outs(DisasContext *s, MemOp ot)
1302 {
1303     gen_string_movl_A0_ESI(s);
1304     gen_op_ld_v(s, ot, s->T0, s->A0);
1305 
1306     tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
1307     tcg_gen_andi_i32(s->tmp2_i32, s->tmp2_i32, 0xffff);
1308     tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T0);
1309     gen_helper_out_func(ot, s->tmp2_i32, s->tmp3_i32);
1310     gen_op_movl_T0_Dshift(s, ot);
1311     gen_op_add_reg_T0(s, s->aflag, R_ESI);
1312     gen_bpt_io(s, s->tmp2_i32, ot);
1313 }
1314 
1315 /* Generate jumps to current or next instruction */
1316 static void gen_repz(DisasContext *s, MemOp ot,
1317                      void (*fn)(DisasContext *s, MemOp ot))
1318 {
1319     TCGLabel *l2;
1320     gen_update_cc_op(s);
1321     l2 = gen_jz_ecx_string(s);
1322     fn(s, ot);
1323     gen_op_add_reg_im(s, s->aflag, R_ECX, -1);
1324     /*
1325      * A loop would cause two single step exceptions if ECX = 1
1326      * before rep string_insn
1327      */
1328     if (s->repz_opt) {
1329         gen_op_jz_ecx(s, l2);
1330     }
1331     gen_jmp_rel_csize(s, -cur_insn_len(s), 0);
1332 }
1333 
1334 #define GEN_REPZ(op) \
1335     static inline void gen_repz_ ## op(DisasContext *s, MemOp ot) \
1336     { gen_repz(s, ot, gen_##op); }
1337 
1338 static void gen_repz2(DisasContext *s, MemOp ot, int nz,
1339                       void (*fn)(DisasContext *s, MemOp ot))
1340 {
1341     TCGLabel *l2;
1342     gen_update_cc_op(s);
1343     l2 = gen_jz_ecx_string(s);
1344     fn(s, ot);
1345     gen_op_add_reg_im(s, s->aflag, R_ECX, -1);
1346     gen_update_cc_op(s);
1347     gen_jcc1(s, (JCC_Z << 1) | (nz ^ 1), l2);
1348     if (s->repz_opt) {
1349         gen_op_jz_ecx(s, l2);
1350     }
1351     gen_jmp_rel_csize(s, -cur_insn_len(s), 0);
1352 }
1353 
1354 #define GEN_REPZ2(op) \
1355     static inline void gen_repz_ ## op(DisasContext *s, MemOp ot, int nz) \
1356     { gen_repz2(s, ot, nz, gen_##op); }
1357 
1358 GEN_REPZ(movs)
1359 GEN_REPZ(stos)
1360 GEN_REPZ(lods)
1361 GEN_REPZ(ins)
1362 GEN_REPZ(outs)
1363 GEN_REPZ2(scas)
1364 GEN_REPZ2(cmps)
1365 
1366 static void gen_helper_fp_arith_ST0_FT0(int op)
1367 {
1368     switch (op) {
1369     case 0:
1370         gen_helper_fadd_ST0_FT0(cpu_env);
1371         break;
1372     case 1:
1373         gen_helper_fmul_ST0_FT0(cpu_env);
1374         break;
1375     case 2:
1376         gen_helper_fcom_ST0_FT0(cpu_env);
1377         break;
1378     case 3:
1379         gen_helper_fcom_ST0_FT0(cpu_env);
1380         break;
1381     case 4:
1382         gen_helper_fsub_ST0_FT0(cpu_env);
1383         break;
1384     case 5:
1385         gen_helper_fsubr_ST0_FT0(cpu_env);
1386         break;
1387     case 6:
1388         gen_helper_fdiv_ST0_FT0(cpu_env);
1389         break;
1390     case 7:
1391         gen_helper_fdivr_ST0_FT0(cpu_env);
1392         break;
1393     }
1394 }
1395 
1396 /* NOTE the exception in "r" op ordering */
1397 static void gen_helper_fp_arith_STN_ST0(int op, int opreg)
1398 {
1399     TCGv_i32 tmp = tcg_const_i32(opreg);
1400     switch (op) {
1401     case 0:
1402         gen_helper_fadd_STN_ST0(cpu_env, tmp);
1403         break;
1404     case 1:
1405         gen_helper_fmul_STN_ST0(cpu_env, tmp);
1406         break;
1407     case 4:
1408         gen_helper_fsubr_STN_ST0(cpu_env, tmp);
1409         break;
1410     case 5:
1411         gen_helper_fsub_STN_ST0(cpu_env, tmp);
1412         break;
1413     case 6:
1414         gen_helper_fdivr_STN_ST0(cpu_env, tmp);
1415         break;
1416     case 7:
1417         gen_helper_fdiv_STN_ST0(cpu_env, tmp);
1418         break;
1419     }
1420 }
1421 
1422 static void gen_exception(DisasContext *s, int trapno)
1423 {
1424     gen_update_cc_op(s);
1425     gen_update_eip_cur(s);
1426     gen_helper_raise_exception(cpu_env, tcg_const_i32(trapno));
1427     s->base.is_jmp = DISAS_NORETURN;
1428 }
1429 
1430 /* Generate #UD for the current instruction.  The assumption here is that
1431    the instruction is known, but it isn't allowed in the current cpu mode.  */
1432 static void gen_illegal_opcode(DisasContext *s)
1433 {
1434     gen_exception(s, EXCP06_ILLOP);
1435 }
1436 
1437 /* Generate #GP for the current instruction. */
1438 static void gen_exception_gpf(DisasContext *s)
1439 {
1440     gen_exception(s, EXCP0D_GPF);
1441 }
1442 
1443 /* Check for cpl == 0; if not, raise #GP and return false. */
1444 static bool check_cpl0(DisasContext *s)
1445 {
1446     if (CPL(s) == 0) {
1447         return true;
1448     }
1449     gen_exception_gpf(s);
1450     return false;
1451 }
1452 
1453 /* If vm86, check for iopl == 3; if not, raise #GP and return false. */
1454 static bool check_vm86_iopl(DisasContext *s)
1455 {
1456     if (!VM86(s) || IOPL(s) == 3) {
1457         return true;
1458     }
1459     gen_exception_gpf(s);
1460     return false;
1461 }
1462 
1463 /* Check for iopl allowing access; if not, raise #GP and return false. */
1464 static bool check_iopl(DisasContext *s)
1465 {
1466     if (VM86(s) ? IOPL(s) == 3 : CPL(s) <= IOPL(s)) {
1467         return true;
1468     }
1469     gen_exception_gpf(s);
1470     return false;
1471 }
1472 
1473 /* if d == OR_TMP0, it means memory operand (address in A0) */
1474 static void gen_op(DisasContext *s1, int op, MemOp ot, int d)
1475 {
1476     if (d != OR_TMP0) {
1477         if (s1->prefix & PREFIX_LOCK) {
1478             /* Lock prefix when destination is not memory.  */
1479             gen_illegal_opcode(s1);
1480             return;
1481         }
1482         gen_op_mov_v_reg(s1, ot, s1->T0, d);
1483     } else if (!(s1->prefix & PREFIX_LOCK)) {
1484         gen_op_ld_v(s1, ot, s1->T0, s1->A0);
1485     }
1486     switch(op) {
1487     case OP_ADCL:
1488         gen_compute_eflags_c(s1, s1->tmp4);
1489         if (s1->prefix & PREFIX_LOCK) {
1490             tcg_gen_add_tl(s1->T0, s1->tmp4, s1->T1);
1491             tcg_gen_atomic_add_fetch_tl(s1->T0, s1->A0, s1->T0,
1492                                         s1->mem_index, ot | MO_LE);
1493         } else {
1494             tcg_gen_add_tl(s1->T0, s1->T0, s1->T1);
1495             tcg_gen_add_tl(s1->T0, s1->T0, s1->tmp4);
1496             gen_op_st_rm_T0_A0(s1, ot, d);
1497         }
1498         gen_op_update3_cc(s1, s1->tmp4);
1499         set_cc_op(s1, CC_OP_ADCB + ot);
1500         break;
1501     case OP_SBBL:
1502         gen_compute_eflags_c(s1, s1->tmp4);
1503         if (s1->prefix & PREFIX_LOCK) {
1504             tcg_gen_add_tl(s1->T0, s1->T1, s1->tmp4);
1505             tcg_gen_neg_tl(s1->T0, s1->T0);
1506             tcg_gen_atomic_add_fetch_tl(s1->T0, s1->A0, s1->T0,
1507                                         s1->mem_index, ot | MO_LE);
1508         } else {
1509             tcg_gen_sub_tl(s1->T0, s1->T0, s1->T1);
1510             tcg_gen_sub_tl(s1->T0, s1->T0, s1->tmp4);
1511             gen_op_st_rm_T0_A0(s1, ot, d);
1512         }
1513         gen_op_update3_cc(s1, s1->tmp4);
1514         set_cc_op(s1, CC_OP_SBBB + ot);
1515         break;
1516     case OP_ADDL:
1517         if (s1->prefix & PREFIX_LOCK) {
1518             tcg_gen_atomic_add_fetch_tl(s1->T0, s1->A0, s1->T1,
1519                                         s1->mem_index, ot | MO_LE);
1520         } else {
1521             tcg_gen_add_tl(s1->T0, s1->T0, s1->T1);
1522             gen_op_st_rm_T0_A0(s1, ot, d);
1523         }
1524         gen_op_update2_cc(s1);
1525         set_cc_op(s1, CC_OP_ADDB + ot);
1526         break;
1527     case OP_SUBL:
1528         if (s1->prefix & PREFIX_LOCK) {
1529             tcg_gen_neg_tl(s1->T0, s1->T1);
1530             tcg_gen_atomic_fetch_add_tl(s1->cc_srcT, s1->A0, s1->T0,
1531                                         s1->mem_index, ot | MO_LE);
1532             tcg_gen_sub_tl(s1->T0, s1->cc_srcT, s1->T1);
1533         } else {
1534             tcg_gen_mov_tl(s1->cc_srcT, s1->T0);
1535             tcg_gen_sub_tl(s1->T0, s1->T0, s1->T1);
1536             gen_op_st_rm_T0_A0(s1, ot, d);
1537         }
1538         gen_op_update2_cc(s1);
1539         set_cc_op(s1, CC_OP_SUBB + ot);
1540         break;
1541     default:
1542     case OP_ANDL:
1543         if (s1->prefix & PREFIX_LOCK) {
1544             tcg_gen_atomic_and_fetch_tl(s1->T0, s1->A0, s1->T1,
1545                                         s1->mem_index, ot | MO_LE);
1546         } else {
1547             tcg_gen_and_tl(s1->T0, s1->T0, s1->T1);
1548             gen_op_st_rm_T0_A0(s1, ot, d);
1549         }
1550         gen_op_update1_cc(s1);
1551         set_cc_op(s1, CC_OP_LOGICB + ot);
1552         break;
1553     case OP_ORL:
1554         if (s1->prefix & PREFIX_LOCK) {
1555             tcg_gen_atomic_or_fetch_tl(s1->T0, s1->A0, s1->T1,
1556                                        s1->mem_index, ot | MO_LE);
1557         } else {
1558             tcg_gen_or_tl(s1->T0, s1->T0, s1->T1);
1559             gen_op_st_rm_T0_A0(s1, ot, d);
1560         }
1561         gen_op_update1_cc(s1);
1562         set_cc_op(s1, CC_OP_LOGICB + ot);
1563         break;
1564     case OP_XORL:
1565         if (s1->prefix & PREFIX_LOCK) {
1566             tcg_gen_atomic_xor_fetch_tl(s1->T0, s1->A0, s1->T1,
1567                                         s1->mem_index, ot | MO_LE);
1568         } else {
1569             tcg_gen_xor_tl(s1->T0, s1->T0, s1->T1);
1570             gen_op_st_rm_T0_A0(s1, ot, d);
1571         }
1572         gen_op_update1_cc(s1);
1573         set_cc_op(s1, CC_OP_LOGICB + ot);
1574         break;
1575     case OP_CMPL:
1576         tcg_gen_mov_tl(cpu_cc_src, s1->T1);
1577         tcg_gen_mov_tl(s1->cc_srcT, s1->T0);
1578         tcg_gen_sub_tl(cpu_cc_dst, s1->T0, s1->T1);
1579         set_cc_op(s1, CC_OP_SUBB + ot);
1580         break;
1581     }
1582 }
1583 
1584 /* if d == OR_TMP0, it means memory operand (address in A0) */
1585 static void gen_inc(DisasContext *s1, MemOp ot, int d, int c)
1586 {
1587     if (s1->prefix & PREFIX_LOCK) {
1588         if (d != OR_TMP0) {
1589             /* Lock prefix when destination is not memory */
1590             gen_illegal_opcode(s1);
1591             return;
1592         }
1593         tcg_gen_movi_tl(s1->T0, c > 0 ? 1 : -1);
1594         tcg_gen_atomic_add_fetch_tl(s1->T0, s1->A0, s1->T0,
1595                                     s1->mem_index, ot | MO_LE);
1596     } else {
1597         if (d != OR_TMP0) {
1598             gen_op_mov_v_reg(s1, ot, s1->T0, d);
1599         } else {
1600             gen_op_ld_v(s1, ot, s1->T0, s1->A0);
1601         }
1602         tcg_gen_addi_tl(s1->T0, s1->T0, (c > 0 ? 1 : -1));
1603         gen_op_st_rm_T0_A0(s1, ot, d);
1604     }
1605 
1606     gen_compute_eflags_c(s1, cpu_cc_src);
1607     tcg_gen_mov_tl(cpu_cc_dst, s1->T0);
1608     set_cc_op(s1, (c > 0 ? CC_OP_INCB : CC_OP_DECB) + ot);
1609 }
1610 
1611 static void gen_shift_flags(DisasContext *s, MemOp ot, TCGv result,
1612                             TCGv shm1, TCGv count, bool is_right)
1613 {
1614     TCGv_i32 z32, s32, oldop;
1615     TCGv z_tl;
1616 
1617     /* Store the results into the CC variables.  If we know that the
1618        variable must be dead, store unconditionally.  Otherwise we'll
1619        need to not disrupt the current contents.  */
1620     z_tl = tcg_const_tl(0);
1621     if (cc_op_live[s->cc_op] & USES_CC_DST) {
1622         tcg_gen_movcond_tl(TCG_COND_NE, cpu_cc_dst, count, z_tl,
1623                            result, cpu_cc_dst);
1624     } else {
1625         tcg_gen_mov_tl(cpu_cc_dst, result);
1626     }
1627     if (cc_op_live[s->cc_op] & USES_CC_SRC) {
1628         tcg_gen_movcond_tl(TCG_COND_NE, cpu_cc_src, count, z_tl,
1629                            shm1, cpu_cc_src);
1630     } else {
1631         tcg_gen_mov_tl(cpu_cc_src, shm1);
1632     }
1633     tcg_temp_free(z_tl);
1634 
1635     /* Get the two potential CC_OP values into temporaries.  */
1636     tcg_gen_movi_i32(s->tmp2_i32, (is_right ? CC_OP_SARB : CC_OP_SHLB) + ot);
1637     if (s->cc_op == CC_OP_DYNAMIC) {
1638         oldop = cpu_cc_op;
1639     } else {
1640         tcg_gen_movi_i32(s->tmp3_i32, s->cc_op);
1641         oldop = s->tmp3_i32;
1642     }
1643 
1644     /* Conditionally store the CC_OP value.  */
1645     z32 = tcg_const_i32(0);
1646     s32 = tcg_temp_new_i32();
1647     tcg_gen_trunc_tl_i32(s32, count);
1648     tcg_gen_movcond_i32(TCG_COND_NE, cpu_cc_op, s32, z32, s->tmp2_i32, oldop);
1649     tcg_temp_free_i32(z32);
1650     tcg_temp_free_i32(s32);
1651 
1652     /* The CC_OP value is no longer predictable.  */
1653     set_cc_op(s, CC_OP_DYNAMIC);
1654 }
1655 
1656 static void gen_shift_rm_T1(DisasContext *s, MemOp ot, int op1,
1657                             int is_right, int is_arith)
1658 {
1659     target_ulong mask = (ot == MO_64 ? 0x3f : 0x1f);
1660 
1661     /* load */
1662     if (op1 == OR_TMP0) {
1663         gen_op_ld_v(s, ot, s->T0, s->A0);
1664     } else {
1665         gen_op_mov_v_reg(s, ot, s->T0, op1);
1666     }
1667 
1668     tcg_gen_andi_tl(s->T1, s->T1, mask);
1669     tcg_gen_subi_tl(s->tmp0, s->T1, 1);
1670 
1671     if (is_right) {
1672         if (is_arith) {
1673             gen_exts(ot, s->T0);
1674             tcg_gen_sar_tl(s->tmp0, s->T0, s->tmp0);
1675             tcg_gen_sar_tl(s->T0, s->T0, s->T1);
1676         } else {
1677             gen_extu(ot, s->T0);
1678             tcg_gen_shr_tl(s->tmp0, s->T0, s->tmp0);
1679             tcg_gen_shr_tl(s->T0, s->T0, s->T1);
1680         }
1681     } else {
1682         tcg_gen_shl_tl(s->tmp0, s->T0, s->tmp0);
1683         tcg_gen_shl_tl(s->T0, s->T0, s->T1);
1684     }
1685 
1686     /* store */
1687     gen_op_st_rm_T0_A0(s, ot, op1);
1688 
1689     gen_shift_flags(s, ot, s->T0, s->tmp0, s->T1, is_right);
1690 }
1691 
1692 static void gen_shift_rm_im(DisasContext *s, MemOp ot, int op1, int op2,
1693                             int is_right, int is_arith)
1694 {
1695     int mask = (ot == MO_64 ? 0x3f : 0x1f);
1696 
1697     /* load */
1698     if (op1 == OR_TMP0)
1699         gen_op_ld_v(s, ot, s->T0, s->A0);
1700     else
1701         gen_op_mov_v_reg(s, ot, s->T0, op1);
1702 
1703     op2 &= mask;
1704     if (op2 != 0) {
1705         if (is_right) {
1706             if (is_arith) {
1707                 gen_exts(ot, s->T0);
1708                 tcg_gen_sari_tl(s->tmp4, s->T0, op2 - 1);
1709                 tcg_gen_sari_tl(s->T0, s->T0, op2);
1710             } else {
1711                 gen_extu(ot, s->T0);
1712                 tcg_gen_shri_tl(s->tmp4, s->T0, op2 - 1);
1713                 tcg_gen_shri_tl(s->T0, s->T0, op2);
1714             }
1715         } else {
1716             tcg_gen_shli_tl(s->tmp4, s->T0, op2 - 1);
1717             tcg_gen_shli_tl(s->T0, s->T0, op2);
1718         }
1719     }
1720 
1721     /* store */
1722     gen_op_st_rm_T0_A0(s, ot, op1);
1723 
1724     /* update eflags if non zero shift */
1725     if (op2 != 0) {
1726         tcg_gen_mov_tl(cpu_cc_src, s->tmp4);
1727         tcg_gen_mov_tl(cpu_cc_dst, s->T0);
1728         set_cc_op(s, (is_right ? CC_OP_SARB : CC_OP_SHLB) + ot);
1729     }
1730 }
1731 
1732 static void gen_rot_rm_T1(DisasContext *s, MemOp ot, int op1, int is_right)
1733 {
1734     target_ulong mask = (ot == MO_64 ? 0x3f : 0x1f);
1735     TCGv_i32 t0, t1;
1736 
1737     /* load */
1738     if (op1 == OR_TMP0) {
1739         gen_op_ld_v(s, ot, s->T0, s->A0);
1740     } else {
1741         gen_op_mov_v_reg(s, ot, s->T0, op1);
1742     }
1743 
1744     tcg_gen_andi_tl(s->T1, s->T1, mask);
1745 
1746     switch (ot) {
1747     case MO_8:
1748         /* Replicate the 8-bit input so that a 32-bit rotate works.  */
1749         tcg_gen_ext8u_tl(s->T0, s->T0);
1750         tcg_gen_muli_tl(s->T0, s->T0, 0x01010101);
1751         goto do_long;
1752     case MO_16:
1753         /* Replicate the 16-bit input so that a 32-bit rotate works.  */
1754         tcg_gen_deposit_tl(s->T0, s->T0, s->T0, 16, 16);
1755         goto do_long;
1756     do_long:
1757 #ifdef TARGET_X86_64
1758     case MO_32:
1759         tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
1760         tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T1);
1761         if (is_right) {
1762             tcg_gen_rotr_i32(s->tmp2_i32, s->tmp2_i32, s->tmp3_i32);
1763         } else {
1764             tcg_gen_rotl_i32(s->tmp2_i32, s->tmp2_i32, s->tmp3_i32);
1765         }
1766         tcg_gen_extu_i32_tl(s->T0, s->tmp2_i32);
1767         break;
1768 #endif
1769     default:
1770         if (is_right) {
1771             tcg_gen_rotr_tl(s->T0, s->T0, s->T1);
1772         } else {
1773             tcg_gen_rotl_tl(s->T0, s->T0, s->T1);
1774         }
1775         break;
1776     }
1777 
1778     /* store */
1779     gen_op_st_rm_T0_A0(s, ot, op1);
1780 
1781     /* We'll need the flags computed into CC_SRC.  */
1782     gen_compute_eflags(s);
1783 
1784     /* The value that was "rotated out" is now present at the other end
1785        of the word.  Compute C into CC_DST and O into CC_SRC2.  Note that
1786        since we've computed the flags into CC_SRC, these variables are
1787        currently dead.  */
1788     if (is_right) {
1789         tcg_gen_shri_tl(cpu_cc_src2, s->T0, mask - 1);
1790         tcg_gen_shri_tl(cpu_cc_dst, s->T0, mask);
1791         tcg_gen_andi_tl(cpu_cc_dst, cpu_cc_dst, 1);
1792     } else {
1793         tcg_gen_shri_tl(cpu_cc_src2, s->T0, mask);
1794         tcg_gen_andi_tl(cpu_cc_dst, s->T0, 1);
1795     }
1796     tcg_gen_andi_tl(cpu_cc_src2, cpu_cc_src2, 1);
1797     tcg_gen_xor_tl(cpu_cc_src2, cpu_cc_src2, cpu_cc_dst);
1798 
1799     /* Now conditionally store the new CC_OP value.  If the shift count
1800        is 0 we keep the CC_OP_EFLAGS setting so that only CC_SRC is live.
1801        Otherwise reuse CC_OP_ADCOX which have the C and O flags split out
1802        exactly as we computed above.  */
1803     t0 = tcg_const_i32(0);
1804     t1 = tcg_temp_new_i32();
1805     tcg_gen_trunc_tl_i32(t1, s->T1);
1806     tcg_gen_movi_i32(s->tmp2_i32, CC_OP_ADCOX);
1807     tcg_gen_movi_i32(s->tmp3_i32, CC_OP_EFLAGS);
1808     tcg_gen_movcond_i32(TCG_COND_NE, cpu_cc_op, t1, t0,
1809                         s->tmp2_i32, s->tmp3_i32);
1810     tcg_temp_free_i32(t0);
1811     tcg_temp_free_i32(t1);
1812 
1813     /* The CC_OP value is no longer predictable.  */
1814     set_cc_op(s, CC_OP_DYNAMIC);
1815 }
1816 
1817 static void gen_rot_rm_im(DisasContext *s, MemOp ot, int op1, int op2,
1818                           int is_right)
1819 {
1820     int mask = (ot == MO_64 ? 0x3f : 0x1f);
1821     int shift;
1822 
1823     /* load */
1824     if (op1 == OR_TMP0) {
1825         gen_op_ld_v(s, ot, s->T0, s->A0);
1826     } else {
1827         gen_op_mov_v_reg(s, ot, s->T0, op1);
1828     }
1829 
1830     op2 &= mask;
1831     if (op2 != 0) {
1832         switch (ot) {
1833 #ifdef TARGET_X86_64
1834         case MO_32:
1835             tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
1836             if (is_right) {
1837                 tcg_gen_rotri_i32(s->tmp2_i32, s->tmp2_i32, op2);
1838             } else {
1839                 tcg_gen_rotli_i32(s->tmp2_i32, s->tmp2_i32, op2);
1840             }
1841             tcg_gen_extu_i32_tl(s->T0, s->tmp2_i32);
1842             break;
1843 #endif
1844         default:
1845             if (is_right) {
1846                 tcg_gen_rotri_tl(s->T0, s->T0, op2);
1847             } else {
1848                 tcg_gen_rotli_tl(s->T0, s->T0, op2);
1849             }
1850             break;
1851         case MO_8:
1852             mask = 7;
1853             goto do_shifts;
1854         case MO_16:
1855             mask = 15;
1856         do_shifts:
1857             shift = op2 & mask;
1858             if (is_right) {
1859                 shift = mask + 1 - shift;
1860             }
1861             gen_extu(ot, s->T0);
1862             tcg_gen_shli_tl(s->tmp0, s->T0, shift);
1863             tcg_gen_shri_tl(s->T0, s->T0, mask + 1 - shift);
1864             tcg_gen_or_tl(s->T0, s->T0, s->tmp0);
1865             break;
1866         }
1867     }
1868 
1869     /* store */
1870     gen_op_st_rm_T0_A0(s, ot, op1);
1871 
1872     if (op2 != 0) {
1873         /* Compute the flags into CC_SRC.  */
1874         gen_compute_eflags(s);
1875 
1876         /* The value that was "rotated out" is now present at the other end
1877            of the word.  Compute C into CC_DST and O into CC_SRC2.  Note that
1878            since we've computed the flags into CC_SRC, these variables are
1879            currently dead.  */
1880         if (is_right) {
1881             tcg_gen_shri_tl(cpu_cc_src2, s->T0, mask - 1);
1882             tcg_gen_shri_tl(cpu_cc_dst, s->T0, mask);
1883             tcg_gen_andi_tl(cpu_cc_dst, cpu_cc_dst, 1);
1884         } else {
1885             tcg_gen_shri_tl(cpu_cc_src2, s->T0, mask);
1886             tcg_gen_andi_tl(cpu_cc_dst, s->T0, 1);
1887         }
1888         tcg_gen_andi_tl(cpu_cc_src2, cpu_cc_src2, 1);
1889         tcg_gen_xor_tl(cpu_cc_src2, cpu_cc_src2, cpu_cc_dst);
1890         set_cc_op(s, CC_OP_ADCOX);
1891     }
1892 }
1893 
1894 /* XXX: add faster immediate = 1 case */
1895 static void gen_rotc_rm_T1(DisasContext *s, MemOp ot, int op1,
1896                            int is_right)
1897 {
1898     gen_compute_eflags(s);
1899     assert(s->cc_op == CC_OP_EFLAGS);
1900 
1901     /* load */
1902     if (op1 == OR_TMP0)
1903         gen_op_ld_v(s, ot, s->T0, s->A0);
1904     else
1905         gen_op_mov_v_reg(s, ot, s->T0, op1);
1906 
1907     if (is_right) {
1908         switch (ot) {
1909         case MO_8:
1910             gen_helper_rcrb(s->T0, cpu_env, s->T0, s->T1);
1911             break;
1912         case MO_16:
1913             gen_helper_rcrw(s->T0, cpu_env, s->T0, s->T1);
1914             break;
1915         case MO_32:
1916             gen_helper_rcrl(s->T0, cpu_env, s->T0, s->T1);
1917             break;
1918 #ifdef TARGET_X86_64
1919         case MO_64:
1920             gen_helper_rcrq(s->T0, cpu_env, s->T0, s->T1);
1921             break;
1922 #endif
1923         default:
1924             tcg_abort();
1925         }
1926     } else {
1927         switch (ot) {
1928         case MO_8:
1929             gen_helper_rclb(s->T0, cpu_env, s->T0, s->T1);
1930             break;
1931         case MO_16:
1932             gen_helper_rclw(s->T0, cpu_env, s->T0, s->T1);
1933             break;
1934         case MO_32:
1935             gen_helper_rcll(s->T0, cpu_env, s->T0, s->T1);
1936             break;
1937 #ifdef TARGET_X86_64
1938         case MO_64:
1939             gen_helper_rclq(s->T0, cpu_env, s->T0, s->T1);
1940             break;
1941 #endif
1942         default:
1943             tcg_abort();
1944         }
1945     }
1946     /* store */
1947     gen_op_st_rm_T0_A0(s, ot, op1);
1948 }
1949 
1950 /* XXX: add faster immediate case */
1951 static void gen_shiftd_rm_T1(DisasContext *s, MemOp ot, int op1,
1952                              bool is_right, TCGv count_in)
1953 {
1954     target_ulong mask = (ot == MO_64 ? 63 : 31);
1955     TCGv count;
1956 
1957     /* load */
1958     if (op1 == OR_TMP0) {
1959         gen_op_ld_v(s, ot, s->T0, s->A0);
1960     } else {
1961         gen_op_mov_v_reg(s, ot, s->T0, op1);
1962     }
1963 
1964     count = tcg_temp_new();
1965     tcg_gen_andi_tl(count, count_in, mask);
1966 
1967     switch (ot) {
1968     case MO_16:
1969         /* Note: we implement the Intel behaviour for shift count > 16.
1970            This means "shrdw C, B, A" shifts A:B:A >> C.  Build the B:A
1971            portion by constructing it as a 32-bit value.  */
1972         if (is_right) {
1973             tcg_gen_deposit_tl(s->tmp0, s->T0, s->T1, 16, 16);
1974             tcg_gen_mov_tl(s->T1, s->T0);
1975             tcg_gen_mov_tl(s->T0, s->tmp0);
1976         } else {
1977             tcg_gen_deposit_tl(s->T1, s->T0, s->T1, 16, 16);
1978         }
1979         /*
1980          * If TARGET_X86_64 defined then fall through into MO_32 case,
1981          * otherwise fall through default case.
1982          */
1983     case MO_32:
1984 #ifdef TARGET_X86_64
1985         /* Concatenate the two 32-bit values and use a 64-bit shift.  */
1986         tcg_gen_subi_tl(s->tmp0, count, 1);
1987         if (is_right) {
1988             tcg_gen_concat_tl_i64(s->T0, s->T0, s->T1);
1989             tcg_gen_shr_i64(s->tmp0, s->T0, s->tmp0);
1990             tcg_gen_shr_i64(s->T0, s->T0, count);
1991         } else {
1992             tcg_gen_concat_tl_i64(s->T0, s->T1, s->T0);
1993             tcg_gen_shl_i64(s->tmp0, s->T0, s->tmp0);
1994             tcg_gen_shl_i64(s->T0, s->T0, count);
1995             tcg_gen_shri_i64(s->tmp0, s->tmp0, 32);
1996             tcg_gen_shri_i64(s->T0, s->T0, 32);
1997         }
1998         break;
1999 #endif
2000     default:
2001         tcg_gen_subi_tl(s->tmp0, count, 1);
2002         if (is_right) {
2003             tcg_gen_shr_tl(s->tmp0, s->T0, s->tmp0);
2004 
2005             tcg_gen_subfi_tl(s->tmp4, mask + 1, count);
2006             tcg_gen_shr_tl(s->T0, s->T0, count);
2007             tcg_gen_shl_tl(s->T1, s->T1, s->tmp4);
2008         } else {
2009             tcg_gen_shl_tl(s->tmp0, s->T0, s->tmp0);
2010             if (ot == MO_16) {
2011                 /* Only needed if count > 16, for Intel behaviour.  */
2012                 tcg_gen_subfi_tl(s->tmp4, 33, count);
2013                 tcg_gen_shr_tl(s->tmp4, s->T1, s->tmp4);
2014                 tcg_gen_or_tl(s->tmp0, s->tmp0, s->tmp4);
2015             }
2016 
2017             tcg_gen_subfi_tl(s->tmp4, mask + 1, count);
2018             tcg_gen_shl_tl(s->T0, s->T0, count);
2019             tcg_gen_shr_tl(s->T1, s->T1, s->tmp4);
2020         }
2021         tcg_gen_movi_tl(s->tmp4, 0);
2022         tcg_gen_movcond_tl(TCG_COND_EQ, s->T1, count, s->tmp4,
2023                            s->tmp4, s->T1);
2024         tcg_gen_or_tl(s->T0, s->T0, s->T1);
2025         break;
2026     }
2027 
2028     /* store */
2029     gen_op_st_rm_T0_A0(s, ot, op1);
2030 
2031     gen_shift_flags(s, ot, s->T0, s->tmp0, count, is_right);
2032     tcg_temp_free(count);
2033 }
2034 
2035 static void gen_shift(DisasContext *s1, int op, MemOp ot, int d, int s)
2036 {
2037     if (s != OR_TMP1)
2038         gen_op_mov_v_reg(s1, ot, s1->T1, s);
2039     switch(op) {
2040     case OP_ROL:
2041         gen_rot_rm_T1(s1, ot, d, 0);
2042         break;
2043     case OP_ROR:
2044         gen_rot_rm_T1(s1, ot, d, 1);
2045         break;
2046     case OP_SHL:
2047     case OP_SHL1:
2048         gen_shift_rm_T1(s1, ot, d, 0, 0);
2049         break;
2050     case OP_SHR:
2051         gen_shift_rm_T1(s1, ot, d, 1, 0);
2052         break;
2053     case OP_SAR:
2054         gen_shift_rm_T1(s1, ot, d, 1, 1);
2055         break;
2056     case OP_RCL:
2057         gen_rotc_rm_T1(s1, ot, d, 0);
2058         break;
2059     case OP_RCR:
2060         gen_rotc_rm_T1(s1, ot, d, 1);
2061         break;
2062     }
2063 }
2064 
2065 static void gen_shifti(DisasContext *s1, int op, MemOp ot, int d, int c)
2066 {
2067     switch(op) {
2068     case OP_ROL:
2069         gen_rot_rm_im(s1, ot, d, c, 0);
2070         break;
2071     case OP_ROR:
2072         gen_rot_rm_im(s1, ot, d, c, 1);
2073         break;
2074     case OP_SHL:
2075     case OP_SHL1:
2076         gen_shift_rm_im(s1, ot, d, c, 0, 0);
2077         break;
2078     case OP_SHR:
2079         gen_shift_rm_im(s1, ot, d, c, 1, 0);
2080         break;
2081     case OP_SAR:
2082         gen_shift_rm_im(s1, ot, d, c, 1, 1);
2083         break;
2084     default:
2085         /* currently not optimized */
2086         tcg_gen_movi_tl(s1->T1, c);
2087         gen_shift(s1, op, ot, d, OR_TMP1);
2088         break;
2089     }
2090 }
2091 
2092 #define X86_MAX_INSN_LENGTH 15
2093 
2094 static uint64_t advance_pc(CPUX86State *env, DisasContext *s, int num_bytes)
2095 {
2096     uint64_t pc = s->pc;
2097 
2098     /* This is a subsequent insn that crosses a page boundary.  */
2099     if (s->base.num_insns > 1 &&
2100         !is_same_page(&s->base, s->pc + num_bytes - 1)) {
2101         siglongjmp(s->jmpbuf, 2);
2102     }
2103 
2104     s->pc += num_bytes;
2105     if (unlikely(cur_insn_len(s) > X86_MAX_INSN_LENGTH)) {
2106         /* If the instruction's 16th byte is on a different page than the 1st, a
2107          * page fault on the second page wins over the general protection fault
2108          * caused by the instruction being too long.
2109          * This can happen even if the operand is only one byte long!
2110          */
2111         if (((s->pc - 1) ^ (pc - 1)) & TARGET_PAGE_MASK) {
2112             volatile uint8_t unused =
2113                 cpu_ldub_code(env, (s->pc - 1) & TARGET_PAGE_MASK);
2114             (void) unused;
2115         }
2116         siglongjmp(s->jmpbuf, 1);
2117     }
2118 
2119     return pc;
2120 }
2121 
2122 static inline uint8_t x86_ldub_code(CPUX86State *env, DisasContext *s)
2123 {
2124     return translator_ldub(env, &s->base, advance_pc(env, s, 1));
2125 }
2126 
2127 static inline int16_t x86_ldsw_code(CPUX86State *env, DisasContext *s)
2128 {
2129     return translator_lduw(env, &s->base, advance_pc(env, s, 2));
2130 }
2131 
2132 static inline uint16_t x86_lduw_code(CPUX86State *env, DisasContext *s)
2133 {
2134     return translator_lduw(env, &s->base, advance_pc(env, s, 2));
2135 }
2136 
2137 static inline uint32_t x86_ldl_code(CPUX86State *env, DisasContext *s)
2138 {
2139     return translator_ldl(env, &s->base, advance_pc(env, s, 4));
2140 }
2141 
2142 #ifdef TARGET_X86_64
2143 static inline uint64_t x86_ldq_code(CPUX86State *env, DisasContext *s)
2144 {
2145     return translator_ldq(env, &s->base, advance_pc(env, s, 8));
2146 }
2147 #endif
2148 
2149 /* Decompose an address.  */
2150 
2151 typedef struct AddressParts {
2152     int def_seg;
2153     int base;
2154     int index;
2155     int scale;
2156     target_long disp;
2157 } AddressParts;
2158 
2159 static AddressParts gen_lea_modrm_0(CPUX86State *env, DisasContext *s,
2160                                     int modrm)
2161 {
2162     int def_seg, base, index, scale, mod, rm;
2163     target_long disp;
2164     bool havesib;
2165 
2166     def_seg = R_DS;
2167     index = -1;
2168     scale = 0;
2169     disp = 0;
2170 
2171     mod = (modrm >> 6) & 3;
2172     rm = modrm & 7;
2173     base = rm | REX_B(s);
2174 
2175     if (mod == 3) {
2176         /* Normally filtered out earlier, but including this path
2177            simplifies multi-byte nop, as well as bndcl, bndcu, bndcn.  */
2178         goto done;
2179     }
2180 
2181     switch (s->aflag) {
2182     case MO_64:
2183     case MO_32:
2184         havesib = 0;
2185         if (rm == 4) {
2186             int code = x86_ldub_code(env, s);
2187             scale = (code >> 6) & 3;
2188             index = ((code >> 3) & 7) | REX_X(s);
2189             if (index == 4) {
2190                 index = -1;  /* no index */
2191             }
2192             base = (code & 7) | REX_B(s);
2193             havesib = 1;
2194         }
2195 
2196         switch (mod) {
2197         case 0:
2198             if ((base & 7) == 5) {
2199                 base = -1;
2200                 disp = (int32_t)x86_ldl_code(env, s);
2201                 if (CODE64(s) && !havesib) {
2202                     base = -2;
2203                     disp += s->pc + s->rip_offset;
2204                 }
2205             }
2206             break;
2207         case 1:
2208             disp = (int8_t)x86_ldub_code(env, s);
2209             break;
2210         default:
2211         case 2:
2212             disp = (int32_t)x86_ldl_code(env, s);
2213             break;
2214         }
2215 
2216         /* For correct popl handling with esp.  */
2217         if (base == R_ESP && s->popl_esp_hack) {
2218             disp += s->popl_esp_hack;
2219         }
2220         if (base == R_EBP || base == R_ESP) {
2221             def_seg = R_SS;
2222         }
2223         break;
2224 
2225     case MO_16:
2226         if (mod == 0) {
2227             if (rm == 6) {
2228                 base = -1;
2229                 disp = x86_lduw_code(env, s);
2230                 break;
2231             }
2232         } else if (mod == 1) {
2233             disp = (int8_t)x86_ldub_code(env, s);
2234         } else {
2235             disp = (int16_t)x86_lduw_code(env, s);
2236         }
2237 
2238         switch (rm) {
2239         case 0:
2240             base = R_EBX;
2241             index = R_ESI;
2242             break;
2243         case 1:
2244             base = R_EBX;
2245             index = R_EDI;
2246             break;
2247         case 2:
2248             base = R_EBP;
2249             index = R_ESI;
2250             def_seg = R_SS;
2251             break;
2252         case 3:
2253             base = R_EBP;
2254             index = R_EDI;
2255             def_seg = R_SS;
2256             break;
2257         case 4:
2258             base = R_ESI;
2259             break;
2260         case 5:
2261             base = R_EDI;
2262             break;
2263         case 6:
2264             base = R_EBP;
2265             def_seg = R_SS;
2266             break;
2267         default:
2268         case 7:
2269             base = R_EBX;
2270             break;
2271         }
2272         break;
2273 
2274     default:
2275         tcg_abort();
2276     }
2277 
2278  done:
2279     return (AddressParts){ def_seg, base, index, scale, disp };
2280 }
2281 
2282 /* Compute the address, with a minimum number of TCG ops.  */
2283 static TCGv gen_lea_modrm_1(DisasContext *s, AddressParts a, bool is_vsib)
2284 {
2285     TCGv ea = NULL;
2286 
2287     if (a.index >= 0 && !is_vsib) {
2288         if (a.scale == 0) {
2289             ea = cpu_regs[a.index];
2290         } else {
2291             tcg_gen_shli_tl(s->A0, cpu_regs[a.index], a.scale);
2292             ea = s->A0;
2293         }
2294         if (a.base >= 0) {
2295             tcg_gen_add_tl(s->A0, ea, cpu_regs[a.base]);
2296             ea = s->A0;
2297         }
2298     } else if (a.base >= 0) {
2299         ea = cpu_regs[a.base];
2300     }
2301     if (!ea) {
2302         if (TARGET_TB_PCREL && a.base == -2) {
2303             /* With cpu_eip ~= pc_save, the expression is pc-relative. */
2304             tcg_gen_addi_tl(s->A0, cpu_eip, a.disp - s->pc_save);
2305         } else {
2306             tcg_gen_movi_tl(s->A0, a.disp);
2307         }
2308         ea = s->A0;
2309     } else if (a.disp != 0) {
2310         tcg_gen_addi_tl(s->A0, ea, a.disp);
2311         ea = s->A0;
2312     }
2313 
2314     return ea;
2315 }
2316 
2317 static void gen_lea_modrm(CPUX86State *env, DisasContext *s, int modrm)
2318 {
2319     AddressParts a = gen_lea_modrm_0(env, s, modrm);
2320     TCGv ea = gen_lea_modrm_1(s, a, false);
2321     gen_lea_v_seg(s, s->aflag, ea, a.def_seg, s->override);
2322 }
2323 
2324 static void gen_nop_modrm(CPUX86State *env, DisasContext *s, int modrm)
2325 {
2326     (void)gen_lea_modrm_0(env, s, modrm);
2327 }
2328 
2329 /* Used for BNDCL, BNDCU, BNDCN.  */
2330 static void gen_bndck(CPUX86State *env, DisasContext *s, int modrm,
2331                       TCGCond cond, TCGv_i64 bndv)
2332 {
2333     AddressParts a = gen_lea_modrm_0(env, s, modrm);
2334     TCGv ea = gen_lea_modrm_1(s, a, false);
2335 
2336     tcg_gen_extu_tl_i64(s->tmp1_i64, ea);
2337     if (!CODE64(s)) {
2338         tcg_gen_ext32u_i64(s->tmp1_i64, s->tmp1_i64);
2339     }
2340     tcg_gen_setcond_i64(cond, s->tmp1_i64, s->tmp1_i64, bndv);
2341     tcg_gen_extrl_i64_i32(s->tmp2_i32, s->tmp1_i64);
2342     gen_helper_bndck(cpu_env, s->tmp2_i32);
2343 }
2344 
2345 /* used for LEA and MOV AX, mem */
2346 static void gen_add_A0_ds_seg(DisasContext *s)
2347 {
2348     gen_lea_v_seg(s, s->aflag, s->A0, R_DS, s->override);
2349 }
2350 
2351 /* generate modrm memory load or store of 'reg'. TMP0 is used if reg ==
2352    OR_TMP0 */
2353 static void gen_ldst_modrm(CPUX86State *env, DisasContext *s, int modrm,
2354                            MemOp ot, int reg, int is_store)
2355 {
2356     int mod, rm;
2357 
2358     mod = (modrm >> 6) & 3;
2359     rm = (modrm & 7) | REX_B(s);
2360     if (mod == 3) {
2361         if (is_store) {
2362             if (reg != OR_TMP0)
2363                 gen_op_mov_v_reg(s, ot, s->T0, reg);
2364             gen_op_mov_reg_v(s, ot, rm, s->T0);
2365         } else {
2366             gen_op_mov_v_reg(s, ot, s->T0, rm);
2367             if (reg != OR_TMP0)
2368                 gen_op_mov_reg_v(s, ot, reg, s->T0);
2369         }
2370     } else {
2371         gen_lea_modrm(env, s, modrm);
2372         if (is_store) {
2373             if (reg != OR_TMP0)
2374                 gen_op_mov_v_reg(s, ot, s->T0, reg);
2375             gen_op_st_v(s, ot, s->T0, s->A0);
2376         } else {
2377             gen_op_ld_v(s, ot, s->T0, s->A0);
2378             if (reg != OR_TMP0)
2379                 gen_op_mov_reg_v(s, ot, reg, s->T0);
2380         }
2381     }
2382 }
2383 
2384 static target_ulong insn_get_addr(CPUX86State *env, DisasContext *s, MemOp ot)
2385 {
2386     target_ulong ret;
2387 
2388     switch (ot) {
2389     case MO_8:
2390         ret = x86_ldub_code(env, s);
2391         break;
2392     case MO_16:
2393         ret = x86_lduw_code(env, s);
2394         break;
2395     case MO_32:
2396         ret = x86_ldl_code(env, s);
2397         break;
2398 #ifdef TARGET_X86_64
2399     case MO_64:
2400         ret = x86_ldq_code(env, s);
2401         break;
2402 #endif
2403     default:
2404         g_assert_not_reached();
2405     }
2406     return ret;
2407 }
2408 
2409 static inline uint32_t insn_get(CPUX86State *env, DisasContext *s, MemOp ot)
2410 {
2411     uint32_t ret;
2412 
2413     switch (ot) {
2414     case MO_8:
2415         ret = x86_ldub_code(env, s);
2416         break;
2417     case MO_16:
2418         ret = x86_lduw_code(env, s);
2419         break;
2420     case MO_32:
2421 #ifdef TARGET_X86_64
2422     case MO_64:
2423 #endif
2424         ret = x86_ldl_code(env, s);
2425         break;
2426     default:
2427         tcg_abort();
2428     }
2429     return ret;
2430 }
2431 
2432 static target_long insn_get_signed(CPUX86State *env, DisasContext *s, MemOp ot)
2433 {
2434     target_long ret;
2435 
2436     switch (ot) {
2437     case MO_8:
2438         ret = (int8_t) x86_ldub_code(env, s);
2439         break;
2440     case MO_16:
2441         ret = (int16_t) x86_lduw_code(env, s);
2442         break;
2443     case MO_32:
2444         ret = (int32_t) x86_ldl_code(env, s);
2445         break;
2446 #ifdef TARGET_X86_64
2447     case MO_64:
2448         ret = x86_ldq_code(env, s);
2449         break;
2450 #endif
2451     default:
2452         g_assert_not_reached();
2453     }
2454     return ret;
2455 }
2456 
2457 static inline int insn_const_size(MemOp ot)
2458 {
2459     if (ot <= MO_32) {
2460         return 1 << ot;
2461     } else {
2462         return 4;
2463     }
2464 }
2465 
2466 static void gen_jcc(DisasContext *s, int b, int diff)
2467 {
2468     TCGLabel *l1 = gen_new_label();
2469 
2470     gen_jcc1(s, b, l1);
2471     gen_jmp_rel_csize(s, 0, 1);
2472     gen_set_label(l1);
2473     gen_jmp_rel(s, s->dflag, diff, 0);
2474 }
2475 
2476 static void gen_cmovcc1(CPUX86State *env, DisasContext *s, MemOp ot, int b,
2477                         int modrm, int reg)
2478 {
2479     CCPrepare cc;
2480 
2481     gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
2482 
2483     cc = gen_prepare_cc(s, b, s->T1);
2484     if (cc.mask != -1) {
2485         TCGv t0 = tcg_temp_new();
2486         tcg_gen_andi_tl(t0, cc.reg, cc.mask);
2487         cc.reg = t0;
2488     }
2489     if (!cc.use_reg2) {
2490         cc.reg2 = tcg_const_tl(cc.imm);
2491     }
2492 
2493     tcg_gen_movcond_tl(cc.cond, s->T0, cc.reg, cc.reg2,
2494                        s->T0, cpu_regs[reg]);
2495     gen_op_mov_reg_v(s, ot, reg, s->T0);
2496 
2497     if (cc.mask != -1) {
2498         tcg_temp_free(cc.reg);
2499     }
2500     if (!cc.use_reg2) {
2501         tcg_temp_free(cc.reg2);
2502     }
2503 }
2504 
2505 static inline void gen_op_movl_T0_seg(DisasContext *s, X86Seg seg_reg)
2506 {
2507     tcg_gen_ld32u_tl(s->T0, cpu_env,
2508                      offsetof(CPUX86State,segs[seg_reg].selector));
2509 }
2510 
2511 static inline void gen_op_movl_seg_T0_vm(DisasContext *s, X86Seg seg_reg)
2512 {
2513     tcg_gen_ext16u_tl(s->T0, s->T0);
2514     tcg_gen_st32_tl(s->T0, cpu_env,
2515                     offsetof(CPUX86State,segs[seg_reg].selector));
2516     tcg_gen_shli_tl(cpu_seg_base[seg_reg], s->T0, 4);
2517 }
2518 
2519 /* move T0 to seg_reg and compute if the CPU state may change. Never
2520    call this function with seg_reg == R_CS */
2521 static void gen_movl_seg_T0(DisasContext *s, X86Seg seg_reg)
2522 {
2523     if (PE(s) && !VM86(s)) {
2524         tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
2525         gen_helper_load_seg(cpu_env, tcg_const_i32(seg_reg), s->tmp2_i32);
2526         /* abort translation because the addseg value may change or
2527            because ss32 may change. For R_SS, translation must always
2528            stop as a special handling must be done to disable hardware
2529            interrupts for the next instruction */
2530         if (seg_reg == R_SS) {
2531             s->base.is_jmp = DISAS_EOB_INHIBIT_IRQ;
2532         } else if (CODE32(s) && seg_reg < R_FS) {
2533             s->base.is_jmp = DISAS_EOB_NEXT;
2534         }
2535     } else {
2536         gen_op_movl_seg_T0_vm(s, seg_reg);
2537         if (seg_reg == R_SS) {
2538             s->base.is_jmp = DISAS_EOB_INHIBIT_IRQ;
2539         }
2540     }
2541 }
2542 
2543 static void gen_svm_check_intercept(DisasContext *s, uint32_t type)
2544 {
2545     /* no SVM activated; fast case */
2546     if (likely(!GUEST(s))) {
2547         return;
2548     }
2549     gen_helper_svm_check_intercept(cpu_env, tcg_constant_i32(type));
2550 }
2551 
2552 static inline void gen_stack_update(DisasContext *s, int addend)
2553 {
2554     gen_op_add_reg_im(s, mo_stacksize(s), R_ESP, addend);
2555 }
2556 
2557 /* Generate a push. It depends on ss32, addseg and dflag.  */
2558 static void gen_push_v(DisasContext *s, TCGv val)
2559 {
2560     MemOp d_ot = mo_pushpop(s, s->dflag);
2561     MemOp a_ot = mo_stacksize(s);
2562     int size = 1 << d_ot;
2563     TCGv new_esp = s->A0;
2564 
2565     tcg_gen_subi_tl(s->A0, cpu_regs[R_ESP], size);
2566 
2567     if (!CODE64(s)) {
2568         if (ADDSEG(s)) {
2569             new_esp = s->tmp4;
2570             tcg_gen_mov_tl(new_esp, s->A0);
2571         }
2572         gen_lea_v_seg(s, a_ot, s->A0, R_SS, -1);
2573     }
2574 
2575     gen_op_st_v(s, d_ot, val, s->A0);
2576     gen_op_mov_reg_v(s, a_ot, R_ESP, new_esp);
2577 }
2578 
2579 /* two step pop is necessary for precise exceptions */
2580 static MemOp gen_pop_T0(DisasContext *s)
2581 {
2582     MemOp d_ot = mo_pushpop(s, s->dflag);
2583 
2584     gen_lea_v_seg(s, mo_stacksize(s), cpu_regs[R_ESP], R_SS, -1);
2585     gen_op_ld_v(s, d_ot, s->T0, s->A0);
2586 
2587     return d_ot;
2588 }
2589 
2590 static inline void gen_pop_update(DisasContext *s, MemOp ot)
2591 {
2592     gen_stack_update(s, 1 << ot);
2593 }
2594 
2595 static inline void gen_stack_A0(DisasContext *s)
2596 {
2597     gen_lea_v_seg(s, SS32(s) ? MO_32 : MO_16, cpu_regs[R_ESP], R_SS, -1);
2598 }
2599 
2600 static void gen_pusha(DisasContext *s)
2601 {
2602     MemOp s_ot = SS32(s) ? MO_32 : MO_16;
2603     MemOp d_ot = s->dflag;
2604     int size = 1 << d_ot;
2605     int i;
2606 
2607     for (i = 0; i < 8; i++) {
2608         tcg_gen_addi_tl(s->A0, cpu_regs[R_ESP], (i - 8) * size);
2609         gen_lea_v_seg(s, s_ot, s->A0, R_SS, -1);
2610         gen_op_st_v(s, d_ot, cpu_regs[7 - i], s->A0);
2611     }
2612 
2613     gen_stack_update(s, -8 * size);
2614 }
2615 
2616 static void gen_popa(DisasContext *s)
2617 {
2618     MemOp s_ot = SS32(s) ? MO_32 : MO_16;
2619     MemOp d_ot = s->dflag;
2620     int size = 1 << d_ot;
2621     int i;
2622 
2623     for (i = 0; i < 8; i++) {
2624         /* ESP is not reloaded */
2625         if (7 - i == R_ESP) {
2626             continue;
2627         }
2628         tcg_gen_addi_tl(s->A0, cpu_regs[R_ESP], i * size);
2629         gen_lea_v_seg(s, s_ot, s->A0, R_SS, -1);
2630         gen_op_ld_v(s, d_ot, s->T0, s->A0);
2631         gen_op_mov_reg_v(s, d_ot, 7 - i, s->T0);
2632     }
2633 
2634     gen_stack_update(s, 8 * size);
2635 }
2636 
2637 static void gen_enter(DisasContext *s, int esp_addend, int level)
2638 {
2639     MemOp d_ot = mo_pushpop(s, s->dflag);
2640     MemOp a_ot = CODE64(s) ? MO_64 : SS32(s) ? MO_32 : MO_16;
2641     int size = 1 << d_ot;
2642 
2643     /* Push BP; compute FrameTemp into T1.  */
2644     tcg_gen_subi_tl(s->T1, cpu_regs[R_ESP], size);
2645     gen_lea_v_seg(s, a_ot, s->T1, R_SS, -1);
2646     gen_op_st_v(s, d_ot, cpu_regs[R_EBP], s->A0);
2647 
2648     level &= 31;
2649     if (level != 0) {
2650         int i;
2651 
2652         /* Copy level-1 pointers from the previous frame.  */
2653         for (i = 1; i < level; ++i) {
2654             tcg_gen_subi_tl(s->A0, cpu_regs[R_EBP], size * i);
2655             gen_lea_v_seg(s, a_ot, s->A0, R_SS, -1);
2656             gen_op_ld_v(s, d_ot, s->tmp0, s->A0);
2657 
2658             tcg_gen_subi_tl(s->A0, s->T1, size * i);
2659             gen_lea_v_seg(s, a_ot, s->A0, R_SS, -1);
2660             gen_op_st_v(s, d_ot, s->tmp0, s->A0);
2661         }
2662 
2663         /* Push the current FrameTemp as the last level.  */
2664         tcg_gen_subi_tl(s->A0, s->T1, size * level);
2665         gen_lea_v_seg(s, a_ot, s->A0, R_SS, -1);
2666         gen_op_st_v(s, d_ot, s->T1, s->A0);
2667     }
2668 
2669     /* Copy the FrameTemp value to EBP.  */
2670     gen_op_mov_reg_v(s, a_ot, R_EBP, s->T1);
2671 
2672     /* Compute the final value of ESP.  */
2673     tcg_gen_subi_tl(s->T1, s->T1, esp_addend + size * level);
2674     gen_op_mov_reg_v(s, a_ot, R_ESP, s->T1);
2675 }
2676 
2677 static void gen_leave(DisasContext *s)
2678 {
2679     MemOp d_ot = mo_pushpop(s, s->dflag);
2680     MemOp a_ot = mo_stacksize(s);
2681 
2682     gen_lea_v_seg(s, a_ot, cpu_regs[R_EBP], R_SS, -1);
2683     gen_op_ld_v(s, d_ot, s->T0, s->A0);
2684 
2685     tcg_gen_addi_tl(s->T1, cpu_regs[R_EBP], 1 << d_ot);
2686 
2687     gen_op_mov_reg_v(s, d_ot, R_EBP, s->T0);
2688     gen_op_mov_reg_v(s, a_ot, R_ESP, s->T1);
2689 }
2690 
2691 /* Similarly, except that the assumption here is that we don't decode
2692    the instruction at all -- either a missing opcode, an unimplemented
2693    feature, or just a bogus instruction stream.  */
2694 static void gen_unknown_opcode(CPUX86State *env, DisasContext *s)
2695 {
2696     gen_illegal_opcode(s);
2697 
2698     if (qemu_loglevel_mask(LOG_UNIMP)) {
2699         FILE *logfile = qemu_log_trylock();
2700         if (logfile) {
2701             target_ulong pc = s->base.pc_next, end = s->pc;
2702 
2703             fprintf(logfile, "ILLOPC: " TARGET_FMT_lx ":", pc);
2704             for (; pc < end; ++pc) {
2705                 fprintf(logfile, " %02x", cpu_ldub_code(env, pc));
2706             }
2707             fprintf(logfile, "\n");
2708             qemu_log_unlock(logfile);
2709         }
2710     }
2711 }
2712 
2713 /* an interrupt is different from an exception because of the
2714    privilege checks */
2715 static void gen_interrupt(DisasContext *s, int intno)
2716 {
2717     gen_update_cc_op(s);
2718     gen_update_eip_cur(s);
2719     gen_helper_raise_interrupt(cpu_env, tcg_constant_i32(intno),
2720                                cur_insn_len_i32(s));
2721     s->base.is_jmp = DISAS_NORETURN;
2722 }
2723 
2724 static void gen_set_hflag(DisasContext *s, uint32_t mask)
2725 {
2726     if ((s->flags & mask) == 0) {
2727         TCGv_i32 t = tcg_temp_new_i32();
2728         tcg_gen_ld_i32(t, cpu_env, offsetof(CPUX86State, hflags));
2729         tcg_gen_ori_i32(t, t, mask);
2730         tcg_gen_st_i32(t, cpu_env, offsetof(CPUX86State, hflags));
2731         tcg_temp_free_i32(t);
2732         s->flags |= mask;
2733     }
2734 }
2735 
2736 static void gen_reset_hflag(DisasContext *s, uint32_t mask)
2737 {
2738     if (s->flags & mask) {
2739         TCGv_i32 t = tcg_temp_new_i32();
2740         tcg_gen_ld_i32(t, cpu_env, offsetof(CPUX86State, hflags));
2741         tcg_gen_andi_i32(t, t, ~mask);
2742         tcg_gen_st_i32(t, cpu_env, offsetof(CPUX86State, hflags));
2743         tcg_temp_free_i32(t);
2744         s->flags &= ~mask;
2745     }
2746 }
2747 
2748 /* Clear BND registers during legacy branches.  */
2749 static void gen_bnd_jmp(DisasContext *s)
2750 {
2751     /* Clear the registers only if BND prefix is missing, MPX is enabled,
2752        and if the BNDREGs are known to be in use (non-zero) already.
2753        The helper itself will check BNDPRESERVE at runtime.  */
2754     if ((s->prefix & PREFIX_REPNZ) == 0
2755         && (s->flags & HF_MPX_EN_MASK) != 0
2756         && (s->flags & HF_MPX_IU_MASK) != 0) {
2757         gen_helper_bnd_jmp(cpu_env);
2758     }
2759 }
2760 
2761 /* Generate an end of block. Trace exception is also generated if needed.
2762    If INHIBIT, set HF_INHIBIT_IRQ_MASK if it isn't already set.
2763    If RECHECK_TF, emit a rechecking helper for #DB, ignoring the state of
2764    S->TF.  This is used by the syscall/sysret insns.  */
2765 static void
2766 do_gen_eob_worker(DisasContext *s, bool inhibit, bool recheck_tf, bool jr)
2767 {
2768     gen_update_cc_op(s);
2769 
2770     /* If several instructions disable interrupts, only the first does it.  */
2771     if (inhibit && !(s->flags & HF_INHIBIT_IRQ_MASK)) {
2772         gen_set_hflag(s, HF_INHIBIT_IRQ_MASK);
2773     } else {
2774         gen_reset_hflag(s, HF_INHIBIT_IRQ_MASK);
2775     }
2776 
2777     if (s->base.tb->flags & HF_RF_MASK) {
2778         gen_helper_reset_rf(cpu_env);
2779     }
2780     if (recheck_tf) {
2781         gen_helper_rechecking_single_step(cpu_env);
2782         tcg_gen_exit_tb(NULL, 0);
2783     } else if (s->flags & HF_TF_MASK) {
2784         gen_helper_single_step(cpu_env);
2785     } else if (jr) {
2786         tcg_gen_lookup_and_goto_ptr();
2787     } else {
2788         tcg_gen_exit_tb(NULL, 0);
2789     }
2790     s->base.is_jmp = DISAS_NORETURN;
2791 }
2792 
2793 static inline void
2794 gen_eob_worker(DisasContext *s, bool inhibit, bool recheck_tf)
2795 {
2796     do_gen_eob_worker(s, inhibit, recheck_tf, false);
2797 }
2798 
2799 /* End of block.
2800    If INHIBIT, set HF_INHIBIT_IRQ_MASK if it isn't already set.  */
2801 static void gen_eob_inhibit_irq(DisasContext *s, bool inhibit)
2802 {
2803     gen_eob_worker(s, inhibit, false);
2804 }
2805 
2806 /* End of block, resetting the inhibit irq flag.  */
2807 static void gen_eob(DisasContext *s)
2808 {
2809     gen_eob_worker(s, false, false);
2810 }
2811 
2812 /* Jump to register */
2813 static void gen_jr(DisasContext *s)
2814 {
2815     do_gen_eob_worker(s, false, false, true);
2816 }
2817 
2818 /* Jump to eip+diff, truncating the result to OT. */
2819 static void gen_jmp_rel(DisasContext *s, MemOp ot, int diff, int tb_num)
2820 {
2821     bool use_goto_tb = s->jmp_opt;
2822     target_ulong mask = -1;
2823     target_ulong new_pc = s->pc + diff;
2824     target_ulong new_eip = new_pc - s->cs_base;
2825 
2826     /* In 64-bit mode, operand size is fixed at 64 bits. */
2827     if (!CODE64(s)) {
2828         if (ot == MO_16) {
2829             mask = 0xffff;
2830             if (TARGET_TB_PCREL && CODE32(s)) {
2831                 use_goto_tb = false;
2832             }
2833         } else {
2834             mask = 0xffffffff;
2835         }
2836     }
2837     new_eip &= mask;
2838 
2839     gen_update_cc_op(s);
2840     set_cc_op(s, CC_OP_DYNAMIC);
2841 
2842     if (TARGET_TB_PCREL) {
2843         tcg_gen_addi_tl(cpu_eip, cpu_eip, new_pc - s->pc_save);
2844         /*
2845          * If we can prove the branch does not leave the page and we have
2846          * no extra masking to apply (data16 branch in code32, see above),
2847          * then we have also proven that the addition does not wrap.
2848          */
2849         if (!use_goto_tb || !is_same_page(&s->base, new_pc)) {
2850             tcg_gen_andi_tl(cpu_eip, cpu_eip, mask);
2851             use_goto_tb = false;
2852         }
2853     }
2854 
2855     if (use_goto_tb &&
2856         translator_use_goto_tb(&s->base, new_eip + s->cs_base)) {
2857         /* jump to same page: we can use a direct jump */
2858         tcg_gen_goto_tb(tb_num);
2859         if (!TARGET_TB_PCREL) {
2860             tcg_gen_movi_tl(cpu_eip, new_eip);
2861         }
2862         tcg_gen_exit_tb(s->base.tb, tb_num);
2863         s->base.is_jmp = DISAS_NORETURN;
2864     } else {
2865         if (!TARGET_TB_PCREL) {
2866             tcg_gen_movi_tl(cpu_eip, new_eip);
2867         }
2868         if (s->jmp_opt) {
2869             gen_jr(s);   /* jump to another page */
2870         } else {
2871             gen_eob(s);  /* exit to main loop */
2872         }
2873     }
2874 }
2875 
2876 /* Jump to eip+diff, truncating to the current code size. */
2877 static void gen_jmp_rel_csize(DisasContext *s, int diff, int tb_num)
2878 {
2879     /* CODE64 ignores the OT argument, so we need not consider it. */
2880     gen_jmp_rel(s, CODE32(s) ? MO_32 : MO_16, diff, tb_num);
2881 }
2882 
2883 static inline void gen_ldq_env_A0(DisasContext *s, int offset)
2884 {
2885     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0, s->mem_index, MO_LEUQ);
2886     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset);
2887 }
2888 
2889 static inline void gen_stq_env_A0(DisasContext *s, int offset)
2890 {
2891     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset);
2892     tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0, s->mem_index, MO_LEUQ);
2893 }
2894 
2895 static inline void gen_ldo_env_A0(DisasContext *s, int offset, bool align)
2896 {
2897     int mem_index = s->mem_index;
2898     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0, mem_index,
2899                         MO_LEUQ | (align ? MO_ALIGN_16 : 0));
2900     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(XMMReg, XMM_Q(0)));
2901     tcg_gen_addi_tl(s->tmp0, s->A0, 8);
2902     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2903     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(XMMReg, XMM_Q(1)));
2904 }
2905 
2906 static inline void gen_sto_env_A0(DisasContext *s, int offset, bool align)
2907 {
2908     int mem_index = s->mem_index;
2909     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(XMMReg, XMM_Q(0)));
2910     tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0, mem_index,
2911                         MO_LEUQ | (align ? MO_ALIGN_16 : 0));
2912     tcg_gen_addi_tl(s->tmp0, s->A0, 8);
2913     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(XMMReg, XMM_Q(1)));
2914     tcg_gen_qemu_st_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2915 }
2916 
2917 static void gen_ldy_env_A0(DisasContext *s, int offset, bool align)
2918 {
2919     int mem_index = s->mem_index;
2920     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0, mem_index,
2921                         MO_LEUQ | (align ? MO_ALIGN_32 : 0));
2922     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(0)));
2923     tcg_gen_addi_tl(s->tmp0, s->A0, 8);
2924     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2925     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(1)));
2926 
2927     tcg_gen_addi_tl(s->tmp0, s->A0, 16);
2928     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2929     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(2)));
2930     tcg_gen_addi_tl(s->tmp0, s->A0, 24);
2931     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2932     tcg_gen_st_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(3)));
2933 }
2934 
2935 static void gen_sty_env_A0(DisasContext *s, int offset, bool align)
2936 {
2937     int mem_index = s->mem_index;
2938     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(0)));
2939     tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0, mem_index,
2940                         MO_LEUQ | (align ? MO_ALIGN_32 : 0));
2941     tcg_gen_addi_tl(s->tmp0, s->A0, 8);
2942     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(1)));
2943     tcg_gen_qemu_st_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2944     tcg_gen_addi_tl(s->tmp0, s->A0, 16);
2945     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(2)));
2946     tcg_gen_qemu_st_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2947     tcg_gen_addi_tl(s->tmp0, s->A0, 24);
2948     tcg_gen_ld_i64(s->tmp1_i64, cpu_env, offset + offsetof(YMMReg, YMM_Q(3)));
2949     tcg_gen_qemu_st_i64(s->tmp1_i64, s->tmp0, mem_index, MO_LEUQ);
2950 }
2951 
2952 #include "decode-new.h"
2953 #include "emit.c.inc"
2954 #include "decode-new.c.inc"
2955 
2956 /* convert one instruction. s->base.is_jmp is set if the translation must
2957    be stopped. Return the next pc value */
2958 static bool disas_insn(DisasContext *s, CPUState *cpu)
2959 {
2960     CPUX86State *env = cpu->env_ptr;
2961     int b, prefixes;
2962     int shift;
2963     MemOp ot, aflag, dflag;
2964     int modrm, reg, rm, mod, op, opreg, val;
2965     bool orig_cc_op_dirty = s->cc_op_dirty;
2966     CCOp orig_cc_op = s->cc_op;
2967     target_ulong orig_pc_save = s->pc_save;
2968 
2969     s->pc = s->base.pc_next;
2970     s->override = -1;
2971 #ifdef TARGET_X86_64
2972     s->rex_r = 0;
2973     s->rex_x = 0;
2974     s->rex_b = 0;
2975 #endif
2976     s->rip_offset = 0; /* for relative ip address */
2977     s->vex_l = 0;
2978     s->vex_v = 0;
2979     s->vex_w = false;
2980     switch (sigsetjmp(s->jmpbuf, 0)) {
2981     case 0:
2982         break;
2983     case 1:
2984         gen_exception_gpf(s);
2985         return true;
2986     case 2:
2987         /* Restore state that may affect the next instruction. */
2988         s->pc = s->base.pc_next;
2989         /*
2990          * TODO: These save/restore can be removed after the table-based
2991          * decoder is complete; we will be decoding the insn completely
2992          * before any code generation that might affect these variables.
2993          */
2994         s->cc_op_dirty = orig_cc_op_dirty;
2995         s->cc_op = orig_cc_op;
2996         s->pc_save = orig_pc_save;
2997         /* END TODO */
2998         s->base.num_insns--;
2999         tcg_remove_ops_after(s->prev_insn_end);
3000         s->base.is_jmp = DISAS_TOO_MANY;
3001         return false;
3002     default:
3003         g_assert_not_reached();
3004     }
3005 
3006     prefixes = 0;
3007 
3008  next_byte:
3009     s->prefix = prefixes;
3010     b = x86_ldub_code(env, s);
3011     /* Collect prefixes.  */
3012     switch (b) {
3013     default:
3014         break;
3015     case 0x0f:
3016         b = x86_ldub_code(env, s) + 0x100;
3017         break;
3018     case 0xf3:
3019         prefixes |= PREFIX_REPZ;
3020         prefixes &= ~PREFIX_REPNZ;
3021         goto next_byte;
3022     case 0xf2:
3023         prefixes |= PREFIX_REPNZ;
3024         prefixes &= ~PREFIX_REPZ;
3025         goto next_byte;
3026     case 0xf0:
3027         prefixes |= PREFIX_LOCK;
3028         goto next_byte;
3029     case 0x2e:
3030         s->override = R_CS;
3031         goto next_byte;
3032     case 0x36:
3033         s->override = R_SS;
3034         goto next_byte;
3035     case 0x3e:
3036         s->override = R_DS;
3037         goto next_byte;
3038     case 0x26:
3039         s->override = R_ES;
3040         goto next_byte;
3041     case 0x64:
3042         s->override = R_FS;
3043         goto next_byte;
3044     case 0x65:
3045         s->override = R_GS;
3046         goto next_byte;
3047     case 0x66:
3048         prefixes |= PREFIX_DATA;
3049         goto next_byte;
3050     case 0x67:
3051         prefixes |= PREFIX_ADR;
3052         goto next_byte;
3053 #ifdef TARGET_X86_64
3054     case 0x40 ... 0x4f:
3055         if (CODE64(s)) {
3056             /* REX prefix */
3057             prefixes |= PREFIX_REX;
3058             s->vex_w = (b >> 3) & 1;
3059             s->rex_r = (b & 0x4) << 1;
3060             s->rex_x = (b & 0x2) << 2;
3061             s->rex_b = (b & 0x1) << 3;
3062             goto next_byte;
3063         }
3064         break;
3065 #endif
3066     case 0xc5: /* 2-byte VEX */
3067     case 0xc4: /* 3-byte VEX */
3068         if (CODE32(s) && !VM86(s)) {
3069             int vex2 = x86_ldub_code(env, s);
3070             s->pc--; /* rewind the advance_pc() x86_ldub_code() did */
3071 
3072             if (!CODE64(s) && (vex2 & 0xc0) != 0xc0) {
3073                 /* 4.1.4.6: In 32-bit mode, bits [7:6] must be 11b,
3074                    otherwise the instruction is LES or LDS.  */
3075                 break;
3076             }
3077             disas_insn_new(s, cpu, b);
3078             return s->pc;
3079         }
3080         break;
3081     }
3082 
3083     /* Post-process prefixes.  */
3084     if (CODE64(s)) {
3085         /* In 64-bit mode, the default data size is 32-bit.  Select 64-bit
3086            data with rex_w, and 16-bit data with 0x66; rex_w takes precedence
3087            over 0x66 if both are present.  */
3088         dflag = (REX_W(s) ? MO_64 : prefixes & PREFIX_DATA ? MO_16 : MO_32);
3089         /* In 64-bit mode, 0x67 selects 32-bit addressing.  */
3090         aflag = (prefixes & PREFIX_ADR ? MO_32 : MO_64);
3091     } else {
3092         /* In 16/32-bit mode, 0x66 selects the opposite data size.  */
3093         if (CODE32(s) ^ ((prefixes & PREFIX_DATA) != 0)) {
3094             dflag = MO_32;
3095         } else {
3096             dflag = MO_16;
3097         }
3098         /* In 16/32-bit mode, 0x67 selects the opposite addressing.  */
3099         if (CODE32(s) ^ ((prefixes & PREFIX_ADR) != 0)) {
3100             aflag = MO_32;
3101         }  else {
3102             aflag = MO_16;
3103         }
3104     }
3105 
3106     s->prefix = prefixes;
3107     s->aflag = aflag;
3108     s->dflag = dflag;
3109 
3110     /* now check op code */
3111     switch (b) {
3112         /**************************/
3113         /* arith & logic */
3114     case 0x00 ... 0x05:
3115     case 0x08 ... 0x0d:
3116     case 0x10 ... 0x15:
3117     case 0x18 ... 0x1d:
3118     case 0x20 ... 0x25:
3119     case 0x28 ... 0x2d:
3120     case 0x30 ... 0x35:
3121     case 0x38 ... 0x3d:
3122         {
3123             int op, f, val;
3124             op = (b >> 3) & 7;
3125             f = (b >> 1) & 3;
3126 
3127             ot = mo_b_d(b, dflag);
3128 
3129             switch(f) {
3130             case 0: /* OP Ev, Gv */
3131                 modrm = x86_ldub_code(env, s);
3132                 reg = ((modrm >> 3) & 7) | REX_R(s);
3133                 mod = (modrm >> 6) & 3;
3134                 rm = (modrm & 7) | REX_B(s);
3135                 if (mod != 3) {
3136                     gen_lea_modrm(env, s, modrm);
3137                     opreg = OR_TMP0;
3138                 } else if (op == OP_XORL && rm == reg) {
3139                 xor_zero:
3140                     /* xor reg, reg optimisation */
3141                     set_cc_op(s, CC_OP_CLR);
3142                     tcg_gen_movi_tl(s->T0, 0);
3143                     gen_op_mov_reg_v(s, ot, reg, s->T0);
3144                     break;
3145                 } else {
3146                     opreg = rm;
3147                 }
3148                 gen_op_mov_v_reg(s, ot, s->T1, reg);
3149                 gen_op(s, op, ot, opreg);
3150                 break;
3151             case 1: /* OP Gv, Ev */
3152                 modrm = x86_ldub_code(env, s);
3153                 mod = (modrm >> 6) & 3;
3154                 reg = ((modrm >> 3) & 7) | REX_R(s);
3155                 rm = (modrm & 7) | REX_B(s);
3156                 if (mod != 3) {
3157                     gen_lea_modrm(env, s, modrm);
3158                     gen_op_ld_v(s, ot, s->T1, s->A0);
3159                 } else if (op == OP_XORL && rm == reg) {
3160                     goto xor_zero;
3161                 } else {
3162                     gen_op_mov_v_reg(s, ot, s->T1, rm);
3163                 }
3164                 gen_op(s, op, ot, reg);
3165                 break;
3166             case 2: /* OP A, Iv */
3167                 val = insn_get(env, s, ot);
3168                 tcg_gen_movi_tl(s->T1, val);
3169                 gen_op(s, op, ot, OR_EAX);
3170                 break;
3171             }
3172         }
3173         break;
3174 
3175     case 0x82:
3176         if (CODE64(s))
3177             goto illegal_op;
3178         /* fall through */
3179     case 0x80: /* GRP1 */
3180     case 0x81:
3181     case 0x83:
3182         {
3183             int val;
3184 
3185             ot = mo_b_d(b, dflag);
3186 
3187             modrm = x86_ldub_code(env, s);
3188             mod = (modrm >> 6) & 3;
3189             rm = (modrm & 7) | REX_B(s);
3190             op = (modrm >> 3) & 7;
3191 
3192             if (mod != 3) {
3193                 if (b == 0x83)
3194                     s->rip_offset = 1;
3195                 else
3196                     s->rip_offset = insn_const_size(ot);
3197                 gen_lea_modrm(env, s, modrm);
3198                 opreg = OR_TMP0;
3199             } else {
3200                 opreg = rm;
3201             }
3202 
3203             switch(b) {
3204             default:
3205             case 0x80:
3206             case 0x81:
3207             case 0x82:
3208                 val = insn_get(env, s, ot);
3209                 break;
3210             case 0x83:
3211                 val = (int8_t)insn_get(env, s, MO_8);
3212                 break;
3213             }
3214             tcg_gen_movi_tl(s->T1, val);
3215             gen_op(s, op, ot, opreg);
3216         }
3217         break;
3218 
3219         /**************************/
3220         /* inc, dec, and other misc arith */
3221     case 0x40 ... 0x47: /* inc Gv */
3222         ot = dflag;
3223         gen_inc(s, ot, OR_EAX + (b & 7), 1);
3224         break;
3225     case 0x48 ... 0x4f: /* dec Gv */
3226         ot = dflag;
3227         gen_inc(s, ot, OR_EAX + (b & 7), -1);
3228         break;
3229     case 0xf6: /* GRP3 */
3230     case 0xf7:
3231         ot = mo_b_d(b, dflag);
3232 
3233         modrm = x86_ldub_code(env, s);
3234         mod = (modrm >> 6) & 3;
3235         rm = (modrm & 7) | REX_B(s);
3236         op = (modrm >> 3) & 7;
3237         if (mod != 3) {
3238             if (op == 0) {
3239                 s->rip_offset = insn_const_size(ot);
3240             }
3241             gen_lea_modrm(env, s, modrm);
3242             /* For those below that handle locked memory, don't load here.  */
3243             if (!(s->prefix & PREFIX_LOCK)
3244                 || op != 2) {
3245                 gen_op_ld_v(s, ot, s->T0, s->A0);
3246             }
3247         } else {
3248             gen_op_mov_v_reg(s, ot, s->T0, rm);
3249         }
3250 
3251         switch(op) {
3252         case 0: /* test */
3253             val = insn_get(env, s, ot);
3254             tcg_gen_movi_tl(s->T1, val);
3255             gen_op_testl_T0_T1_cc(s);
3256             set_cc_op(s, CC_OP_LOGICB + ot);
3257             break;
3258         case 2: /* not */
3259             if (s->prefix & PREFIX_LOCK) {
3260                 if (mod == 3) {
3261                     goto illegal_op;
3262                 }
3263                 tcg_gen_movi_tl(s->T0, ~0);
3264                 tcg_gen_atomic_xor_fetch_tl(s->T0, s->A0, s->T0,
3265                                             s->mem_index, ot | MO_LE);
3266             } else {
3267                 tcg_gen_not_tl(s->T0, s->T0);
3268                 if (mod != 3) {
3269                     gen_op_st_v(s, ot, s->T0, s->A0);
3270                 } else {
3271                     gen_op_mov_reg_v(s, ot, rm, s->T0);
3272                 }
3273             }
3274             break;
3275         case 3: /* neg */
3276             if (s->prefix & PREFIX_LOCK) {
3277                 TCGLabel *label1;
3278                 TCGv a0, t0, t1, t2;
3279 
3280                 if (mod == 3) {
3281                     goto illegal_op;
3282                 }
3283                 a0 = tcg_temp_local_new();
3284                 t0 = tcg_temp_local_new();
3285                 label1 = gen_new_label();
3286 
3287                 tcg_gen_mov_tl(a0, s->A0);
3288                 tcg_gen_mov_tl(t0, s->T0);
3289 
3290                 gen_set_label(label1);
3291                 t1 = tcg_temp_new();
3292                 t2 = tcg_temp_new();
3293                 tcg_gen_mov_tl(t2, t0);
3294                 tcg_gen_neg_tl(t1, t0);
3295                 tcg_gen_atomic_cmpxchg_tl(t0, a0, t0, t1,
3296                                           s->mem_index, ot | MO_LE);
3297                 tcg_temp_free(t1);
3298                 tcg_gen_brcond_tl(TCG_COND_NE, t0, t2, label1);
3299 
3300                 tcg_temp_free(t2);
3301                 tcg_temp_free(a0);
3302                 tcg_gen_mov_tl(s->T0, t0);
3303                 tcg_temp_free(t0);
3304             } else {
3305                 tcg_gen_neg_tl(s->T0, s->T0);
3306                 if (mod != 3) {
3307                     gen_op_st_v(s, ot, s->T0, s->A0);
3308                 } else {
3309                     gen_op_mov_reg_v(s, ot, rm, s->T0);
3310                 }
3311             }
3312             gen_op_update_neg_cc(s);
3313             set_cc_op(s, CC_OP_SUBB + ot);
3314             break;
3315         case 4: /* mul */
3316             switch(ot) {
3317             case MO_8:
3318                 gen_op_mov_v_reg(s, MO_8, s->T1, R_EAX);
3319                 tcg_gen_ext8u_tl(s->T0, s->T0);
3320                 tcg_gen_ext8u_tl(s->T1, s->T1);
3321                 /* XXX: use 32 bit mul which could be faster */
3322                 tcg_gen_mul_tl(s->T0, s->T0, s->T1);
3323                 gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
3324                 tcg_gen_mov_tl(cpu_cc_dst, s->T0);
3325                 tcg_gen_andi_tl(cpu_cc_src, s->T0, 0xff00);
3326                 set_cc_op(s, CC_OP_MULB);
3327                 break;
3328             case MO_16:
3329                 gen_op_mov_v_reg(s, MO_16, s->T1, R_EAX);
3330                 tcg_gen_ext16u_tl(s->T0, s->T0);
3331                 tcg_gen_ext16u_tl(s->T1, s->T1);
3332                 /* XXX: use 32 bit mul which could be faster */
3333                 tcg_gen_mul_tl(s->T0, s->T0, s->T1);
3334                 gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
3335                 tcg_gen_mov_tl(cpu_cc_dst, s->T0);
3336                 tcg_gen_shri_tl(s->T0, s->T0, 16);
3337                 gen_op_mov_reg_v(s, MO_16, R_EDX, s->T0);
3338                 tcg_gen_mov_tl(cpu_cc_src, s->T0);
3339                 set_cc_op(s, CC_OP_MULW);
3340                 break;
3341             default:
3342             case MO_32:
3343                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3344                 tcg_gen_trunc_tl_i32(s->tmp3_i32, cpu_regs[R_EAX]);
3345                 tcg_gen_mulu2_i32(s->tmp2_i32, s->tmp3_i32,
3346                                   s->tmp2_i32, s->tmp3_i32);
3347                 tcg_gen_extu_i32_tl(cpu_regs[R_EAX], s->tmp2_i32);
3348                 tcg_gen_extu_i32_tl(cpu_regs[R_EDX], s->tmp3_i32);
3349                 tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[R_EAX]);
3350                 tcg_gen_mov_tl(cpu_cc_src, cpu_regs[R_EDX]);
3351                 set_cc_op(s, CC_OP_MULL);
3352                 break;
3353 #ifdef TARGET_X86_64
3354             case MO_64:
3355                 tcg_gen_mulu2_i64(cpu_regs[R_EAX], cpu_regs[R_EDX],
3356                                   s->T0, cpu_regs[R_EAX]);
3357                 tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[R_EAX]);
3358                 tcg_gen_mov_tl(cpu_cc_src, cpu_regs[R_EDX]);
3359                 set_cc_op(s, CC_OP_MULQ);
3360                 break;
3361 #endif
3362             }
3363             break;
3364         case 5: /* imul */
3365             switch(ot) {
3366             case MO_8:
3367                 gen_op_mov_v_reg(s, MO_8, s->T1, R_EAX);
3368                 tcg_gen_ext8s_tl(s->T0, s->T0);
3369                 tcg_gen_ext8s_tl(s->T1, s->T1);
3370                 /* XXX: use 32 bit mul which could be faster */
3371                 tcg_gen_mul_tl(s->T0, s->T0, s->T1);
3372                 gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
3373                 tcg_gen_mov_tl(cpu_cc_dst, s->T0);
3374                 tcg_gen_ext8s_tl(s->tmp0, s->T0);
3375                 tcg_gen_sub_tl(cpu_cc_src, s->T0, s->tmp0);
3376                 set_cc_op(s, CC_OP_MULB);
3377                 break;
3378             case MO_16:
3379                 gen_op_mov_v_reg(s, MO_16, s->T1, R_EAX);
3380                 tcg_gen_ext16s_tl(s->T0, s->T0);
3381                 tcg_gen_ext16s_tl(s->T1, s->T1);
3382                 /* XXX: use 32 bit mul which could be faster */
3383                 tcg_gen_mul_tl(s->T0, s->T0, s->T1);
3384                 gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
3385                 tcg_gen_mov_tl(cpu_cc_dst, s->T0);
3386                 tcg_gen_ext16s_tl(s->tmp0, s->T0);
3387                 tcg_gen_sub_tl(cpu_cc_src, s->T0, s->tmp0);
3388                 tcg_gen_shri_tl(s->T0, s->T0, 16);
3389                 gen_op_mov_reg_v(s, MO_16, R_EDX, s->T0);
3390                 set_cc_op(s, CC_OP_MULW);
3391                 break;
3392             default:
3393             case MO_32:
3394                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3395                 tcg_gen_trunc_tl_i32(s->tmp3_i32, cpu_regs[R_EAX]);
3396                 tcg_gen_muls2_i32(s->tmp2_i32, s->tmp3_i32,
3397                                   s->tmp2_i32, s->tmp3_i32);
3398                 tcg_gen_extu_i32_tl(cpu_regs[R_EAX], s->tmp2_i32);
3399                 tcg_gen_extu_i32_tl(cpu_regs[R_EDX], s->tmp3_i32);
3400                 tcg_gen_sari_i32(s->tmp2_i32, s->tmp2_i32, 31);
3401                 tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[R_EAX]);
3402                 tcg_gen_sub_i32(s->tmp2_i32, s->tmp2_i32, s->tmp3_i32);
3403                 tcg_gen_extu_i32_tl(cpu_cc_src, s->tmp2_i32);
3404                 set_cc_op(s, CC_OP_MULL);
3405                 break;
3406 #ifdef TARGET_X86_64
3407             case MO_64:
3408                 tcg_gen_muls2_i64(cpu_regs[R_EAX], cpu_regs[R_EDX],
3409                                   s->T0, cpu_regs[R_EAX]);
3410                 tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[R_EAX]);
3411                 tcg_gen_sari_tl(cpu_cc_src, cpu_regs[R_EAX], 63);
3412                 tcg_gen_sub_tl(cpu_cc_src, cpu_cc_src, cpu_regs[R_EDX]);
3413                 set_cc_op(s, CC_OP_MULQ);
3414                 break;
3415 #endif
3416             }
3417             break;
3418         case 6: /* div */
3419             switch(ot) {
3420             case MO_8:
3421                 gen_helper_divb_AL(cpu_env, s->T0);
3422                 break;
3423             case MO_16:
3424                 gen_helper_divw_AX(cpu_env, s->T0);
3425                 break;
3426             default:
3427             case MO_32:
3428                 gen_helper_divl_EAX(cpu_env, s->T0);
3429                 break;
3430 #ifdef TARGET_X86_64
3431             case MO_64:
3432                 gen_helper_divq_EAX(cpu_env, s->T0);
3433                 break;
3434 #endif
3435             }
3436             break;
3437         case 7: /* idiv */
3438             switch(ot) {
3439             case MO_8:
3440                 gen_helper_idivb_AL(cpu_env, s->T0);
3441                 break;
3442             case MO_16:
3443                 gen_helper_idivw_AX(cpu_env, s->T0);
3444                 break;
3445             default:
3446             case MO_32:
3447                 gen_helper_idivl_EAX(cpu_env, s->T0);
3448                 break;
3449 #ifdef TARGET_X86_64
3450             case MO_64:
3451                 gen_helper_idivq_EAX(cpu_env, s->T0);
3452                 break;
3453 #endif
3454             }
3455             break;
3456         default:
3457             goto unknown_op;
3458         }
3459         break;
3460 
3461     case 0xfe: /* GRP4 */
3462     case 0xff: /* GRP5 */
3463         ot = mo_b_d(b, dflag);
3464 
3465         modrm = x86_ldub_code(env, s);
3466         mod = (modrm >> 6) & 3;
3467         rm = (modrm & 7) | REX_B(s);
3468         op = (modrm >> 3) & 7;
3469         if (op >= 2 && b == 0xfe) {
3470             goto unknown_op;
3471         }
3472         if (CODE64(s)) {
3473             if (op == 2 || op == 4) {
3474                 /* operand size for jumps is 64 bit */
3475                 ot = MO_64;
3476             } else if (op == 3 || op == 5) {
3477                 ot = dflag != MO_16 ? MO_32 + REX_W(s) : MO_16;
3478             } else if (op == 6) {
3479                 /* default push size is 64 bit */
3480                 ot = mo_pushpop(s, dflag);
3481             }
3482         }
3483         if (mod != 3) {
3484             gen_lea_modrm(env, s, modrm);
3485             if (op >= 2 && op != 3 && op != 5)
3486                 gen_op_ld_v(s, ot, s->T0, s->A0);
3487         } else {
3488             gen_op_mov_v_reg(s, ot, s->T0, rm);
3489         }
3490 
3491         switch(op) {
3492         case 0: /* inc Ev */
3493             if (mod != 3)
3494                 opreg = OR_TMP0;
3495             else
3496                 opreg = rm;
3497             gen_inc(s, ot, opreg, 1);
3498             break;
3499         case 1: /* dec Ev */
3500             if (mod != 3)
3501                 opreg = OR_TMP0;
3502             else
3503                 opreg = rm;
3504             gen_inc(s, ot, opreg, -1);
3505             break;
3506         case 2: /* call Ev */
3507             /* XXX: optimize if memory (no 'and' is necessary) */
3508             if (dflag == MO_16) {
3509                 tcg_gen_ext16u_tl(s->T0, s->T0);
3510             }
3511             gen_push_v(s, eip_next_tl(s));
3512             gen_op_jmp_v(s, s->T0);
3513             gen_bnd_jmp(s);
3514             s->base.is_jmp = DISAS_JUMP;
3515             break;
3516         case 3: /* lcall Ev */
3517             if (mod == 3) {
3518                 goto illegal_op;
3519             }
3520             gen_op_ld_v(s, ot, s->T1, s->A0);
3521             gen_add_A0_im(s, 1 << ot);
3522             gen_op_ld_v(s, MO_16, s->T0, s->A0);
3523         do_lcall:
3524             if (PE(s) && !VM86(s)) {
3525                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3526                 gen_helper_lcall_protected(cpu_env, s->tmp2_i32, s->T1,
3527                                            tcg_constant_i32(dflag - 1),
3528                                            eip_next_tl(s));
3529             } else {
3530                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3531                 tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T1);
3532                 gen_helper_lcall_real(cpu_env, s->tmp2_i32, s->tmp3_i32,
3533                                       tcg_constant_i32(dflag - 1),
3534                                       eip_next_i32(s));
3535             }
3536             s->base.is_jmp = DISAS_JUMP;
3537             break;
3538         case 4: /* jmp Ev */
3539             if (dflag == MO_16) {
3540                 tcg_gen_ext16u_tl(s->T0, s->T0);
3541             }
3542             gen_op_jmp_v(s, s->T0);
3543             gen_bnd_jmp(s);
3544             s->base.is_jmp = DISAS_JUMP;
3545             break;
3546         case 5: /* ljmp Ev */
3547             if (mod == 3) {
3548                 goto illegal_op;
3549             }
3550             gen_op_ld_v(s, ot, s->T1, s->A0);
3551             gen_add_A0_im(s, 1 << ot);
3552             gen_op_ld_v(s, MO_16, s->T0, s->A0);
3553         do_ljmp:
3554             if (PE(s) && !VM86(s)) {
3555                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3556                 gen_helper_ljmp_protected(cpu_env, s->tmp2_i32, s->T1,
3557                                           eip_next_tl(s));
3558             } else {
3559                 gen_op_movl_seg_T0_vm(s, R_CS);
3560                 gen_op_jmp_v(s, s->T1);
3561             }
3562             s->base.is_jmp = DISAS_JUMP;
3563             break;
3564         case 6: /* push Ev */
3565             gen_push_v(s, s->T0);
3566             break;
3567         default:
3568             goto unknown_op;
3569         }
3570         break;
3571 
3572     case 0x84: /* test Ev, Gv */
3573     case 0x85:
3574         ot = mo_b_d(b, dflag);
3575 
3576         modrm = x86_ldub_code(env, s);
3577         reg = ((modrm >> 3) & 7) | REX_R(s);
3578 
3579         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
3580         gen_op_mov_v_reg(s, ot, s->T1, reg);
3581         gen_op_testl_T0_T1_cc(s);
3582         set_cc_op(s, CC_OP_LOGICB + ot);
3583         break;
3584 
3585     case 0xa8: /* test eAX, Iv */
3586     case 0xa9:
3587         ot = mo_b_d(b, dflag);
3588         val = insn_get(env, s, ot);
3589 
3590         gen_op_mov_v_reg(s, ot, s->T0, OR_EAX);
3591         tcg_gen_movi_tl(s->T1, val);
3592         gen_op_testl_T0_T1_cc(s);
3593         set_cc_op(s, CC_OP_LOGICB + ot);
3594         break;
3595 
3596     case 0x98: /* CWDE/CBW */
3597         switch (dflag) {
3598 #ifdef TARGET_X86_64
3599         case MO_64:
3600             gen_op_mov_v_reg(s, MO_32, s->T0, R_EAX);
3601             tcg_gen_ext32s_tl(s->T0, s->T0);
3602             gen_op_mov_reg_v(s, MO_64, R_EAX, s->T0);
3603             break;
3604 #endif
3605         case MO_32:
3606             gen_op_mov_v_reg(s, MO_16, s->T0, R_EAX);
3607             tcg_gen_ext16s_tl(s->T0, s->T0);
3608             gen_op_mov_reg_v(s, MO_32, R_EAX, s->T0);
3609             break;
3610         case MO_16:
3611             gen_op_mov_v_reg(s, MO_8, s->T0, R_EAX);
3612             tcg_gen_ext8s_tl(s->T0, s->T0);
3613             gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
3614             break;
3615         default:
3616             tcg_abort();
3617         }
3618         break;
3619     case 0x99: /* CDQ/CWD */
3620         switch (dflag) {
3621 #ifdef TARGET_X86_64
3622         case MO_64:
3623             gen_op_mov_v_reg(s, MO_64, s->T0, R_EAX);
3624             tcg_gen_sari_tl(s->T0, s->T0, 63);
3625             gen_op_mov_reg_v(s, MO_64, R_EDX, s->T0);
3626             break;
3627 #endif
3628         case MO_32:
3629             gen_op_mov_v_reg(s, MO_32, s->T0, R_EAX);
3630             tcg_gen_ext32s_tl(s->T0, s->T0);
3631             tcg_gen_sari_tl(s->T0, s->T0, 31);
3632             gen_op_mov_reg_v(s, MO_32, R_EDX, s->T0);
3633             break;
3634         case MO_16:
3635             gen_op_mov_v_reg(s, MO_16, s->T0, R_EAX);
3636             tcg_gen_ext16s_tl(s->T0, s->T0);
3637             tcg_gen_sari_tl(s->T0, s->T0, 15);
3638             gen_op_mov_reg_v(s, MO_16, R_EDX, s->T0);
3639             break;
3640         default:
3641             tcg_abort();
3642         }
3643         break;
3644     case 0x1af: /* imul Gv, Ev */
3645     case 0x69: /* imul Gv, Ev, I */
3646     case 0x6b:
3647         ot = dflag;
3648         modrm = x86_ldub_code(env, s);
3649         reg = ((modrm >> 3) & 7) | REX_R(s);
3650         if (b == 0x69)
3651             s->rip_offset = insn_const_size(ot);
3652         else if (b == 0x6b)
3653             s->rip_offset = 1;
3654         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
3655         if (b == 0x69) {
3656             val = insn_get(env, s, ot);
3657             tcg_gen_movi_tl(s->T1, val);
3658         } else if (b == 0x6b) {
3659             val = (int8_t)insn_get(env, s, MO_8);
3660             tcg_gen_movi_tl(s->T1, val);
3661         } else {
3662             gen_op_mov_v_reg(s, ot, s->T1, reg);
3663         }
3664         switch (ot) {
3665 #ifdef TARGET_X86_64
3666         case MO_64:
3667             tcg_gen_muls2_i64(cpu_regs[reg], s->T1, s->T0, s->T1);
3668             tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[reg]);
3669             tcg_gen_sari_tl(cpu_cc_src, cpu_cc_dst, 63);
3670             tcg_gen_sub_tl(cpu_cc_src, cpu_cc_src, s->T1);
3671             break;
3672 #endif
3673         case MO_32:
3674             tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
3675             tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T1);
3676             tcg_gen_muls2_i32(s->tmp2_i32, s->tmp3_i32,
3677                               s->tmp2_i32, s->tmp3_i32);
3678             tcg_gen_extu_i32_tl(cpu_regs[reg], s->tmp2_i32);
3679             tcg_gen_sari_i32(s->tmp2_i32, s->tmp2_i32, 31);
3680             tcg_gen_mov_tl(cpu_cc_dst, cpu_regs[reg]);
3681             tcg_gen_sub_i32(s->tmp2_i32, s->tmp2_i32, s->tmp3_i32);
3682             tcg_gen_extu_i32_tl(cpu_cc_src, s->tmp2_i32);
3683             break;
3684         default:
3685             tcg_gen_ext16s_tl(s->T0, s->T0);
3686             tcg_gen_ext16s_tl(s->T1, s->T1);
3687             /* XXX: use 32 bit mul which could be faster */
3688             tcg_gen_mul_tl(s->T0, s->T0, s->T1);
3689             tcg_gen_mov_tl(cpu_cc_dst, s->T0);
3690             tcg_gen_ext16s_tl(s->tmp0, s->T0);
3691             tcg_gen_sub_tl(cpu_cc_src, s->T0, s->tmp0);
3692             gen_op_mov_reg_v(s, ot, reg, s->T0);
3693             break;
3694         }
3695         set_cc_op(s, CC_OP_MULB + ot);
3696         break;
3697     case 0x1c0:
3698     case 0x1c1: /* xadd Ev, Gv */
3699         ot = mo_b_d(b, dflag);
3700         modrm = x86_ldub_code(env, s);
3701         reg = ((modrm >> 3) & 7) | REX_R(s);
3702         mod = (modrm >> 6) & 3;
3703         gen_op_mov_v_reg(s, ot, s->T0, reg);
3704         if (mod == 3) {
3705             rm = (modrm & 7) | REX_B(s);
3706             gen_op_mov_v_reg(s, ot, s->T1, rm);
3707             tcg_gen_add_tl(s->T0, s->T0, s->T1);
3708             gen_op_mov_reg_v(s, ot, reg, s->T1);
3709             gen_op_mov_reg_v(s, ot, rm, s->T0);
3710         } else {
3711             gen_lea_modrm(env, s, modrm);
3712             if (s->prefix & PREFIX_LOCK) {
3713                 tcg_gen_atomic_fetch_add_tl(s->T1, s->A0, s->T0,
3714                                             s->mem_index, ot | MO_LE);
3715                 tcg_gen_add_tl(s->T0, s->T0, s->T1);
3716             } else {
3717                 gen_op_ld_v(s, ot, s->T1, s->A0);
3718                 tcg_gen_add_tl(s->T0, s->T0, s->T1);
3719                 gen_op_st_v(s, ot, s->T0, s->A0);
3720             }
3721             gen_op_mov_reg_v(s, ot, reg, s->T1);
3722         }
3723         gen_op_update2_cc(s);
3724         set_cc_op(s, CC_OP_ADDB + ot);
3725         break;
3726     case 0x1b0:
3727     case 0x1b1: /* cmpxchg Ev, Gv */
3728         {
3729             TCGv oldv, newv, cmpv;
3730 
3731             ot = mo_b_d(b, dflag);
3732             modrm = x86_ldub_code(env, s);
3733             reg = ((modrm >> 3) & 7) | REX_R(s);
3734             mod = (modrm >> 6) & 3;
3735             oldv = tcg_temp_new();
3736             newv = tcg_temp_new();
3737             cmpv = tcg_temp_new();
3738             gen_op_mov_v_reg(s, ot, newv, reg);
3739             tcg_gen_mov_tl(cmpv, cpu_regs[R_EAX]);
3740 
3741             if (s->prefix & PREFIX_LOCK) {
3742                 if (mod == 3) {
3743                     goto illegal_op;
3744                 }
3745                 gen_lea_modrm(env, s, modrm);
3746                 tcg_gen_atomic_cmpxchg_tl(oldv, s->A0, cmpv, newv,
3747                                           s->mem_index, ot | MO_LE);
3748                 gen_op_mov_reg_v(s, ot, R_EAX, oldv);
3749             } else {
3750                 if (mod == 3) {
3751                     rm = (modrm & 7) | REX_B(s);
3752                     gen_op_mov_v_reg(s, ot, oldv, rm);
3753                 } else {
3754                     gen_lea_modrm(env, s, modrm);
3755                     gen_op_ld_v(s, ot, oldv, s->A0);
3756                     rm = 0; /* avoid warning */
3757                 }
3758                 gen_extu(ot, oldv);
3759                 gen_extu(ot, cmpv);
3760                 /* store value = (old == cmp ? new : old);  */
3761                 tcg_gen_movcond_tl(TCG_COND_EQ, newv, oldv, cmpv, newv, oldv);
3762                 if (mod == 3) {
3763                     gen_op_mov_reg_v(s, ot, R_EAX, oldv);
3764                     gen_op_mov_reg_v(s, ot, rm, newv);
3765                 } else {
3766                     /* Perform an unconditional store cycle like physical cpu;
3767                        must be before changing accumulator to ensure
3768                        idempotency if the store faults and the instruction
3769                        is restarted */
3770                     gen_op_st_v(s, ot, newv, s->A0);
3771                     gen_op_mov_reg_v(s, ot, R_EAX, oldv);
3772                 }
3773             }
3774             tcg_gen_mov_tl(cpu_cc_src, oldv);
3775             tcg_gen_mov_tl(s->cc_srcT, cmpv);
3776             tcg_gen_sub_tl(cpu_cc_dst, cmpv, oldv);
3777             set_cc_op(s, CC_OP_SUBB + ot);
3778             tcg_temp_free(oldv);
3779             tcg_temp_free(newv);
3780             tcg_temp_free(cmpv);
3781         }
3782         break;
3783     case 0x1c7: /* cmpxchg8b */
3784         modrm = x86_ldub_code(env, s);
3785         mod = (modrm >> 6) & 3;
3786         switch ((modrm >> 3) & 7) {
3787         case 1: /* CMPXCHG8, CMPXCHG16 */
3788             if (mod == 3) {
3789                 goto illegal_op;
3790             }
3791 #ifdef TARGET_X86_64
3792             if (dflag == MO_64) {
3793                 if (!(s->cpuid_ext_features & CPUID_EXT_CX16)) {
3794                     goto illegal_op;
3795                 }
3796                 gen_lea_modrm(env, s, modrm);
3797                 if ((s->prefix & PREFIX_LOCK) &&
3798                     (tb_cflags(s->base.tb) & CF_PARALLEL)) {
3799                     gen_helper_cmpxchg16b(cpu_env, s->A0);
3800                 } else {
3801                     gen_helper_cmpxchg16b_unlocked(cpu_env, s->A0);
3802                 }
3803                 set_cc_op(s, CC_OP_EFLAGS);
3804                 break;
3805             }
3806 #endif
3807             if (!(s->cpuid_features & CPUID_CX8)) {
3808                 goto illegal_op;
3809             }
3810             gen_lea_modrm(env, s, modrm);
3811             if ((s->prefix & PREFIX_LOCK) &&
3812                 (tb_cflags(s->base.tb) & CF_PARALLEL)) {
3813                 gen_helper_cmpxchg8b(cpu_env, s->A0);
3814             } else {
3815                 gen_helper_cmpxchg8b_unlocked(cpu_env, s->A0);
3816             }
3817             set_cc_op(s, CC_OP_EFLAGS);
3818             break;
3819 
3820         case 7: /* RDSEED */
3821         case 6: /* RDRAND */
3822             if (mod != 3 ||
3823                 (s->prefix & (PREFIX_LOCK | PREFIX_REPZ | PREFIX_REPNZ)) ||
3824                 !(s->cpuid_ext_features & CPUID_EXT_RDRAND)) {
3825                 goto illegal_op;
3826             }
3827             if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
3828                 gen_io_start();
3829                 s->base.is_jmp = DISAS_TOO_MANY;
3830             }
3831             gen_helper_rdrand(s->T0, cpu_env);
3832             rm = (modrm & 7) | REX_B(s);
3833             gen_op_mov_reg_v(s, dflag, rm, s->T0);
3834             set_cc_op(s, CC_OP_EFLAGS);
3835             break;
3836 
3837         default:
3838             goto illegal_op;
3839         }
3840         break;
3841 
3842         /**************************/
3843         /* push/pop */
3844     case 0x50 ... 0x57: /* push */
3845         gen_op_mov_v_reg(s, MO_32, s->T0, (b & 7) | REX_B(s));
3846         gen_push_v(s, s->T0);
3847         break;
3848     case 0x58 ... 0x5f: /* pop */
3849         ot = gen_pop_T0(s);
3850         /* NOTE: order is important for pop %sp */
3851         gen_pop_update(s, ot);
3852         gen_op_mov_reg_v(s, ot, (b & 7) | REX_B(s), s->T0);
3853         break;
3854     case 0x60: /* pusha */
3855         if (CODE64(s))
3856             goto illegal_op;
3857         gen_pusha(s);
3858         break;
3859     case 0x61: /* popa */
3860         if (CODE64(s))
3861             goto illegal_op;
3862         gen_popa(s);
3863         break;
3864     case 0x68: /* push Iv */
3865     case 0x6a:
3866         ot = mo_pushpop(s, dflag);
3867         if (b == 0x68)
3868             val = insn_get(env, s, ot);
3869         else
3870             val = (int8_t)insn_get(env, s, MO_8);
3871         tcg_gen_movi_tl(s->T0, val);
3872         gen_push_v(s, s->T0);
3873         break;
3874     case 0x8f: /* pop Ev */
3875         modrm = x86_ldub_code(env, s);
3876         mod = (modrm >> 6) & 3;
3877         ot = gen_pop_T0(s);
3878         if (mod == 3) {
3879             /* NOTE: order is important for pop %sp */
3880             gen_pop_update(s, ot);
3881             rm = (modrm & 7) | REX_B(s);
3882             gen_op_mov_reg_v(s, ot, rm, s->T0);
3883         } else {
3884             /* NOTE: order is important too for MMU exceptions */
3885             s->popl_esp_hack = 1 << ot;
3886             gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 1);
3887             s->popl_esp_hack = 0;
3888             gen_pop_update(s, ot);
3889         }
3890         break;
3891     case 0xc8: /* enter */
3892         {
3893             int level;
3894             val = x86_lduw_code(env, s);
3895             level = x86_ldub_code(env, s);
3896             gen_enter(s, val, level);
3897         }
3898         break;
3899     case 0xc9: /* leave */
3900         gen_leave(s);
3901         break;
3902     case 0x06: /* push es */
3903     case 0x0e: /* push cs */
3904     case 0x16: /* push ss */
3905     case 0x1e: /* push ds */
3906         if (CODE64(s))
3907             goto illegal_op;
3908         gen_op_movl_T0_seg(s, b >> 3);
3909         gen_push_v(s, s->T0);
3910         break;
3911     case 0x1a0: /* push fs */
3912     case 0x1a8: /* push gs */
3913         gen_op_movl_T0_seg(s, (b >> 3) & 7);
3914         gen_push_v(s, s->T0);
3915         break;
3916     case 0x07: /* pop es */
3917     case 0x17: /* pop ss */
3918     case 0x1f: /* pop ds */
3919         if (CODE64(s))
3920             goto illegal_op;
3921         reg = b >> 3;
3922         ot = gen_pop_T0(s);
3923         gen_movl_seg_T0(s, reg);
3924         gen_pop_update(s, ot);
3925         break;
3926     case 0x1a1: /* pop fs */
3927     case 0x1a9: /* pop gs */
3928         ot = gen_pop_T0(s);
3929         gen_movl_seg_T0(s, (b >> 3) & 7);
3930         gen_pop_update(s, ot);
3931         break;
3932 
3933         /**************************/
3934         /* mov */
3935     case 0x88:
3936     case 0x89: /* mov Gv, Ev */
3937         ot = mo_b_d(b, dflag);
3938         modrm = x86_ldub_code(env, s);
3939         reg = ((modrm >> 3) & 7) | REX_R(s);
3940 
3941         /* generate a generic store */
3942         gen_ldst_modrm(env, s, modrm, ot, reg, 1);
3943         break;
3944     case 0xc6:
3945     case 0xc7: /* mov Ev, Iv */
3946         ot = mo_b_d(b, dflag);
3947         modrm = x86_ldub_code(env, s);
3948         mod = (modrm >> 6) & 3;
3949         if (mod != 3) {
3950             s->rip_offset = insn_const_size(ot);
3951             gen_lea_modrm(env, s, modrm);
3952         }
3953         val = insn_get(env, s, ot);
3954         tcg_gen_movi_tl(s->T0, val);
3955         if (mod != 3) {
3956             gen_op_st_v(s, ot, s->T0, s->A0);
3957         } else {
3958             gen_op_mov_reg_v(s, ot, (modrm & 7) | REX_B(s), s->T0);
3959         }
3960         break;
3961     case 0x8a:
3962     case 0x8b: /* mov Ev, Gv */
3963         ot = mo_b_d(b, dflag);
3964         modrm = x86_ldub_code(env, s);
3965         reg = ((modrm >> 3) & 7) | REX_R(s);
3966 
3967         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
3968         gen_op_mov_reg_v(s, ot, reg, s->T0);
3969         break;
3970     case 0x8e: /* mov seg, Gv */
3971         modrm = x86_ldub_code(env, s);
3972         reg = (modrm >> 3) & 7;
3973         if (reg >= 6 || reg == R_CS)
3974             goto illegal_op;
3975         gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
3976         gen_movl_seg_T0(s, reg);
3977         break;
3978     case 0x8c: /* mov Gv, seg */
3979         modrm = x86_ldub_code(env, s);
3980         reg = (modrm >> 3) & 7;
3981         mod = (modrm >> 6) & 3;
3982         if (reg >= 6)
3983             goto illegal_op;
3984         gen_op_movl_T0_seg(s, reg);
3985         ot = mod == 3 ? dflag : MO_16;
3986         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 1);
3987         break;
3988 
3989     case 0x1b6: /* movzbS Gv, Eb */
3990     case 0x1b7: /* movzwS Gv, Eb */
3991     case 0x1be: /* movsbS Gv, Eb */
3992     case 0x1bf: /* movswS Gv, Eb */
3993         {
3994             MemOp d_ot;
3995             MemOp s_ot;
3996 
3997             /* d_ot is the size of destination */
3998             d_ot = dflag;
3999             /* ot is the size of source */
4000             ot = (b & 1) + MO_8;
4001             /* s_ot is the sign+size of source */
4002             s_ot = b & 8 ? MO_SIGN | ot : ot;
4003 
4004             modrm = x86_ldub_code(env, s);
4005             reg = ((modrm >> 3) & 7) | REX_R(s);
4006             mod = (modrm >> 6) & 3;
4007             rm = (modrm & 7) | REX_B(s);
4008 
4009             if (mod == 3) {
4010                 if (s_ot == MO_SB && byte_reg_is_xH(s, rm)) {
4011                     tcg_gen_sextract_tl(s->T0, cpu_regs[rm - 4], 8, 8);
4012                 } else {
4013                     gen_op_mov_v_reg(s, ot, s->T0, rm);
4014                     switch (s_ot) {
4015                     case MO_UB:
4016                         tcg_gen_ext8u_tl(s->T0, s->T0);
4017                         break;
4018                     case MO_SB:
4019                         tcg_gen_ext8s_tl(s->T0, s->T0);
4020                         break;
4021                     case MO_UW:
4022                         tcg_gen_ext16u_tl(s->T0, s->T0);
4023                         break;
4024                     default:
4025                     case MO_SW:
4026                         tcg_gen_ext16s_tl(s->T0, s->T0);
4027                         break;
4028                     }
4029                 }
4030                 gen_op_mov_reg_v(s, d_ot, reg, s->T0);
4031             } else {
4032                 gen_lea_modrm(env, s, modrm);
4033                 gen_op_ld_v(s, s_ot, s->T0, s->A0);
4034                 gen_op_mov_reg_v(s, d_ot, reg, s->T0);
4035             }
4036         }
4037         break;
4038 
4039     case 0x8d: /* lea */
4040         modrm = x86_ldub_code(env, s);
4041         mod = (modrm >> 6) & 3;
4042         if (mod == 3)
4043             goto illegal_op;
4044         reg = ((modrm >> 3) & 7) | REX_R(s);
4045         {
4046             AddressParts a = gen_lea_modrm_0(env, s, modrm);
4047             TCGv ea = gen_lea_modrm_1(s, a, false);
4048             gen_lea_v_seg(s, s->aflag, ea, -1, -1);
4049             gen_op_mov_reg_v(s, dflag, reg, s->A0);
4050         }
4051         break;
4052 
4053     case 0xa0: /* mov EAX, Ov */
4054     case 0xa1:
4055     case 0xa2: /* mov Ov, EAX */
4056     case 0xa3:
4057         {
4058             target_ulong offset_addr;
4059 
4060             ot = mo_b_d(b, dflag);
4061             offset_addr = insn_get_addr(env, s, s->aflag);
4062             tcg_gen_movi_tl(s->A0, offset_addr);
4063             gen_add_A0_ds_seg(s);
4064             if ((b & 2) == 0) {
4065                 gen_op_ld_v(s, ot, s->T0, s->A0);
4066                 gen_op_mov_reg_v(s, ot, R_EAX, s->T0);
4067             } else {
4068                 gen_op_mov_v_reg(s, ot, s->T0, R_EAX);
4069                 gen_op_st_v(s, ot, s->T0, s->A0);
4070             }
4071         }
4072         break;
4073     case 0xd7: /* xlat */
4074         tcg_gen_mov_tl(s->A0, cpu_regs[R_EBX]);
4075         tcg_gen_ext8u_tl(s->T0, cpu_regs[R_EAX]);
4076         tcg_gen_add_tl(s->A0, s->A0, s->T0);
4077         gen_extu(s->aflag, s->A0);
4078         gen_add_A0_ds_seg(s);
4079         gen_op_ld_v(s, MO_8, s->T0, s->A0);
4080         gen_op_mov_reg_v(s, MO_8, R_EAX, s->T0);
4081         break;
4082     case 0xb0 ... 0xb7: /* mov R, Ib */
4083         val = insn_get(env, s, MO_8);
4084         tcg_gen_movi_tl(s->T0, val);
4085         gen_op_mov_reg_v(s, MO_8, (b & 7) | REX_B(s), s->T0);
4086         break;
4087     case 0xb8 ... 0xbf: /* mov R, Iv */
4088 #ifdef TARGET_X86_64
4089         if (dflag == MO_64) {
4090             uint64_t tmp;
4091             /* 64 bit case */
4092             tmp = x86_ldq_code(env, s);
4093             reg = (b & 7) | REX_B(s);
4094             tcg_gen_movi_tl(s->T0, tmp);
4095             gen_op_mov_reg_v(s, MO_64, reg, s->T0);
4096         } else
4097 #endif
4098         {
4099             ot = dflag;
4100             val = insn_get(env, s, ot);
4101             reg = (b & 7) | REX_B(s);
4102             tcg_gen_movi_tl(s->T0, val);
4103             gen_op_mov_reg_v(s, ot, reg, s->T0);
4104         }
4105         break;
4106 
4107     case 0x91 ... 0x97: /* xchg R, EAX */
4108     do_xchg_reg_eax:
4109         ot = dflag;
4110         reg = (b & 7) | REX_B(s);
4111         rm = R_EAX;
4112         goto do_xchg_reg;
4113     case 0x86:
4114     case 0x87: /* xchg Ev, Gv */
4115         ot = mo_b_d(b, dflag);
4116         modrm = x86_ldub_code(env, s);
4117         reg = ((modrm >> 3) & 7) | REX_R(s);
4118         mod = (modrm >> 6) & 3;
4119         if (mod == 3) {
4120             rm = (modrm & 7) | REX_B(s);
4121         do_xchg_reg:
4122             gen_op_mov_v_reg(s, ot, s->T0, reg);
4123             gen_op_mov_v_reg(s, ot, s->T1, rm);
4124             gen_op_mov_reg_v(s, ot, rm, s->T0);
4125             gen_op_mov_reg_v(s, ot, reg, s->T1);
4126         } else {
4127             gen_lea_modrm(env, s, modrm);
4128             gen_op_mov_v_reg(s, ot, s->T0, reg);
4129             /* for xchg, lock is implicit */
4130             tcg_gen_atomic_xchg_tl(s->T1, s->A0, s->T0,
4131                                    s->mem_index, ot | MO_LE);
4132             gen_op_mov_reg_v(s, ot, reg, s->T1);
4133         }
4134         break;
4135     case 0xc4: /* les Gv */
4136         /* In CODE64 this is VEX3; see above.  */
4137         op = R_ES;
4138         goto do_lxx;
4139     case 0xc5: /* lds Gv */
4140         /* In CODE64 this is VEX2; see above.  */
4141         op = R_DS;
4142         goto do_lxx;
4143     case 0x1b2: /* lss Gv */
4144         op = R_SS;
4145         goto do_lxx;
4146     case 0x1b4: /* lfs Gv */
4147         op = R_FS;
4148         goto do_lxx;
4149     case 0x1b5: /* lgs Gv */
4150         op = R_GS;
4151     do_lxx:
4152         ot = dflag != MO_16 ? MO_32 : MO_16;
4153         modrm = x86_ldub_code(env, s);
4154         reg = ((modrm >> 3) & 7) | REX_R(s);
4155         mod = (modrm >> 6) & 3;
4156         if (mod == 3)
4157             goto illegal_op;
4158         gen_lea_modrm(env, s, modrm);
4159         gen_op_ld_v(s, ot, s->T1, s->A0);
4160         gen_add_A0_im(s, 1 << ot);
4161         /* load the segment first to handle exceptions properly */
4162         gen_op_ld_v(s, MO_16, s->T0, s->A0);
4163         gen_movl_seg_T0(s, op);
4164         /* then put the data */
4165         gen_op_mov_reg_v(s, ot, reg, s->T1);
4166         break;
4167 
4168         /************************/
4169         /* shifts */
4170     case 0xc0:
4171     case 0xc1:
4172         /* shift Ev,Ib */
4173         shift = 2;
4174     grp2:
4175         {
4176             ot = mo_b_d(b, dflag);
4177             modrm = x86_ldub_code(env, s);
4178             mod = (modrm >> 6) & 3;
4179             op = (modrm >> 3) & 7;
4180 
4181             if (mod != 3) {
4182                 if (shift == 2) {
4183                     s->rip_offset = 1;
4184                 }
4185                 gen_lea_modrm(env, s, modrm);
4186                 opreg = OR_TMP0;
4187             } else {
4188                 opreg = (modrm & 7) | REX_B(s);
4189             }
4190 
4191             /* simpler op */
4192             if (shift == 0) {
4193                 gen_shift(s, op, ot, opreg, OR_ECX);
4194             } else {
4195                 if (shift == 2) {
4196                     shift = x86_ldub_code(env, s);
4197                 }
4198                 gen_shifti(s, op, ot, opreg, shift);
4199             }
4200         }
4201         break;
4202     case 0xd0:
4203     case 0xd1:
4204         /* shift Ev,1 */
4205         shift = 1;
4206         goto grp2;
4207     case 0xd2:
4208     case 0xd3:
4209         /* shift Ev,cl */
4210         shift = 0;
4211         goto grp2;
4212 
4213     case 0x1a4: /* shld imm */
4214         op = 0;
4215         shift = 1;
4216         goto do_shiftd;
4217     case 0x1a5: /* shld cl */
4218         op = 0;
4219         shift = 0;
4220         goto do_shiftd;
4221     case 0x1ac: /* shrd imm */
4222         op = 1;
4223         shift = 1;
4224         goto do_shiftd;
4225     case 0x1ad: /* shrd cl */
4226         op = 1;
4227         shift = 0;
4228     do_shiftd:
4229         ot = dflag;
4230         modrm = x86_ldub_code(env, s);
4231         mod = (modrm >> 6) & 3;
4232         rm = (modrm & 7) | REX_B(s);
4233         reg = ((modrm >> 3) & 7) | REX_R(s);
4234         if (mod != 3) {
4235             gen_lea_modrm(env, s, modrm);
4236             opreg = OR_TMP0;
4237         } else {
4238             opreg = rm;
4239         }
4240         gen_op_mov_v_reg(s, ot, s->T1, reg);
4241 
4242         if (shift) {
4243             TCGv imm = tcg_const_tl(x86_ldub_code(env, s));
4244             gen_shiftd_rm_T1(s, ot, opreg, op, imm);
4245             tcg_temp_free(imm);
4246         } else {
4247             gen_shiftd_rm_T1(s, ot, opreg, op, cpu_regs[R_ECX]);
4248         }
4249         break;
4250 
4251         /************************/
4252         /* floats */
4253     case 0xd8 ... 0xdf:
4254         {
4255             bool update_fip = true;
4256 
4257             if (s->flags & (HF_EM_MASK | HF_TS_MASK)) {
4258                 /* if CR0.EM or CR0.TS are set, generate an FPU exception */
4259                 /* XXX: what to do if illegal op ? */
4260                 gen_exception(s, EXCP07_PREX);
4261                 break;
4262             }
4263             modrm = x86_ldub_code(env, s);
4264             mod = (modrm >> 6) & 3;
4265             rm = modrm & 7;
4266             op = ((b & 7) << 3) | ((modrm >> 3) & 7);
4267             if (mod != 3) {
4268                 /* memory op */
4269                 AddressParts a = gen_lea_modrm_0(env, s, modrm);
4270                 TCGv ea = gen_lea_modrm_1(s, a, false);
4271                 TCGv last_addr = tcg_temp_new();
4272                 bool update_fdp = true;
4273 
4274                 tcg_gen_mov_tl(last_addr, ea);
4275                 gen_lea_v_seg(s, s->aflag, ea, a.def_seg, s->override);
4276 
4277                 switch (op) {
4278                 case 0x00 ... 0x07: /* fxxxs */
4279                 case 0x10 ... 0x17: /* fixxxl */
4280                 case 0x20 ... 0x27: /* fxxxl */
4281                 case 0x30 ... 0x37: /* fixxx */
4282                     {
4283                         int op1;
4284                         op1 = op & 7;
4285 
4286                         switch (op >> 4) {
4287                         case 0:
4288                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4289                                                 s->mem_index, MO_LEUL);
4290                             gen_helper_flds_FT0(cpu_env, s->tmp2_i32);
4291                             break;
4292                         case 1:
4293                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4294                                                 s->mem_index, MO_LEUL);
4295                             gen_helper_fildl_FT0(cpu_env, s->tmp2_i32);
4296                             break;
4297                         case 2:
4298                             tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0,
4299                                                 s->mem_index, MO_LEUQ);
4300                             gen_helper_fldl_FT0(cpu_env, s->tmp1_i64);
4301                             break;
4302                         case 3:
4303                         default:
4304                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4305                                                 s->mem_index, MO_LESW);
4306                             gen_helper_fildl_FT0(cpu_env, s->tmp2_i32);
4307                             break;
4308                         }
4309 
4310                         gen_helper_fp_arith_ST0_FT0(op1);
4311                         if (op1 == 3) {
4312                             /* fcomp needs pop */
4313                             gen_helper_fpop(cpu_env);
4314                         }
4315                     }
4316                     break;
4317                 case 0x08: /* flds */
4318                 case 0x0a: /* fsts */
4319                 case 0x0b: /* fstps */
4320                 case 0x18 ... 0x1b: /* fildl, fisttpl, fistl, fistpl */
4321                 case 0x28 ... 0x2b: /* fldl, fisttpll, fstl, fstpl */
4322                 case 0x38 ... 0x3b: /* filds, fisttps, fists, fistps */
4323                     switch (op & 7) {
4324                     case 0:
4325                         switch (op >> 4) {
4326                         case 0:
4327                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4328                                                 s->mem_index, MO_LEUL);
4329                             gen_helper_flds_ST0(cpu_env, s->tmp2_i32);
4330                             break;
4331                         case 1:
4332                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4333                                                 s->mem_index, MO_LEUL);
4334                             gen_helper_fildl_ST0(cpu_env, s->tmp2_i32);
4335                             break;
4336                         case 2:
4337                             tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0,
4338                                                 s->mem_index, MO_LEUQ);
4339                             gen_helper_fldl_ST0(cpu_env, s->tmp1_i64);
4340                             break;
4341                         case 3:
4342                         default:
4343                             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4344                                                 s->mem_index, MO_LESW);
4345                             gen_helper_fildl_ST0(cpu_env, s->tmp2_i32);
4346                             break;
4347                         }
4348                         break;
4349                     case 1:
4350                         /* XXX: the corresponding CPUID bit must be tested ! */
4351                         switch (op >> 4) {
4352                         case 1:
4353                             gen_helper_fisttl_ST0(s->tmp2_i32, cpu_env);
4354                             tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4355                                                 s->mem_index, MO_LEUL);
4356                             break;
4357                         case 2:
4358                             gen_helper_fisttll_ST0(s->tmp1_i64, cpu_env);
4359                             tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0,
4360                                                 s->mem_index, MO_LEUQ);
4361                             break;
4362                         case 3:
4363                         default:
4364                             gen_helper_fistt_ST0(s->tmp2_i32, cpu_env);
4365                             tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4366                                                 s->mem_index, MO_LEUW);
4367                             break;
4368                         }
4369                         gen_helper_fpop(cpu_env);
4370                         break;
4371                     default:
4372                         switch (op >> 4) {
4373                         case 0:
4374                             gen_helper_fsts_ST0(s->tmp2_i32, cpu_env);
4375                             tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4376                                                 s->mem_index, MO_LEUL);
4377                             break;
4378                         case 1:
4379                             gen_helper_fistl_ST0(s->tmp2_i32, cpu_env);
4380                             tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4381                                                 s->mem_index, MO_LEUL);
4382                             break;
4383                         case 2:
4384                             gen_helper_fstl_ST0(s->tmp1_i64, cpu_env);
4385                             tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0,
4386                                                 s->mem_index, MO_LEUQ);
4387                             break;
4388                         case 3:
4389                         default:
4390                             gen_helper_fist_ST0(s->tmp2_i32, cpu_env);
4391                             tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4392                                                 s->mem_index, MO_LEUW);
4393                             break;
4394                         }
4395                         if ((op & 7) == 3) {
4396                             gen_helper_fpop(cpu_env);
4397                         }
4398                         break;
4399                     }
4400                     break;
4401                 case 0x0c: /* fldenv mem */
4402                     gen_helper_fldenv(cpu_env, s->A0,
4403                                       tcg_const_i32(dflag - 1));
4404                     update_fip = update_fdp = false;
4405                     break;
4406                 case 0x0d: /* fldcw mem */
4407                     tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0,
4408                                         s->mem_index, MO_LEUW);
4409                     gen_helper_fldcw(cpu_env, s->tmp2_i32);
4410                     update_fip = update_fdp = false;
4411                     break;
4412                 case 0x0e: /* fnstenv mem */
4413                     gen_helper_fstenv(cpu_env, s->A0,
4414                                       tcg_const_i32(dflag - 1));
4415                     update_fip = update_fdp = false;
4416                     break;
4417                 case 0x0f: /* fnstcw mem */
4418                     gen_helper_fnstcw(s->tmp2_i32, cpu_env);
4419                     tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4420                                         s->mem_index, MO_LEUW);
4421                     update_fip = update_fdp = false;
4422                     break;
4423                 case 0x1d: /* fldt mem */
4424                     gen_helper_fldt_ST0(cpu_env, s->A0);
4425                     break;
4426                 case 0x1f: /* fstpt mem */
4427                     gen_helper_fstt_ST0(cpu_env, s->A0);
4428                     gen_helper_fpop(cpu_env);
4429                     break;
4430                 case 0x2c: /* frstor mem */
4431                     gen_helper_frstor(cpu_env, s->A0,
4432                                       tcg_const_i32(dflag - 1));
4433                     update_fip = update_fdp = false;
4434                     break;
4435                 case 0x2e: /* fnsave mem */
4436                     gen_helper_fsave(cpu_env, s->A0,
4437                                      tcg_const_i32(dflag - 1));
4438                     update_fip = update_fdp = false;
4439                     break;
4440                 case 0x2f: /* fnstsw mem */
4441                     gen_helper_fnstsw(s->tmp2_i32, cpu_env);
4442                     tcg_gen_qemu_st_i32(s->tmp2_i32, s->A0,
4443                                         s->mem_index, MO_LEUW);
4444                     update_fip = update_fdp = false;
4445                     break;
4446                 case 0x3c: /* fbld */
4447                     gen_helper_fbld_ST0(cpu_env, s->A0);
4448                     break;
4449                 case 0x3e: /* fbstp */
4450                     gen_helper_fbst_ST0(cpu_env, s->A0);
4451                     gen_helper_fpop(cpu_env);
4452                     break;
4453                 case 0x3d: /* fildll */
4454                     tcg_gen_qemu_ld_i64(s->tmp1_i64, s->A0,
4455                                         s->mem_index, MO_LEUQ);
4456                     gen_helper_fildll_ST0(cpu_env, s->tmp1_i64);
4457                     break;
4458                 case 0x3f: /* fistpll */
4459                     gen_helper_fistll_ST0(s->tmp1_i64, cpu_env);
4460                     tcg_gen_qemu_st_i64(s->tmp1_i64, s->A0,
4461                                         s->mem_index, MO_LEUQ);
4462                     gen_helper_fpop(cpu_env);
4463                     break;
4464                 default:
4465                     goto unknown_op;
4466                 }
4467 
4468                 if (update_fdp) {
4469                     int last_seg = s->override >= 0 ? s->override : a.def_seg;
4470 
4471                     tcg_gen_ld_i32(s->tmp2_i32, cpu_env,
4472                                    offsetof(CPUX86State,
4473                                             segs[last_seg].selector));
4474                     tcg_gen_st16_i32(s->tmp2_i32, cpu_env,
4475                                      offsetof(CPUX86State, fpds));
4476                     tcg_gen_st_tl(last_addr, cpu_env,
4477                                   offsetof(CPUX86State, fpdp));
4478                 }
4479                 tcg_temp_free(last_addr);
4480             } else {
4481                 /* register float ops */
4482                 opreg = rm;
4483 
4484                 switch (op) {
4485                 case 0x08: /* fld sti */
4486                     gen_helper_fpush(cpu_env);
4487                     gen_helper_fmov_ST0_STN(cpu_env,
4488                                             tcg_const_i32((opreg + 1) & 7));
4489                     break;
4490                 case 0x09: /* fxchg sti */
4491                 case 0x29: /* fxchg4 sti, undocumented op */
4492                 case 0x39: /* fxchg7 sti, undocumented op */
4493                     gen_helper_fxchg_ST0_STN(cpu_env, tcg_const_i32(opreg));
4494                     break;
4495                 case 0x0a: /* grp d9/2 */
4496                     switch (rm) {
4497                     case 0: /* fnop */
4498                         /* check exceptions (FreeBSD FPU probe) */
4499                         gen_helper_fwait(cpu_env);
4500                         update_fip = false;
4501                         break;
4502                     default:
4503                         goto unknown_op;
4504                     }
4505                     break;
4506                 case 0x0c: /* grp d9/4 */
4507                     switch (rm) {
4508                     case 0: /* fchs */
4509                         gen_helper_fchs_ST0(cpu_env);
4510                         break;
4511                     case 1: /* fabs */
4512                         gen_helper_fabs_ST0(cpu_env);
4513                         break;
4514                     case 4: /* ftst */
4515                         gen_helper_fldz_FT0(cpu_env);
4516                         gen_helper_fcom_ST0_FT0(cpu_env);
4517                         break;
4518                     case 5: /* fxam */
4519                         gen_helper_fxam_ST0(cpu_env);
4520                         break;
4521                     default:
4522                         goto unknown_op;
4523                     }
4524                     break;
4525                 case 0x0d: /* grp d9/5 */
4526                     {
4527                         switch (rm) {
4528                         case 0:
4529                             gen_helper_fpush(cpu_env);
4530                             gen_helper_fld1_ST0(cpu_env);
4531                             break;
4532                         case 1:
4533                             gen_helper_fpush(cpu_env);
4534                             gen_helper_fldl2t_ST0(cpu_env);
4535                             break;
4536                         case 2:
4537                             gen_helper_fpush(cpu_env);
4538                             gen_helper_fldl2e_ST0(cpu_env);
4539                             break;
4540                         case 3:
4541                             gen_helper_fpush(cpu_env);
4542                             gen_helper_fldpi_ST0(cpu_env);
4543                             break;
4544                         case 4:
4545                             gen_helper_fpush(cpu_env);
4546                             gen_helper_fldlg2_ST0(cpu_env);
4547                             break;
4548                         case 5:
4549                             gen_helper_fpush(cpu_env);
4550                             gen_helper_fldln2_ST0(cpu_env);
4551                             break;
4552                         case 6:
4553                             gen_helper_fpush(cpu_env);
4554                             gen_helper_fldz_ST0(cpu_env);
4555                             break;
4556                         default:
4557                             goto unknown_op;
4558                         }
4559                     }
4560                     break;
4561                 case 0x0e: /* grp d9/6 */
4562                     switch (rm) {
4563                     case 0: /* f2xm1 */
4564                         gen_helper_f2xm1(cpu_env);
4565                         break;
4566                     case 1: /* fyl2x */
4567                         gen_helper_fyl2x(cpu_env);
4568                         break;
4569                     case 2: /* fptan */
4570                         gen_helper_fptan(cpu_env);
4571                         break;
4572                     case 3: /* fpatan */
4573                         gen_helper_fpatan(cpu_env);
4574                         break;
4575                     case 4: /* fxtract */
4576                         gen_helper_fxtract(cpu_env);
4577                         break;
4578                     case 5: /* fprem1 */
4579                         gen_helper_fprem1(cpu_env);
4580                         break;
4581                     case 6: /* fdecstp */
4582                         gen_helper_fdecstp(cpu_env);
4583                         break;
4584                     default:
4585                     case 7: /* fincstp */
4586                         gen_helper_fincstp(cpu_env);
4587                         break;
4588                     }
4589                     break;
4590                 case 0x0f: /* grp d9/7 */
4591                     switch (rm) {
4592                     case 0: /* fprem */
4593                         gen_helper_fprem(cpu_env);
4594                         break;
4595                     case 1: /* fyl2xp1 */
4596                         gen_helper_fyl2xp1(cpu_env);
4597                         break;
4598                     case 2: /* fsqrt */
4599                         gen_helper_fsqrt(cpu_env);
4600                         break;
4601                     case 3: /* fsincos */
4602                         gen_helper_fsincos(cpu_env);
4603                         break;
4604                     case 5: /* fscale */
4605                         gen_helper_fscale(cpu_env);
4606                         break;
4607                     case 4: /* frndint */
4608                         gen_helper_frndint(cpu_env);
4609                         break;
4610                     case 6: /* fsin */
4611                         gen_helper_fsin(cpu_env);
4612                         break;
4613                     default:
4614                     case 7: /* fcos */
4615                         gen_helper_fcos(cpu_env);
4616                         break;
4617                     }
4618                     break;
4619                 case 0x00: case 0x01: case 0x04 ... 0x07: /* fxxx st, sti */
4620                 case 0x20: case 0x21: case 0x24 ... 0x27: /* fxxx sti, st */
4621                 case 0x30: case 0x31: case 0x34 ... 0x37: /* fxxxp sti, st */
4622                     {
4623                         int op1;
4624 
4625                         op1 = op & 7;
4626                         if (op >= 0x20) {
4627                             gen_helper_fp_arith_STN_ST0(op1, opreg);
4628                             if (op >= 0x30) {
4629                                 gen_helper_fpop(cpu_env);
4630                             }
4631                         } else {
4632                             gen_helper_fmov_FT0_STN(cpu_env,
4633                                                     tcg_const_i32(opreg));
4634                             gen_helper_fp_arith_ST0_FT0(op1);
4635                         }
4636                     }
4637                     break;
4638                 case 0x02: /* fcom */
4639                 case 0x22: /* fcom2, undocumented op */
4640                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4641                     gen_helper_fcom_ST0_FT0(cpu_env);
4642                     break;
4643                 case 0x03: /* fcomp */
4644                 case 0x23: /* fcomp3, undocumented op */
4645                 case 0x32: /* fcomp5, undocumented op */
4646                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4647                     gen_helper_fcom_ST0_FT0(cpu_env);
4648                     gen_helper_fpop(cpu_env);
4649                     break;
4650                 case 0x15: /* da/5 */
4651                     switch (rm) {
4652                     case 1: /* fucompp */
4653                         gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(1));
4654                         gen_helper_fucom_ST0_FT0(cpu_env);
4655                         gen_helper_fpop(cpu_env);
4656                         gen_helper_fpop(cpu_env);
4657                         break;
4658                     default:
4659                         goto unknown_op;
4660                     }
4661                     break;
4662                 case 0x1c:
4663                     switch (rm) {
4664                     case 0: /* feni (287 only, just do nop here) */
4665                         break;
4666                     case 1: /* fdisi (287 only, just do nop here) */
4667                         break;
4668                     case 2: /* fclex */
4669                         gen_helper_fclex(cpu_env);
4670                         update_fip = false;
4671                         break;
4672                     case 3: /* fninit */
4673                         gen_helper_fninit(cpu_env);
4674                         update_fip = false;
4675                         break;
4676                     case 4: /* fsetpm (287 only, just do nop here) */
4677                         break;
4678                     default:
4679                         goto unknown_op;
4680                     }
4681                     break;
4682                 case 0x1d: /* fucomi */
4683                     if (!(s->cpuid_features & CPUID_CMOV)) {
4684                         goto illegal_op;
4685                     }
4686                     gen_update_cc_op(s);
4687                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4688                     gen_helper_fucomi_ST0_FT0(cpu_env);
4689                     set_cc_op(s, CC_OP_EFLAGS);
4690                     break;
4691                 case 0x1e: /* fcomi */
4692                     if (!(s->cpuid_features & CPUID_CMOV)) {
4693                         goto illegal_op;
4694                     }
4695                     gen_update_cc_op(s);
4696                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4697                     gen_helper_fcomi_ST0_FT0(cpu_env);
4698                     set_cc_op(s, CC_OP_EFLAGS);
4699                     break;
4700                 case 0x28: /* ffree sti */
4701                     gen_helper_ffree_STN(cpu_env, tcg_const_i32(opreg));
4702                     break;
4703                 case 0x2a: /* fst sti */
4704                     gen_helper_fmov_STN_ST0(cpu_env, tcg_const_i32(opreg));
4705                     break;
4706                 case 0x2b: /* fstp sti */
4707                 case 0x0b: /* fstp1 sti, undocumented op */
4708                 case 0x3a: /* fstp8 sti, undocumented op */
4709                 case 0x3b: /* fstp9 sti, undocumented op */
4710                     gen_helper_fmov_STN_ST0(cpu_env, tcg_const_i32(opreg));
4711                     gen_helper_fpop(cpu_env);
4712                     break;
4713                 case 0x2c: /* fucom st(i) */
4714                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4715                     gen_helper_fucom_ST0_FT0(cpu_env);
4716                     break;
4717                 case 0x2d: /* fucomp st(i) */
4718                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4719                     gen_helper_fucom_ST0_FT0(cpu_env);
4720                     gen_helper_fpop(cpu_env);
4721                     break;
4722                 case 0x33: /* de/3 */
4723                     switch (rm) {
4724                     case 1: /* fcompp */
4725                         gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(1));
4726                         gen_helper_fcom_ST0_FT0(cpu_env);
4727                         gen_helper_fpop(cpu_env);
4728                         gen_helper_fpop(cpu_env);
4729                         break;
4730                     default:
4731                         goto unknown_op;
4732                     }
4733                     break;
4734                 case 0x38: /* ffreep sti, undocumented op */
4735                     gen_helper_ffree_STN(cpu_env, tcg_const_i32(opreg));
4736                     gen_helper_fpop(cpu_env);
4737                     break;
4738                 case 0x3c: /* df/4 */
4739                     switch (rm) {
4740                     case 0:
4741                         gen_helper_fnstsw(s->tmp2_i32, cpu_env);
4742                         tcg_gen_extu_i32_tl(s->T0, s->tmp2_i32);
4743                         gen_op_mov_reg_v(s, MO_16, R_EAX, s->T0);
4744                         break;
4745                     default:
4746                         goto unknown_op;
4747                     }
4748                     break;
4749                 case 0x3d: /* fucomip */
4750                     if (!(s->cpuid_features & CPUID_CMOV)) {
4751                         goto illegal_op;
4752                     }
4753                     gen_update_cc_op(s);
4754                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4755                     gen_helper_fucomi_ST0_FT0(cpu_env);
4756                     gen_helper_fpop(cpu_env);
4757                     set_cc_op(s, CC_OP_EFLAGS);
4758                     break;
4759                 case 0x3e: /* fcomip */
4760                     if (!(s->cpuid_features & CPUID_CMOV)) {
4761                         goto illegal_op;
4762                     }
4763                     gen_update_cc_op(s);
4764                     gen_helper_fmov_FT0_STN(cpu_env, tcg_const_i32(opreg));
4765                     gen_helper_fcomi_ST0_FT0(cpu_env);
4766                     gen_helper_fpop(cpu_env);
4767                     set_cc_op(s, CC_OP_EFLAGS);
4768                     break;
4769                 case 0x10 ... 0x13: /* fcmovxx */
4770                 case 0x18 ... 0x1b:
4771                     {
4772                         int op1;
4773                         TCGLabel *l1;
4774                         static const uint8_t fcmov_cc[8] = {
4775                             (JCC_B << 1),
4776                             (JCC_Z << 1),
4777                             (JCC_BE << 1),
4778                             (JCC_P << 1),
4779                         };
4780 
4781                         if (!(s->cpuid_features & CPUID_CMOV)) {
4782                             goto illegal_op;
4783                         }
4784                         op1 = fcmov_cc[op & 3] | (((op >> 3) & 1) ^ 1);
4785                         l1 = gen_new_label();
4786                         gen_jcc1_noeob(s, op1, l1);
4787                         gen_helper_fmov_ST0_STN(cpu_env, tcg_const_i32(opreg));
4788                         gen_set_label(l1);
4789                     }
4790                     break;
4791                 default:
4792                     goto unknown_op;
4793                 }
4794             }
4795 
4796             if (update_fip) {
4797                 tcg_gen_ld_i32(s->tmp2_i32, cpu_env,
4798                                offsetof(CPUX86State, segs[R_CS].selector));
4799                 tcg_gen_st16_i32(s->tmp2_i32, cpu_env,
4800                                  offsetof(CPUX86State, fpcs));
4801                 tcg_gen_st_tl(eip_cur_tl(s),
4802                               cpu_env, offsetof(CPUX86State, fpip));
4803             }
4804         }
4805         break;
4806         /************************/
4807         /* string ops */
4808 
4809     case 0xa4: /* movsS */
4810     case 0xa5:
4811         ot = mo_b_d(b, dflag);
4812         if (prefixes & (PREFIX_REPZ | PREFIX_REPNZ)) {
4813             gen_repz_movs(s, ot);
4814         } else {
4815             gen_movs(s, ot);
4816         }
4817         break;
4818 
4819     case 0xaa: /* stosS */
4820     case 0xab:
4821         ot = mo_b_d(b, dflag);
4822         if (prefixes & (PREFIX_REPZ | PREFIX_REPNZ)) {
4823             gen_repz_stos(s, ot);
4824         } else {
4825             gen_stos(s, ot);
4826         }
4827         break;
4828     case 0xac: /* lodsS */
4829     case 0xad:
4830         ot = mo_b_d(b, dflag);
4831         if (prefixes & (PREFIX_REPZ | PREFIX_REPNZ)) {
4832             gen_repz_lods(s, ot);
4833         } else {
4834             gen_lods(s, ot);
4835         }
4836         break;
4837     case 0xae: /* scasS */
4838     case 0xaf:
4839         ot = mo_b_d(b, dflag);
4840         if (prefixes & PREFIX_REPNZ) {
4841             gen_repz_scas(s, ot, 1);
4842         } else if (prefixes & PREFIX_REPZ) {
4843             gen_repz_scas(s, ot, 0);
4844         } else {
4845             gen_scas(s, ot);
4846         }
4847         break;
4848 
4849     case 0xa6: /* cmpsS */
4850     case 0xa7:
4851         ot = mo_b_d(b, dflag);
4852         if (prefixes & PREFIX_REPNZ) {
4853             gen_repz_cmps(s, ot, 1);
4854         } else if (prefixes & PREFIX_REPZ) {
4855             gen_repz_cmps(s, ot, 0);
4856         } else {
4857             gen_cmps(s, ot);
4858         }
4859         break;
4860     case 0x6c: /* insS */
4861     case 0x6d:
4862         ot = mo_b_d32(b, dflag);
4863         tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
4864         tcg_gen_ext16u_i32(s->tmp2_i32, s->tmp2_i32);
4865         if (!gen_check_io(s, ot, s->tmp2_i32,
4866                           SVM_IOIO_TYPE_MASK | SVM_IOIO_STR_MASK)) {
4867             break;
4868         }
4869         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4870             gen_io_start();
4871             s->base.is_jmp = DISAS_TOO_MANY;
4872         }
4873         if (prefixes & (PREFIX_REPZ | PREFIX_REPNZ)) {
4874             gen_repz_ins(s, ot);
4875         } else {
4876             gen_ins(s, ot);
4877         }
4878         break;
4879     case 0x6e: /* outsS */
4880     case 0x6f:
4881         ot = mo_b_d32(b, dflag);
4882         tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
4883         tcg_gen_ext16u_i32(s->tmp2_i32, s->tmp2_i32);
4884         if (!gen_check_io(s, ot, s->tmp2_i32, SVM_IOIO_STR_MASK)) {
4885             break;
4886         }
4887         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4888             gen_io_start();
4889             s->base.is_jmp = DISAS_TOO_MANY;
4890         }
4891         if (prefixes & (PREFIX_REPZ | PREFIX_REPNZ)) {
4892             gen_repz_outs(s, ot);
4893         } else {
4894             gen_outs(s, ot);
4895         }
4896         break;
4897 
4898         /************************/
4899         /* port I/O */
4900 
4901     case 0xe4:
4902     case 0xe5:
4903         ot = mo_b_d32(b, dflag);
4904         val = x86_ldub_code(env, s);
4905         tcg_gen_movi_i32(s->tmp2_i32, val);
4906         if (!gen_check_io(s, ot, s->tmp2_i32, SVM_IOIO_TYPE_MASK)) {
4907             break;
4908         }
4909         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4910             gen_io_start();
4911             s->base.is_jmp = DISAS_TOO_MANY;
4912         }
4913         gen_helper_in_func(ot, s->T1, s->tmp2_i32);
4914         gen_op_mov_reg_v(s, ot, R_EAX, s->T1);
4915         gen_bpt_io(s, s->tmp2_i32, ot);
4916         break;
4917     case 0xe6:
4918     case 0xe7:
4919         ot = mo_b_d32(b, dflag);
4920         val = x86_ldub_code(env, s);
4921         tcg_gen_movi_i32(s->tmp2_i32, val);
4922         if (!gen_check_io(s, ot, s->tmp2_i32, 0)) {
4923             break;
4924         }
4925         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4926             gen_io_start();
4927             s->base.is_jmp = DISAS_TOO_MANY;
4928         }
4929         gen_op_mov_v_reg(s, ot, s->T1, R_EAX);
4930         tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T1);
4931         gen_helper_out_func(ot, s->tmp2_i32, s->tmp3_i32);
4932         gen_bpt_io(s, s->tmp2_i32, ot);
4933         break;
4934     case 0xec:
4935     case 0xed:
4936         ot = mo_b_d32(b, dflag);
4937         tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
4938         tcg_gen_ext16u_i32(s->tmp2_i32, s->tmp2_i32);
4939         if (!gen_check_io(s, ot, s->tmp2_i32, SVM_IOIO_TYPE_MASK)) {
4940             break;
4941         }
4942         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4943             gen_io_start();
4944             s->base.is_jmp = DISAS_TOO_MANY;
4945         }
4946         gen_helper_in_func(ot, s->T1, s->tmp2_i32);
4947         gen_op_mov_reg_v(s, ot, R_EAX, s->T1);
4948         gen_bpt_io(s, s->tmp2_i32, ot);
4949         break;
4950     case 0xee:
4951     case 0xef:
4952         ot = mo_b_d32(b, dflag);
4953         tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_EDX]);
4954         tcg_gen_ext16u_i32(s->tmp2_i32, s->tmp2_i32);
4955         if (!gen_check_io(s, ot, s->tmp2_i32, 0)) {
4956             break;
4957         }
4958         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
4959             gen_io_start();
4960             s->base.is_jmp = DISAS_TOO_MANY;
4961         }
4962         gen_op_mov_v_reg(s, ot, s->T1, R_EAX);
4963         tcg_gen_trunc_tl_i32(s->tmp3_i32, s->T1);
4964         gen_helper_out_func(ot, s->tmp2_i32, s->tmp3_i32);
4965         gen_bpt_io(s, s->tmp2_i32, ot);
4966         break;
4967 
4968         /************************/
4969         /* control */
4970     case 0xc2: /* ret im */
4971         val = x86_ldsw_code(env, s);
4972         ot = gen_pop_T0(s);
4973         gen_stack_update(s, val + (1 << ot));
4974         /* Note that gen_pop_T0 uses a zero-extending load.  */
4975         gen_op_jmp_v(s, s->T0);
4976         gen_bnd_jmp(s);
4977         s->base.is_jmp = DISAS_JUMP;
4978         break;
4979     case 0xc3: /* ret */
4980         ot = gen_pop_T0(s);
4981         gen_pop_update(s, ot);
4982         /* Note that gen_pop_T0 uses a zero-extending load.  */
4983         gen_op_jmp_v(s, s->T0);
4984         gen_bnd_jmp(s);
4985         s->base.is_jmp = DISAS_JUMP;
4986         break;
4987     case 0xca: /* lret im */
4988         val = x86_ldsw_code(env, s);
4989     do_lret:
4990         if (PE(s) && !VM86(s)) {
4991             gen_update_cc_op(s);
4992             gen_update_eip_cur(s);
4993             gen_helper_lret_protected(cpu_env, tcg_const_i32(dflag - 1),
4994                                       tcg_const_i32(val));
4995         } else {
4996             gen_stack_A0(s);
4997             /* pop offset */
4998             gen_op_ld_v(s, dflag, s->T0, s->A0);
4999             /* NOTE: keeping EIP updated is not a problem in case of
5000                exception */
5001             gen_op_jmp_v(s, s->T0);
5002             /* pop selector */
5003             gen_add_A0_im(s, 1 << dflag);
5004             gen_op_ld_v(s, dflag, s->T0, s->A0);
5005             gen_op_movl_seg_T0_vm(s, R_CS);
5006             /* add stack offset */
5007             gen_stack_update(s, val + (2 << dflag));
5008         }
5009         s->base.is_jmp = DISAS_EOB_ONLY;
5010         break;
5011     case 0xcb: /* lret */
5012         val = 0;
5013         goto do_lret;
5014     case 0xcf: /* iret */
5015         gen_svm_check_intercept(s, SVM_EXIT_IRET);
5016         if (!PE(s) || VM86(s)) {
5017             /* real mode or vm86 mode */
5018             if (!check_vm86_iopl(s)) {
5019                 break;
5020             }
5021             gen_helper_iret_real(cpu_env, tcg_const_i32(dflag - 1));
5022         } else {
5023             gen_helper_iret_protected(cpu_env, tcg_constant_i32(dflag - 1),
5024                                       eip_next_i32(s));
5025         }
5026         set_cc_op(s, CC_OP_EFLAGS);
5027         s->base.is_jmp = DISAS_EOB_ONLY;
5028         break;
5029     case 0xe8: /* call im */
5030         {
5031             int diff = (dflag != MO_16
5032                         ? (int32_t)insn_get(env, s, MO_32)
5033                         : (int16_t)insn_get(env, s, MO_16));
5034             gen_push_v(s, eip_next_tl(s));
5035             gen_bnd_jmp(s);
5036             gen_jmp_rel(s, dflag, diff, 0);
5037         }
5038         break;
5039     case 0x9a: /* lcall im */
5040         {
5041             unsigned int selector, offset;
5042 
5043             if (CODE64(s))
5044                 goto illegal_op;
5045             ot = dflag;
5046             offset = insn_get(env, s, ot);
5047             selector = insn_get(env, s, MO_16);
5048 
5049             tcg_gen_movi_tl(s->T0, selector);
5050             tcg_gen_movi_tl(s->T1, offset);
5051         }
5052         goto do_lcall;
5053     case 0xe9: /* jmp im */
5054         {
5055             int diff = (dflag != MO_16
5056                         ? (int32_t)insn_get(env, s, MO_32)
5057                         : (int16_t)insn_get(env, s, MO_16));
5058             gen_bnd_jmp(s);
5059             gen_jmp_rel(s, dflag, diff, 0);
5060         }
5061         break;
5062     case 0xea: /* ljmp im */
5063         {
5064             unsigned int selector, offset;
5065 
5066             if (CODE64(s))
5067                 goto illegal_op;
5068             ot = dflag;
5069             offset = insn_get(env, s, ot);
5070             selector = insn_get(env, s, MO_16);
5071 
5072             tcg_gen_movi_tl(s->T0, selector);
5073             tcg_gen_movi_tl(s->T1, offset);
5074         }
5075         goto do_ljmp;
5076     case 0xeb: /* jmp Jb */
5077         {
5078             int diff = (int8_t)insn_get(env, s, MO_8);
5079             gen_jmp_rel(s, dflag, diff, 0);
5080         }
5081         break;
5082     case 0x70 ... 0x7f: /* jcc Jb */
5083         {
5084             int diff = (int8_t)insn_get(env, s, MO_8);
5085             gen_bnd_jmp(s);
5086             gen_jcc(s, b, diff);
5087         }
5088         break;
5089     case 0x180 ... 0x18f: /* jcc Jv */
5090         {
5091             int diff = (dflag != MO_16
5092                         ? (int32_t)insn_get(env, s, MO_32)
5093                         : (int16_t)insn_get(env, s, MO_16));
5094             gen_bnd_jmp(s);
5095             gen_jcc(s, b, diff);
5096         }
5097         break;
5098 
5099     case 0x190 ... 0x19f: /* setcc Gv */
5100         modrm = x86_ldub_code(env, s);
5101         gen_setcc1(s, b, s->T0);
5102         gen_ldst_modrm(env, s, modrm, MO_8, OR_TMP0, 1);
5103         break;
5104     case 0x140 ... 0x14f: /* cmov Gv, Ev */
5105         if (!(s->cpuid_features & CPUID_CMOV)) {
5106             goto illegal_op;
5107         }
5108         ot = dflag;
5109         modrm = x86_ldub_code(env, s);
5110         reg = ((modrm >> 3) & 7) | REX_R(s);
5111         gen_cmovcc1(env, s, ot, b, modrm, reg);
5112         break;
5113 
5114         /************************/
5115         /* flags */
5116     case 0x9c: /* pushf */
5117         gen_svm_check_intercept(s, SVM_EXIT_PUSHF);
5118         if (check_vm86_iopl(s)) {
5119             gen_update_cc_op(s);
5120             gen_helper_read_eflags(s->T0, cpu_env);
5121             gen_push_v(s, s->T0);
5122         }
5123         break;
5124     case 0x9d: /* popf */
5125         gen_svm_check_intercept(s, SVM_EXIT_POPF);
5126         if (check_vm86_iopl(s)) {
5127             ot = gen_pop_T0(s);
5128             if (CPL(s) == 0) {
5129                 if (dflag != MO_16) {
5130                     gen_helper_write_eflags(cpu_env, s->T0,
5131                                             tcg_const_i32((TF_MASK | AC_MASK |
5132                                                            ID_MASK | NT_MASK |
5133                                                            IF_MASK |
5134                                                            IOPL_MASK)));
5135                 } else {
5136                     gen_helper_write_eflags(cpu_env, s->T0,
5137                                             tcg_const_i32((TF_MASK | AC_MASK |
5138                                                            ID_MASK | NT_MASK |
5139                                                            IF_MASK | IOPL_MASK)
5140                                                           & 0xffff));
5141                 }
5142             } else {
5143                 if (CPL(s) <= IOPL(s)) {
5144                     if (dflag != MO_16) {
5145                         gen_helper_write_eflags(cpu_env, s->T0,
5146                                                 tcg_const_i32((TF_MASK |
5147                                                                AC_MASK |
5148                                                                ID_MASK |
5149                                                                NT_MASK |
5150                                                                IF_MASK)));
5151                     } else {
5152                         gen_helper_write_eflags(cpu_env, s->T0,
5153                                                 tcg_const_i32((TF_MASK |
5154                                                                AC_MASK |
5155                                                                ID_MASK |
5156                                                                NT_MASK |
5157                                                                IF_MASK)
5158                                                               & 0xffff));
5159                     }
5160                 } else {
5161                     if (dflag != MO_16) {
5162                         gen_helper_write_eflags(cpu_env, s->T0,
5163                                            tcg_const_i32((TF_MASK | AC_MASK |
5164                                                           ID_MASK | NT_MASK)));
5165                     } else {
5166                         gen_helper_write_eflags(cpu_env, s->T0,
5167                                            tcg_const_i32((TF_MASK | AC_MASK |
5168                                                           ID_MASK | NT_MASK)
5169                                                          & 0xffff));
5170                     }
5171                 }
5172             }
5173             gen_pop_update(s, ot);
5174             set_cc_op(s, CC_OP_EFLAGS);
5175             /* abort translation because TF/AC flag may change */
5176             s->base.is_jmp = DISAS_EOB_NEXT;
5177         }
5178         break;
5179     case 0x9e: /* sahf */
5180         if (CODE64(s) && !(s->cpuid_ext3_features & CPUID_EXT3_LAHF_LM))
5181             goto illegal_op;
5182         gen_op_mov_v_reg(s, MO_8, s->T0, R_AH);
5183         gen_compute_eflags(s);
5184         tcg_gen_andi_tl(cpu_cc_src, cpu_cc_src, CC_O);
5185         tcg_gen_andi_tl(s->T0, s->T0, CC_S | CC_Z | CC_A | CC_P | CC_C);
5186         tcg_gen_or_tl(cpu_cc_src, cpu_cc_src, s->T0);
5187         break;
5188     case 0x9f: /* lahf */
5189         if (CODE64(s) && !(s->cpuid_ext3_features & CPUID_EXT3_LAHF_LM))
5190             goto illegal_op;
5191         gen_compute_eflags(s);
5192         /* Note: gen_compute_eflags() only gives the condition codes */
5193         tcg_gen_ori_tl(s->T0, cpu_cc_src, 0x02);
5194         gen_op_mov_reg_v(s, MO_8, R_AH, s->T0);
5195         break;
5196     case 0xf5: /* cmc */
5197         gen_compute_eflags(s);
5198         tcg_gen_xori_tl(cpu_cc_src, cpu_cc_src, CC_C);
5199         break;
5200     case 0xf8: /* clc */
5201         gen_compute_eflags(s);
5202         tcg_gen_andi_tl(cpu_cc_src, cpu_cc_src, ~CC_C);
5203         break;
5204     case 0xf9: /* stc */
5205         gen_compute_eflags(s);
5206         tcg_gen_ori_tl(cpu_cc_src, cpu_cc_src, CC_C);
5207         break;
5208     case 0xfc: /* cld */
5209         tcg_gen_movi_i32(s->tmp2_i32, 1);
5210         tcg_gen_st_i32(s->tmp2_i32, cpu_env, offsetof(CPUX86State, df));
5211         break;
5212     case 0xfd: /* std */
5213         tcg_gen_movi_i32(s->tmp2_i32, -1);
5214         tcg_gen_st_i32(s->tmp2_i32, cpu_env, offsetof(CPUX86State, df));
5215         break;
5216 
5217         /************************/
5218         /* bit operations */
5219     case 0x1ba: /* bt/bts/btr/btc Gv, im */
5220         ot = dflag;
5221         modrm = x86_ldub_code(env, s);
5222         op = (modrm >> 3) & 7;
5223         mod = (modrm >> 6) & 3;
5224         rm = (modrm & 7) | REX_B(s);
5225         if (mod != 3) {
5226             s->rip_offset = 1;
5227             gen_lea_modrm(env, s, modrm);
5228             if (!(s->prefix & PREFIX_LOCK)) {
5229                 gen_op_ld_v(s, ot, s->T0, s->A0);
5230             }
5231         } else {
5232             gen_op_mov_v_reg(s, ot, s->T0, rm);
5233         }
5234         /* load shift */
5235         val = x86_ldub_code(env, s);
5236         tcg_gen_movi_tl(s->T1, val);
5237         if (op < 4)
5238             goto unknown_op;
5239         op -= 4;
5240         goto bt_op;
5241     case 0x1a3: /* bt Gv, Ev */
5242         op = 0;
5243         goto do_btx;
5244     case 0x1ab: /* bts */
5245         op = 1;
5246         goto do_btx;
5247     case 0x1b3: /* btr */
5248         op = 2;
5249         goto do_btx;
5250     case 0x1bb: /* btc */
5251         op = 3;
5252     do_btx:
5253         ot = dflag;
5254         modrm = x86_ldub_code(env, s);
5255         reg = ((modrm >> 3) & 7) | REX_R(s);
5256         mod = (modrm >> 6) & 3;
5257         rm = (modrm & 7) | REX_B(s);
5258         gen_op_mov_v_reg(s, MO_32, s->T1, reg);
5259         if (mod != 3) {
5260             AddressParts a = gen_lea_modrm_0(env, s, modrm);
5261             /* specific case: we need to add a displacement */
5262             gen_exts(ot, s->T1);
5263             tcg_gen_sari_tl(s->tmp0, s->T1, 3 + ot);
5264             tcg_gen_shli_tl(s->tmp0, s->tmp0, ot);
5265             tcg_gen_add_tl(s->A0, gen_lea_modrm_1(s, a, false), s->tmp0);
5266             gen_lea_v_seg(s, s->aflag, s->A0, a.def_seg, s->override);
5267             if (!(s->prefix & PREFIX_LOCK)) {
5268                 gen_op_ld_v(s, ot, s->T0, s->A0);
5269             }
5270         } else {
5271             gen_op_mov_v_reg(s, ot, s->T0, rm);
5272         }
5273     bt_op:
5274         tcg_gen_andi_tl(s->T1, s->T1, (1 << (3 + ot)) - 1);
5275         tcg_gen_movi_tl(s->tmp0, 1);
5276         tcg_gen_shl_tl(s->tmp0, s->tmp0, s->T1);
5277         if (s->prefix & PREFIX_LOCK) {
5278             switch (op) {
5279             case 0: /* bt */
5280                 /* Needs no atomic ops; we surpressed the normal
5281                    memory load for LOCK above so do it now.  */
5282                 gen_op_ld_v(s, ot, s->T0, s->A0);
5283                 break;
5284             case 1: /* bts */
5285                 tcg_gen_atomic_fetch_or_tl(s->T0, s->A0, s->tmp0,
5286                                            s->mem_index, ot | MO_LE);
5287                 break;
5288             case 2: /* btr */
5289                 tcg_gen_not_tl(s->tmp0, s->tmp0);
5290                 tcg_gen_atomic_fetch_and_tl(s->T0, s->A0, s->tmp0,
5291                                             s->mem_index, ot | MO_LE);
5292                 break;
5293             default:
5294             case 3: /* btc */
5295                 tcg_gen_atomic_fetch_xor_tl(s->T0, s->A0, s->tmp0,
5296                                             s->mem_index, ot | MO_LE);
5297                 break;
5298             }
5299             tcg_gen_shr_tl(s->tmp4, s->T0, s->T1);
5300         } else {
5301             tcg_gen_shr_tl(s->tmp4, s->T0, s->T1);
5302             switch (op) {
5303             case 0: /* bt */
5304                 /* Data already loaded; nothing to do.  */
5305                 break;
5306             case 1: /* bts */
5307                 tcg_gen_or_tl(s->T0, s->T0, s->tmp0);
5308                 break;
5309             case 2: /* btr */
5310                 tcg_gen_andc_tl(s->T0, s->T0, s->tmp0);
5311                 break;
5312             default:
5313             case 3: /* btc */
5314                 tcg_gen_xor_tl(s->T0, s->T0, s->tmp0);
5315                 break;
5316             }
5317             if (op != 0) {
5318                 if (mod != 3) {
5319                     gen_op_st_v(s, ot, s->T0, s->A0);
5320                 } else {
5321                     gen_op_mov_reg_v(s, ot, rm, s->T0);
5322                 }
5323             }
5324         }
5325 
5326         /* Delay all CC updates until after the store above.  Note that
5327            C is the result of the test, Z is unchanged, and the others
5328            are all undefined.  */
5329         switch (s->cc_op) {
5330         case CC_OP_MULB ... CC_OP_MULQ:
5331         case CC_OP_ADDB ... CC_OP_ADDQ:
5332         case CC_OP_ADCB ... CC_OP_ADCQ:
5333         case CC_OP_SUBB ... CC_OP_SUBQ:
5334         case CC_OP_SBBB ... CC_OP_SBBQ:
5335         case CC_OP_LOGICB ... CC_OP_LOGICQ:
5336         case CC_OP_INCB ... CC_OP_INCQ:
5337         case CC_OP_DECB ... CC_OP_DECQ:
5338         case CC_OP_SHLB ... CC_OP_SHLQ:
5339         case CC_OP_SARB ... CC_OP_SARQ:
5340         case CC_OP_BMILGB ... CC_OP_BMILGQ:
5341             /* Z was going to be computed from the non-zero status of CC_DST.
5342                We can get that same Z value (and the new C value) by leaving
5343                CC_DST alone, setting CC_SRC, and using a CC_OP_SAR of the
5344                same width.  */
5345             tcg_gen_mov_tl(cpu_cc_src, s->tmp4);
5346             set_cc_op(s, ((s->cc_op - CC_OP_MULB) & 3) + CC_OP_SARB);
5347             break;
5348         default:
5349             /* Otherwise, generate EFLAGS and replace the C bit.  */
5350             gen_compute_eflags(s);
5351             tcg_gen_deposit_tl(cpu_cc_src, cpu_cc_src, s->tmp4,
5352                                ctz32(CC_C), 1);
5353             break;
5354         }
5355         break;
5356     case 0x1bc: /* bsf / tzcnt */
5357     case 0x1bd: /* bsr / lzcnt */
5358         ot = dflag;
5359         modrm = x86_ldub_code(env, s);
5360         reg = ((modrm >> 3) & 7) | REX_R(s);
5361         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
5362         gen_extu(ot, s->T0);
5363 
5364         /* Note that lzcnt and tzcnt are in different extensions.  */
5365         if ((prefixes & PREFIX_REPZ)
5366             && (b & 1
5367                 ? s->cpuid_ext3_features & CPUID_EXT3_ABM
5368                 : s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_BMI1)) {
5369             int size = 8 << ot;
5370             /* For lzcnt/tzcnt, C bit is defined related to the input. */
5371             tcg_gen_mov_tl(cpu_cc_src, s->T0);
5372             if (b & 1) {
5373                 /* For lzcnt, reduce the target_ulong result by the
5374                    number of zeros that we expect to find at the top.  */
5375                 tcg_gen_clzi_tl(s->T0, s->T0, TARGET_LONG_BITS);
5376                 tcg_gen_subi_tl(s->T0, s->T0, TARGET_LONG_BITS - size);
5377             } else {
5378                 /* For tzcnt, a zero input must return the operand size.  */
5379                 tcg_gen_ctzi_tl(s->T0, s->T0, size);
5380             }
5381             /* For lzcnt/tzcnt, Z bit is defined related to the result.  */
5382             gen_op_update1_cc(s);
5383             set_cc_op(s, CC_OP_BMILGB + ot);
5384         } else {
5385             /* For bsr/bsf, only the Z bit is defined and it is related
5386                to the input and not the result.  */
5387             tcg_gen_mov_tl(cpu_cc_dst, s->T0);
5388             set_cc_op(s, CC_OP_LOGICB + ot);
5389 
5390             /* ??? The manual says that the output is undefined when the
5391                input is zero, but real hardware leaves it unchanged, and
5392                real programs appear to depend on that.  Accomplish this
5393                by passing the output as the value to return upon zero.  */
5394             if (b & 1) {
5395                 /* For bsr, return the bit index of the first 1 bit,
5396                    not the count of leading zeros.  */
5397                 tcg_gen_xori_tl(s->T1, cpu_regs[reg], TARGET_LONG_BITS - 1);
5398                 tcg_gen_clz_tl(s->T0, s->T0, s->T1);
5399                 tcg_gen_xori_tl(s->T0, s->T0, TARGET_LONG_BITS - 1);
5400             } else {
5401                 tcg_gen_ctz_tl(s->T0, s->T0, cpu_regs[reg]);
5402             }
5403         }
5404         gen_op_mov_reg_v(s, ot, reg, s->T0);
5405         break;
5406         /************************/
5407         /* bcd */
5408     case 0x27: /* daa */
5409         if (CODE64(s))
5410             goto illegal_op;
5411         gen_update_cc_op(s);
5412         gen_helper_daa(cpu_env);
5413         set_cc_op(s, CC_OP_EFLAGS);
5414         break;
5415     case 0x2f: /* das */
5416         if (CODE64(s))
5417             goto illegal_op;
5418         gen_update_cc_op(s);
5419         gen_helper_das(cpu_env);
5420         set_cc_op(s, CC_OP_EFLAGS);
5421         break;
5422     case 0x37: /* aaa */
5423         if (CODE64(s))
5424             goto illegal_op;
5425         gen_update_cc_op(s);
5426         gen_helper_aaa(cpu_env);
5427         set_cc_op(s, CC_OP_EFLAGS);
5428         break;
5429     case 0x3f: /* aas */
5430         if (CODE64(s))
5431             goto illegal_op;
5432         gen_update_cc_op(s);
5433         gen_helper_aas(cpu_env);
5434         set_cc_op(s, CC_OP_EFLAGS);
5435         break;
5436     case 0xd4: /* aam */
5437         if (CODE64(s))
5438             goto illegal_op;
5439         val = x86_ldub_code(env, s);
5440         if (val == 0) {
5441             gen_exception(s, EXCP00_DIVZ);
5442         } else {
5443             gen_helper_aam(cpu_env, tcg_const_i32(val));
5444             set_cc_op(s, CC_OP_LOGICB);
5445         }
5446         break;
5447     case 0xd5: /* aad */
5448         if (CODE64(s))
5449             goto illegal_op;
5450         val = x86_ldub_code(env, s);
5451         gen_helper_aad(cpu_env, tcg_const_i32(val));
5452         set_cc_op(s, CC_OP_LOGICB);
5453         break;
5454         /************************/
5455         /* misc */
5456     case 0x90: /* nop */
5457         /* XXX: correct lock test for all insn */
5458         if (prefixes & PREFIX_LOCK) {
5459             goto illegal_op;
5460         }
5461         /* If REX_B is set, then this is xchg eax, r8d, not a nop.  */
5462         if (REX_B(s)) {
5463             goto do_xchg_reg_eax;
5464         }
5465         if (prefixes & PREFIX_REPZ) {
5466             gen_update_cc_op(s);
5467             gen_update_eip_cur(s);
5468             gen_helper_pause(cpu_env, cur_insn_len_i32(s));
5469             s->base.is_jmp = DISAS_NORETURN;
5470         }
5471         break;
5472     case 0x9b: /* fwait */
5473         if ((s->flags & (HF_MP_MASK | HF_TS_MASK)) ==
5474             (HF_MP_MASK | HF_TS_MASK)) {
5475             gen_exception(s, EXCP07_PREX);
5476         } else {
5477             gen_helper_fwait(cpu_env);
5478         }
5479         break;
5480     case 0xcc: /* int3 */
5481         gen_interrupt(s, EXCP03_INT3);
5482         break;
5483     case 0xcd: /* int N */
5484         val = x86_ldub_code(env, s);
5485         if (check_vm86_iopl(s)) {
5486             gen_interrupt(s, val);
5487         }
5488         break;
5489     case 0xce: /* into */
5490         if (CODE64(s))
5491             goto illegal_op;
5492         gen_update_cc_op(s);
5493         gen_update_eip_cur(s);
5494         gen_helper_into(cpu_env, cur_insn_len_i32(s));
5495         break;
5496 #ifdef WANT_ICEBP
5497     case 0xf1: /* icebp (undocumented, exits to external debugger) */
5498         gen_svm_check_intercept(s, SVM_EXIT_ICEBP);
5499         gen_debug(s);
5500         break;
5501 #endif
5502     case 0xfa: /* cli */
5503         if (check_iopl(s)) {
5504             gen_helper_cli(cpu_env);
5505         }
5506         break;
5507     case 0xfb: /* sti */
5508         if (check_iopl(s)) {
5509             gen_helper_sti(cpu_env);
5510             /* interruptions are enabled only the first insn after sti */
5511             gen_update_eip_next(s);
5512             gen_eob_inhibit_irq(s, true);
5513         }
5514         break;
5515     case 0x62: /* bound */
5516         if (CODE64(s))
5517             goto illegal_op;
5518         ot = dflag;
5519         modrm = x86_ldub_code(env, s);
5520         reg = (modrm >> 3) & 7;
5521         mod = (modrm >> 6) & 3;
5522         if (mod == 3)
5523             goto illegal_op;
5524         gen_op_mov_v_reg(s, ot, s->T0, reg);
5525         gen_lea_modrm(env, s, modrm);
5526         tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
5527         if (ot == MO_16) {
5528             gen_helper_boundw(cpu_env, s->A0, s->tmp2_i32);
5529         } else {
5530             gen_helper_boundl(cpu_env, s->A0, s->tmp2_i32);
5531         }
5532         break;
5533     case 0x1c8 ... 0x1cf: /* bswap reg */
5534         reg = (b & 7) | REX_B(s);
5535 #ifdef TARGET_X86_64
5536         if (dflag == MO_64) {
5537             tcg_gen_bswap64_i64(cpu_regs[reg], cpu_regs[reg]);
5538             break;
5539         }
5540 #endif
5541         tcg_gen_bswap32_tl(cpu_regs[reg], cpu_regs[reg], TCG_BSWAP_OZ);
5542         break;
5543     case 0xd6: /* salc */
5544         if (CODE64(s))
5545             goto illegal_op;
5546         gen_compute_eflags_c(s, s->T0);
5547         tcg_gen_neg_tl(s->T0, s->T0);
5548         gen_op_mov_reg_v(s, MO_8, R_EAX, s->T0);
5549         break;
5550     case 0xe0: /* loopnz */
5551     case 0xe1: /* loopz */
5552     case 0xe2: /* loop */
5553     case 0xe3: /* jecxz */
5554         {
5555             TCGLabel *l1, *l2;
5556             int diff = (int8_t)insn_get(env, s, MO_8);
5557 
5558             l1 = gen_new_label();
5559             l2 = gen_new_label();
5560             gen_update_cc_op(s);
5561             b &= 3;
5562             switch(b) {
5563             case 0: /* loopnz */
5564             case 1: /* loopz */
5565                 gen_op_add_reg_im(s, s->aflag, R_ECX, -1);
5566                 gen_op_jz_ecx(s, l2);
5567                 gen_jcc1(s, (JCC_Z << 1) | (b ^ 1), l1);
5568                 break;
5569             case 2: /* loop */
5570                 gen_op_add_reg_im(s, s->aflag, R_ECX, -1);
5571                 gen_op_jnz_ecx(s, l1);
5572                 break;
5573             default:
5574             case 3: /* jcxz */
5575                 gen_op_jz_ecx(s, l1);
5576                 break;
5577             }
5578 
5579             gen_set_label(l2);
5580             gen_jmp_rel_csize(s, 0, 1);
5581 
5582             gen_set_label(l1);
5583             gen_jmp_rel(s, dflag, diff, 0);
5584         }
5585         break;
5586     case 0x130: /* wrmsr */
5587     case 0x132: /* rdmsr */
5588         if (check_cpl0(s)) {
5589             gen_update_cc_op(s);
5590             gen_update_eip_cur(s);
5591             if (b & 2) {
5592                 gen_helper_rdmsr(cpu_env);
5593             } else {
5594                 gen_helper_wrmsr(cpu_env);
5595                 s->base.is_jmp = DISAS_EOB_NEXT;
5596             }
5597         }
5598         break;
5599     case 0x131: /* rdtsc */
5600         gen_update_cc_op(s);
5601         gen_update_eip_cur(s);
5602         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
5603             gen_io_start();
5604             s->base.is_jmp = DISAS_TOO_MANY;
5605         }
5606         gen_helper_rdtsc(cpu_env);
5607         break;
5608     case 0x133: /* rdpmc */
5609         gen_update_cc_op(s);
5610         gen_update_eip_cur(s);
5611         gen_helper_rdpmc(cpu_env);
5612         s->base.is_jmp = DISAS_NORETURN;
5613         break;
5614     case 0x134: /* sysenter */
5615         /* For Intel SYSENTER is valid on 64-bit */
5616         if (CODE64(s) && env->cpuid_vendor1 != CPUID_VENDOR_INTEL_1)
5617             goto illegal_op;
5618         if (!PE(s)) {
5619             gen_exception_gpf(s);
5620         } else {
5621             gen_helper_sysenter(cpu_env);
5622             s->base.is_jmp = DISAS_EOB_ONLY;
5623         }
5624         break;
5625     case 0x135: /* sysexit */
5626         /* For Intel SYSEXIT is valid on 64-bit */
5627         if (CODE64(s) && env->cpuid_vendor1 != CPUID_VENDOR_INTEL_1)
5628             goto illegal_op;
5629         if (!PE(s)) {
5630             gen_exception_gpf(s);
5631         } else {
5632             gen_helper_sysexit(cpu_env, tcg_const_i32(dflag - 1));
5633             s->base.is_jmp = DISAS_EOB_ONLY;
5634         }
5635         break;
5636 #ifdef TARGET_X86_64
5637     case 0x105: /* syscall */
5638         /* XXX: is it usable in real mode ? */
5639         gen_update_cc_op(s);
5640         gen_update_eip_cur(s);
5641         gen_helper_syscall(cpu_env, cur_insn_len_i32(s));
5642         /* TF handling for the syscall insn is different. The TF bit is  checked
5643            after the syscall insn completes. This allows #DB to not be
5644            generated after one has entered CPL0 if TF is set in FMASK.  */
5645         gen_eob_worker(s, false, true);
5646         break;
5647     case 0x107: /* sysret */
5648         if (!PE(s)) {
5649             gen_exception_gpf(s);
5650         } else {
5651             gen_helper_sysret(cpu_env, tcg_const_i32(dflag - 1));
5652             /* condition codes are modified only in long mode */
5653             if (LMA(s)) {
5654                 set_cc_op(s, CC_OP_EFLAGS);
5655             }
5656             /* TF handling for the sysret insn is different. The TF bit is
5657                checked after the sysret insn completes. This allows #DB to be
5658                generated "as if" the syscall insn in userspace has just
5659                completed.  */
5660             gen_eob_worker(s, false, true);
5661         }
5662         break;
5663 #endif
5664     case 0x1a2: /* cpuid */
5665         gen_update_cc_op(s);
5666         gen_update_eip_cur(s);
5667         gen_helper_cpuid(cpu_env);
5668         break;
5669     case 0xf4: /* hlt */
5670         if (check_cpl0(s)) {
5671             gen_update_cc_op(s);
5672             gen_update_eip_cur(s);
5673             gen_helper_hlt(cpu_env, cur_insn_len_i32(s));
5674             s->base.is_jmp = DISAS_NORETURN;
5675         }
5676         break;
5677     case 0x100:
5678         modrm = x86_ldub_code(env, s);
5679         mod = (modrm >> 6) & 3;
5680         op = (modrm >> 3) & 7;
5681         switch(op) {
5682         case 0: /* sldt */
5683             if (!PE(s) || VM86(s))
5684                 goto illegal_op;
5685             if (s->flags & HF_UMIP_MASK && !check_cpl0(s)) {
5686                 break;
5687             }
5688             gen_svm_check_intercept(s, SVM_EXIT_LDTR_READ);
5689             tcg_gen_ld32u_tl(s->T0, cpu_env,
5690                              offsetof(CPUX86State, ldt.selector));
5691             ot = mod == 3 ? dflag : MO_16;
5692             gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 1);
5693             break;
5694         case 2: /* lldt */
5695             if (!PE(s) || VM86(s))
5696                 goto illegal_op;
5697             if (check_cpl0(s)) {
5698                 gen_svm_check_intercept(s, SVM_EXIT_LDTR_WRITE);
5699                 gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
5700                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
5701                 gen_helper_lldt(cpu_env, s->tmp2_i32);
5702             }
5703             break;
5704         case 1: /* str */
5705             if (!PE(s) || VM86(s))
5706                 goto illegal_op;
5707             if (s->flags & HF_UMIP_MASK && !check_cpl0(s)) {
5708                 break;
5709             }
5710             gen_svm_check_intercept(s, SVM_EXIT_TR_READ);
5711             tcg_gen_ld32u_tl(s->T0, cpu_env,
5712                              offsetof(CPUX86State, tr.selector));
5713             ot = mod == 3 ? dflag : MO_16;
5714             gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 1);
5715             break;
5716         case 3: /* ltr */
5717             if (!PE(s) || VM86(s))
5718                 goto illegal_op;
5719             if (check_cpl0(s)) {
5720                 gen_svm_check_intercept(s, SVM_EXIT_TR_WRITE);
5721                 gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
5722                 tcg_gen_trunc_tl_i32(s->tmp2_i32, s->T0);
5723                 gen_helper_ltr(cpu_env, s->tmp2_i32);
5724             }
5725             break;
5726         case 4: /* verr */
5727         case 5: /* verw */
5728             if (!PE(s) || VM86(s))
5729                 goto illegal_op;
5730             gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
5731             gen_update_cc_op(s);
5732             if (op == 4) {
5733                 gen_helper_verr(cpu_env, s->T0);
5734             } else {
5735                 gen_helper_verw(cpu_env, s->T0);
5736             }
5737             set_cc_op(s, CC_OP_EFLAGS);
5738             break;
5739         default:
5740             goto unknown_op;
5741         }
5742         break;
5743 
5744     case 0x101:
5745         modrm = x86_ldub_code(env, s);
5746         switch (modrm) {
5747         CASE_MODRM_MEM_OP(0): /* sgdt */
5748             if (s->flags & HF_UMIP_MASK && !check_cpl0(s)) {
5749                 break;
5750             }
5751             gen_svm_check_intercept(s, SVM_EXIT_GDTR_READ);
5752             gen_lea_modrm(env, s, modrm);
5753             tcg_gen_ld32u_tl(s->T0,
5754                              cpu_env, offsetof(CPUX86State, gdt.limit));
5755             gen_op_st_v(s, MO_16, s->T0, s->A0);
5756             gen_add_A0_im(s, 2);
5757             tcg_gen_ld_tl(s->T0, cpu_env, offsetof(CPUX86State, gdt.base));
5758             if (dflag == MO_16) {
5759                 tcg_gen_andi_tl(s->T0, s->T0, 0xffffff);
5760             }
5761             gen_op_st_v(s, CODE64(s) + MO_32, s->T0, s->A0);
5762             break;
5763 
5764         case 0xc8: /* monitor */
5765             if (!(s->cpuid_ext_features & CPUID_EXT_MONITOR) || CPL(s) != 0) {
5766                 goto illegal_op;
5767             }
5768             gen_update_cc_op(s);
5769             gen_update_eip_cur(s);
5770             tcg_gen_mov_tl(s->A0, cpu_regs[R_EAX]);
5771             gen_extu(s->aflag, s->A0);
5772             gen_add_A0_ds_seg(s);
5773             gen_helper_monitor(cpu_env, s->A0);
5774             break;
5775 
5776         case 0xc9: /* mwait */
5777             if (!(s->cpuid_ext_features & CPUID_EXT_MONITOR) || CPL(s) != 0) {
5778                 goto illegal_op;
5779             }
5780             gen_update_cc_op(s);
5781             gen_update_eip_cur(s);
5782             gen_helper_mwait(cpu_env, cur_insn_len_i32(s));
5783             s->base.is_jmp = DISAS_NORETURN;
5784             break;
5785 
5786         case 0xca: /* clac */
5787             if (!(s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_SMAP)
5788                 || CPL(s) != 0) {
5789                 goto illegal_op;
5790             }
5791             gen_helper_clac(cpu_env);
5792             s->base.is_jmp = DISAS_EOB_NEXT;
5793             break;
5794 
5795         case 0xcb: /* stac */
5796             if (!(s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_SMAP)
5797                 || CPL(s) != 0) {
5798                 goto illegal_op;
5799             }
5800             gen_helper_stac(cpu_env);
5801             s->base.is_jmp = DISAS_EOB_NEXT;
5802             break;
5803 
5804         CASE_MODRM_MEM_OP(1): /* sidt */
5805             if (s->flags & HF_UMIP_MASK && !check_cpl0(s)) {
5806                 break;
5807             }
5808             gen_svm_check_intercept(s, SVM_EXIT_IDTR_READ);
5809             gen_lea_modrm(env, s, modrm);
5810             tcg_gen_ld32u_tl(s->T0, cpu_env, offsetof(CPUX86State, idt.limit));
5811             gen_op_st_v(s, MO_16, s->T0, s->A0);
5812             gen_add_A0_im(s, 2);
5813             tcg_gen_ld_tl(s->T0, cpu_env, offsetof(CPUX86State, idt.base));
5814             if (dflag == MO_16) {
5815                 tcg_gen_andi_tl(s->T0, s->T0, 0xffffff);
5816             }
5817             gen_op_st_v(s, CODE64(s) + MO_32, s->T0, s->A0);
5818             break;
5819 
5820         case 0xd0: /* xgetbv */
5821             if ((s->cpuid_ext_features & CPUID_EXT_XSAVE) == 0
5822                 || (s->prefix & (PREFIX_LOCK | PREFIX_DATA
5823                                  | PREFIX_REPZ | PREFIX_REPNZ))) {
5824                 goto illegal_op;
5825             }
5826             tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_ECX]);
5827             gen_helper_xgetbv(s->tmp1_i64, cpu_env, s->tmp2_i32);
5828             tcg_gen_extr_i64_tl(cpu_regs[R_EAX], cpu_regs[R_EDX], s->tmp1_i64);
5829             break;
5830 
5831         case 0xd1: /* xsetbv */
5832             if ((s->cpuid_ext_features & CPUID_EXT_XSAVE) == 0
5833                 || (s->prefix & (PREFIX_LOCK | PREFIX_DATA
5834                                  | PREFIX_REPZ | PREFIX_REPNZ))) {
5835                 goto illegal_op;
5836             }
5837             if (!check_cpl0(s)) {
5838                 break;
5839             }
5840             tcg_gen_concat_tl_i64(s->tmp1_i64, cpu_regs[R_EAX],
5841                                   cpu_regs[R_EDX]);
5842             tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_ECX]);
5843             gen_helper_xsetbv(cpu_env, s->tmp2_i32, s->tmp1_i64);
5844             /* End TB because translation flags may change.  */
5845             s->base.is_jmp = DISAS_EOB_NEXT;
5846             break;
5847 
5848         case 0xd8: /* VMRUN */
5849             if (!SVME(s) || !PE(s)) {
5850                 goto illegal_op;
5851             }
5852             if (!check_cpl0(s)) {
5853                 break;
5854             }
5855             gen_update_cc_op(s);
5856             gen_update_eip_cur(s);
5857             gen_helper_vmrun(cpu_env, tcg_const_i32(s->aflag - 1),
5858                              cur_insn_len_i32(s));
5859             tcg_gen_exit_tb(NULL, 0);
5860             s->base.is_jmp = DISAS_NORETURN;
5861             break;
5862 
5863         case 0xd9: /* VMMCALL */
5864             if (!SVME(s)) {
5865                 goto illegal_op;
5866             }
5867             gen_update_cc_op(s);
5868             gen_update_eip_cur(s);
5869             gen_helper_vmmcall(cpu_env);
5870             break;
5871 
5872         case 0xda: /* VMLOAD */
5873             if (!SVME(s) || !PE(s)) {
5874                 goto illegal_op;
5875             }
5876             if (!check_cpl0(s)) {
5877                 break;
5878             }
5879             gen_update_cc_op(s);
5880             gen_update_eip_cur(s);
5881             gen_helper_vmload(cpu_env, tcg_const_i32(s->aflag - 1));
5882             break;
5883 
5884         case 0xdb: /* VMSAVE */
5885             if (!SVME(s) || !PE(s)) {
5886                 goto illegal_op;
5887             }
5888             if (!check_cpl0(s)) {
5889                 break;
5890             }
5891             gen_update_cc_op(s);
5892             gen_update_eip_cur(s);
5893             gen_helper_vmsave(cpu_env, tcg_const_i32(s->aflag - 1));
5894             break;
5895 
5896         case 0xdc: /* STGI */
5897             if ((!SVME(s) && !(s->cpuid_ext3_features & CPUID_EXT3_SKINIT))
5898                 || !PE(s)) {
5899                 goto illegal_op;
5900             }
5901             if (!check_cpl0(s)) {
5902                 break;
5903             }
5904             gen_update_cc_op(s);
5905             gen_helper_stgi(cpu_env);
5906             s->base.is_jmp = DISAS_EOB_NEXT;
5907             break;
5908 
5909         case 0xdd: /* CLGI */
5910             if (!SVME(s) || !PE(s)) {
5911                 goto illegal_op;
5912             }
5913             if (!check_cpl0(s)) {
5914                 break;
5915             }
5916             gen_update_cc_op(s);
5917             gen_update_eip_cur(s);
5918             gen_helper_clgi(cpu_env);
5919             break;
5920 
5921         case 0xde: /* SKINIT */
5922             if ((!SVME(s) && !(s->cpuid_ext3_features & CPUID_EXT3_SKINIT))
5923                 || !PE(s)) {
5924                 goto illegal_op;
5925             }
5926             gen_svm_check_intercept(s, SVM_EXIT_SKINIT);
5927             /* If not intercepted, not implemented -- raise #UD. */
5928             goto illegal_op;
5929 
5930         case 0xdf: /* INVLPGA */
5931             if (!SVME(s) || !PE(s)) {
5932                 goto illegal_op;
5933             }
5934             if (!check_cpl0(s)) {
5935                 break;
5936             }
5937             gen_svm_check_intercept(s, SVM_EXIT_INVLPGA);
5938             if (s->aflag == MO_64) {
5939                 tcg_gen_mov_tl(s->A0, cpu_regs[R_EAX]);
5940             } else {
5941                 tcg_gen_ext32u_tl(s->A0, cpu_regs[R_EAX]);
5942             }
5943             gen_helper_flush_page(cpu_env, s->A0);
5944             s->base.is_jmp = DISAS_EOB_NEXT;
5945             break;
5946 
5947         CASE_MODRM_MEM_OP(2): /* lgdt */
5948             if (!check_cpl0(s)) {
5949                 break;
5950             }
5951             gen_svm_check_intercept(s, SVM_EXIT_GDTR_WRITE);
5952             gen_lea_modrm(env, s, modrm);
5953             gen_op_ld_v(s, MO_16, s->T1, s->A0);
5954             gen_add_A0_im(s, 2);
5955             gen_op_ld_v(s, CODE64(s) + MO_32, s->T0, s->A0);
5956             if (dflag == MO_16) {
5957                 tcg_gen_andi_tl(s->T0, s->T0, 0xffffff);
5958             }
5959             tcg_gen_st_tl(s->T0, cpu_env, offsetof(CPUX86State, gdt.base));
5960             tcg_gen_st32_tl(s->T1, cpu_env, offsetof(CPUX86State, gdt.limit));
5961             break;
5962 
5963         CASE_MODRM_MEM_OP(3): /* lidt */
5964             if (!check_cpl0(s)) {
5965                 break;
5966             }
5967             gen_svm_check_intercept(s, SVM_EXIT_IDTR_WRITE);
5968             gen_lea_modrm(env, s, modrm);
5969             gen_op_ld_v(s, MO_16, s->T1, s->A0);
5970             gen_add_A0_im(s, 2);
5971             gen_op_ld_v(s, CODE64(s) + MO_32, s->T0, s->A0);
5972             if (dflag == MO_16) {
5973                 tcg_gen_andi_tl(s->T0, s->T0, 0xffffff);
5974             }
5975             tcg_gen_st_tl(s->T0, cpu_env, offsetof(CPUX86State, idt.base));
5976             tcg_gen_st32_tl(s->T1, cpu_env, offsetof(CPUX86State, idt.limit));
5977             break;
5978 
5979         CASE_MODRM_OP(4): /* smsw */
5980             if (s->flags & HF_UMIP_MASK && !check_cpl0(s)) {
5981                 break;
5982             }
5983             gen_svm_check_intercept(s, SVM_EXIT_READ_CR0);
5984             tcg_gen_ld_tl(s->T0, cpu_env, offsetof(CPUX86State, cr[0]));
5985             /*
5986              * In 32-bit mode, the higher 16 bits of the destination
5987              * register are undefined.  In practice CR0[31:0] is stored
5988              * just like in 64-bit mode.
5989              */
5990             mod = (modrm >> 6) & 3;
5991             ot = (mod != 3 ? MO_16 : s->dflag);
5992             gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 1);
5993             break;
5994         case 0xee: /* rdpkru */
5995             if (prefixes & PREFIX_LOCK) {
5996                 goto illegal_op;
5997             }
5998             tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_ECX]);
5999             gen_helper_rdpkru(s->tmp1_i64, cpu_env, s->tmp2_i32);
6000             tcg_gen_extr_i64_tl(cpu_regs[R_EAX], cpu_regs[R_EDX], s->tmp1_i64);
6001             break;
6002         case 0xef: /* wrpkru */
6003             if (prefixes & PREFIX_LOCK) {
6004                 goto illegal_op;
6005             }
6006             tcg_gen_concat_tl_i64(s->tmp1_i64, cpu_regs[R_EAX],
6007                                   cpu_regs[R_EDX]);
6008             tcg_gen_trunc_tl_i32(s->tmp2_i32, cpu_regs[R_ECX]);
6009             gen_helper_wrpkru(cpu_env, s->tmp2_i32, s->tmp1_i64);
6010             break;
6011 
6012         CASE_MODRM_OP(6): /* lmsw */
6013             if (!check_cpl0(s)) {
6014                 break;
6015             }
6016             gen_svm_check_intercept(s, SVM_EXIT_WRITE_CR0);
6017             gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
6018             /*
6019              * Only the 4 lower bits of CR0 are modified.
6020              * PE cannot be set to zero if already set to one.
6021              */
6022             tcg_gen_ld_tl(s->T1, cpu_env, offsetof(CPUX86State, cr[0]));
6023             tcg_gen_andi_tl(s->T0, s->T0, 0xf);
6024             tcg_gen_andi_tl(s->T1, s->T1, ~0xe);
6025             tcg_gen_or_tl(s->T0, s->T0, s->T1);
6026             gen_helper_write_crN(cpu_env, tcg_constant_i32(0), s->T0);
6027             s->base.is_jmp = DISAS_EOB_NEXT;
6028             break;
6029 
6030         CASE_MODRM_MEM_OP(7): /* invlpg */
6031             if (!check_cpl0(s)) {
6032                 break;
6033             }
6034             gen_svm_check_intercept(s, SVM_EXIT_INVLPG);
6035             gen_lea_modrm(env, s, modrm);
6036             gen_helper_flush_page(cpu_env, s->A0);
6037             s->base.is_jmp = DISAS_EOB_NEXT;
6038             break;
6039 
6040         case 0xf8: /* swapgs */
6041 #ifdef TARGET_X86_64
6042             if (CODE64(s)) {
6043                 if (check_cpl0(s)) {
6044                     tcg_gen_mov_tl(s->T0, cpu_seg_base[R_GS]);
6045                     tcg_gen_ld_tl(cpu_seg_base[R_GS], cpu_env,
6046                                   offsetof(CPUX86State, kernelgsbase));
6047                     tcg_gen_st_tl(s->T0, cpu_env,
6048                                   offsetof(CPUX86State, kernelgsbase));
6049                 }
6050                 break;
6051             }
6052 #endif
6053             goto illegal_op;
6054 
6055         case 0xf9: /* rdtscp */
6056             if (!(s->cpuid_ext2_features & CPUID_EXT2_RDTSCP)) {
6057                 goto illegal_op;
6058             }
6059             gen_update_cc_op(s);
6060             gen_update_eip_cur(s);
6061             if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
6062                 gen_io_start();
6063                 s->base.is_jmp = DISAS_TOO_MANY;
6064             }
6065             gen_helper_rdtscp(cpu_env);
6066             break;
6067 
6068         default:
6069             goto unknown_op;
6070         }
6071         break;
6072 
6073     case 0x108: /* invd */
6074     case 0x109: /* wbinvd */
6075         if (check_cpl0(s)) {
6076             gen_svm_check_intercept(s, (b & 2) ? SVM_EXIT_INVD : SVM_EXIT_WBINVD);
6077             /* nothing to do */
6078         }
6079         break;
6080     case 0x63: /* arpl or movslS (x86_64) */
6081 #ifdef TARGET_X86_64
6082         if (CODE64(s)) {
6083             int d_ot;
6084             /* d_ot is the size of destination */
6085             d_ot = dflag;
6086 
6087             modrm = x86_ldub_code(env, s);
6088             reg = ((modrm >> 3) & 7) | REX_R(s);
6089             mod = (modrm >> 6) & 3;
6090             rm = (modrm & 7) | REX_B(s);
6091 
6092             if (mod == 3) {
6093                 gen_op_mov_v_reg(s, MO_32, s->T0, rm);
6094                 /* sign extend */
6095                 if (d_ot == MO_64) {
6096                     tcg_gen_ext32s_tl(s->T0, s->T0);
6097                 }
6098                 gen_op_mov_reg_v(s, d_ot, reg, s->T0);
6099             } else {
6100                 gen_lea_modrm(env, s, modrm);
6101                 gen_op_ld_v(s, MO_32 | MO_SIGN, s->T0, s->A0);
6102                 gen_op_mov_reg_v(s, d_ot, reg, s->T0);
6103             }
6104         } else
6105 #endif
6106         {
6107             TCGLabel *label1;
6108             TCGv t0, t1, t2, a0;
6109 
6110             if (!PE(s) || VM86(s))
6111                 goto illegal_op;
6112             t0 = tcg_temp_local_new();
6113             t1 = tcg_temp_local_new();
6114             t2 = tcg_temp_local_new();
6115             ot = MO_16;
6116             modrm = x86_ldub_code(env, s);
6117             reg = (modrm >> 3) & 7;
6118             mod = (modrm >> 6) & 3;
6119             rm = modrm & 7;
6120             if (mod != 3) {
6121                 gen_lea_modrm(env, s, modrm);
6122                 gen_op_ld_v(s, ot, t0, s->A0);
6123                 a0 = tcg_temp_local_new();
6124                 tcg_gen_mov_tl(a0, s->A0);
6125             } else {
6126                 gen_op_mov_v_reg(s, ot, t0, rm);
6127                 a0 = NULL;
6128             }
6129             gen_op_mov_v_reg(s, ot, t1, reg);
6130             tcg_gen_andi_tl(s->tmp0, t0, 3);
6131             tcg_gen_andi_tl(t1, t1, 3);
6132             tcg_gen_movi_tl(t2, 0);
6133             label1 = gen_new_label();
6134             tcg_gen_brcond_tl(TCG_COND_GE, s->tmp0, t1, label1);
6135             tcg_gen_andi_tl(t0, t0, ~3);
6136             tcg_gen_or_tl(t0, t0, t1);
6137             tcg_gen_movi_tl(t2, CC_Z);
6138             gen_set_label(label1);
6139             if (mod != 3) {
6140                 gen_op_st_v(s, ot, t0, a0);
6141                 tcg_temp_free(a0);
6142            } else {
6143                 gen_op_mov_reg_v(s, ot, rm, t0);
6144             }
6145             gen_compute_eflags(s);
6146             tcg_gen_andi_tl(cpu_cc_src, cpu_cc_src, ~CC_Z);
6147             tcg_gen_or_tl(cpu_cc_src, cpu_cc_src, t2);
6148             tcg_temp_free(t0);
6149             tcg_temp_free(t1);
6150             tcg_temp_free(t2);
6151         }
6152         break;
6153     case 0x102: /* lar */
6154     case 0x103: /* lsl */
6155         {
6156             TCGLabel *label1;
6157             TCGv t0;
6158             if (!PE(s) || VM86(s))
6159                 goto illegal_op;
6160             ot = dflag != MO_16 ? MO_32 : MO_16;
6161             modrm = x86_ldub_code(env, s);
6162             reg = ((modrm >> 3) & 7) | REX_R(s);
6163             gen_ldst_modrm(env, s, modrm, MO_16, OR_TMP0, 0);
6164             t0 = tcg_temp_local_new();
6165             gen_update_cc_op(s);
6166             if (b == 0x102) {
6167                 gen_helper_lar(t0, cpu_env, s->T0);
6168             } else {
6169                 gen_helper_lsl(t0, cpu_env, s->T0);
6170             }
6171             tcg_gen_andi_tl(s->tmp0, cpu_cc_src, CC_Z);
6172             label1 = gen_new_label();
6173             tcg_gen_brcondi_tl(TCG_COND_EQ, s->tmp0, 0, label1);
6174             gen_op_mov_reg_v(s, ot, reg, t0);
6175             gen_set_label(label1);
6176             set_cc_op(s, CC_OP_EFLAGS);
6177             tcg_temp_free(t0);
6178         }
6179         break;
6180     case 0x118:
6181         modrm = x86_ldub_code(env, s);
6182         mod = (modrm >> 6) & 3;
6183         op = (modrm >> 3) & 7;
6184         switch(op) {
6185         case 0: /* prefetchnta */
6186         case 1: /* prefetchnt0 */
6187         case 2: /* prefetchnt0 */
6188         case 3: /* prefetchnt0 */
6189             if (mod == 3)
6190                 goto illegal_op;
6191             gen_nop_modrm(env, s, modrm);
6192             /* nothing more to do */
6193             break;
6194         default: /* nop (multi byte) */
6195             gen_nop_modrm(env, s, modrm);
6196             break;
6197         }
6198         break;
6199     case 0x11a:
6200         modrm = x86_ldub_code(env, s);
6201         if (s->flags & HF_MPX_EN_MASK) {
6202             mod = (modrm >> 6) & 3;
6203             reg = ((modrm >> 3) & 7) | REX_R(s);
6204             if (prefixes & PREFIX_REPZ) {
6205                 /* bndcl */
6206                 if (reg >= 4
6207                     || (prefixes & PREFIX_LOCK)
6208                     || s->aflag == MO_16) {
6209                     goto illegal_op;
6210                 }
6211                 gen_bndck(env, s, modrm, TCG_COND_LTU, cpu_bndl[reg]);
6212             } else if (prefixes & PREFIX_REPNZ) {
6213                 /* bndcu */
6214                 if (reg >= 4
6215                     || (prefixes & PREFIX_LOCK)
6216                     || s->aflag == MO_16) {
6217                     goto illegal_op;
6218                 }
6219                 TCGv_i64 notu = tcg_temp_new_i64();
6220                 tcg_gen_not_i64(notu, cpu_bndu[reg]);
6221                 gen_bndck(env, s, modrm, TCG_COND_GTU, notu);
6222                 tcg_temp_free_i64(notu);
6223             } else if (prefixes & PREFIX_DATA) {
6224                 /* bndmov -- from reg/mem */
6225                 if (reg >= 4 || s->aflag == MO_16) {
6226                     goto illegal_op;
6227                 }
6228                 if (mod == 3) {
6229                     int reg2 = (modrm & 7) | REX_B(s);
6230                     if (reg2 >= 4 || (prefixes & PREFIX_LOCK)) {
6231                         goto illegal_op;
6232                     }
6233                     if (s->flags & HF_MPX_IU_MASK) {
6234                         tcg_gen_mov_i64(cpu_bndl[reg], cpu_bndl[reg2]);
6235                         tcg_gen_mov_i64(cpu_bndu[reg], cpu_bndu[reg2]);
6236                     }
6237                 } else {
6238                     gen_lea_modrm(env, s, modrm);
6239                     if (CODE64(s)) {
6240                         tcg_gen_qemu_ld_i64(cpu_bndl[reg], s->A0,
6241                                             s->mem_index, MO_LEUQ);
6242                         tcg_gen_addi_tl(s->A0, s->A0, 8);
6243                         tcg_gen_qemu_ld_i64(cpu_bndu[reg], s->A0,
6244                                             s->mem_index, MO_LEUQ);
6245                     } else {
6246                         tcg_gen_qemu_ld_i64(cpu_bndl[reg], s->A0,
6247                                             s->mem_index, MO_LEUL);
6248                         tcg_gen_addi_tl(s->A0, s->A0, 4);
6249                         tcg_gen_qemu_ld_i64(cpu_bndu[reg], s->A0,
6250                                             s->mem_index, MO_LEUL);
6251                     }
6252                     /* bnd registers are now in-use */
6253                     gen_set_hflag(s, HF_MPX_IU_MASK);
6254                 }
6255             } else if (mod != 3) {
6256                 /* bndldx */
6257                 AddressParts a = gen_lea_modrm_0(env, s, modrm);
6258                 if (reg >= 4
6259                     || (prefixes & PREFIX_LOCK)
6260                     || s->aflag == MO_16
6261                     || a.base < -1) {
6262                     goto illegal_op;
6263                 }
6264                 if (a.base >= 0) {
6265                     tcg_gen_addi_tl(s->A0, cpu_regs[a.base], a.disp);
6266                 } else {
6267                     tcg_gen_movi_tl(s->A0, 0);
6268                 }
6269                 gen_lea_v_seg(s, s->aflag, s->A0, a.def_seg, s->override);
6270                 if (a.index >= 0) {
6271                     tcg_gen_mov_tl(s->T0, cpu_regs[a.index]);
6272                 } else {
6273                     tcg_gen_movi_tl(s->T0, 0);
6274                 }
6275                 if (CODE64(s)) {
6276                     gen_helper_bndldx64(cpu_bndl[reg], cpu_env, s->A0, s->T0);
6277                     tcg_gen_ld_i64(cpu_bndu[reg], cpu_env,
6278                                    offsetof(CPUX86State, mmx_t0.MMX_Q(0)));
6279                 } else {
6280                     gen_helper_bndldx32(cpu_bndu[reg], cpu_env, s->A0, s->T0);
6281                     tcg_gen_ext32u_i64(cpu_bndl[reg], cpu_bndu[reg]);
6282                     tcg_gen_shri_i64(cpu_bndu[reg], cpu_bndu[reg], 32);
6283                 }
6284                 gen_set_hflag(s, HF_MPX_IU_MASK);
6285             }
6286         }
6287         gen_nop_modrm(env, s, modrm);
6288         break;
6289     case 0x11b:
6290         modrm = x86_ldub_code(env, s);
6291         if (s->flags & HF_MPX_EN_MASK) {
6292             mod = (modrm >> 6) & 3;
6293             reg = ((modrm >> 3) & 7) | REX_R(s);
6294             if (mod != 3 && (prefixes & PREFIX_REPZ)) {
6295                 /* bndmk */
6296                 if (reg >= 4
6297                     || (prefixes & PREFIX_LOCK)
6298                     || s->aflag == MO_16) {
6299                     goto illegal_op;
6300                 }
6301                 AddressParts a = gen_lea_modrm_0(env, s, modrm);
6302                 if (a.base >= 0) {
6303                     tcg_gen_extu_tl_i64(cpu_bndl[reg], cpu_regs[a.base]);
6304                     if (!CODE64(s)) {
6305                         tcg_gen_ext32u_i64(cpu_bndl[reg], cpu_bndl[reg]);
6306                     }
6307                 } else if (a.base == -1) {
6308                     /* no base register has lower bound of 0 */
6309                     tcg_gen_movi_i64(cpu_bndl[reg], 0);
6310                 } else {
6311                     /* rip-relative generates #ud */
6312                     goto illegal_op;
6313                 }
6314                 tcg_gen_not_tl(s->A0, gen_lea_modrm_1(s, a, false));
6315                 if (!CODE64(s)) {
6316                     tcg_gen_ext32u_tl(s->A0, s->A0);
6317                 }
6318                 tcg_gen_extu_tl_i64(cpu_bndu[reg], s->A0);
6319                 /* bnd registers are now in-use */
6320                 gen_set_hflag(s, HF_MPX_IU_MASK);
6321                 break;
6322             } else if (prefixes & PREFIX_REPNZ) {
6323                 /* bndcn */
6324                 if (reg >= 4
6325                     || (prefixes & PREFIX_LOCK)
6326                     || s->aflag == MO_16) {
6327                     goto illegal_op;
6328                 }
6329                 gen_bndck(env, s, modrm, TCG_COND_GTU, cpu_bndu[reg]);
6330             } else if (prefixes & PREFIX_DATA) {
6331                 /* bndmov -- to reg/mem */
6332                 if (reg >= 4 || s->aflag == MO_16) {
6333                     goto illegal_op;
6334                 }
6335                 if (mod == 3) {
6336                     int reg2 = (modrm & 7) | REX_B(s);
6337                     if (reg2 >= 4 || (prefixes & PREFIX_LOCK)) {
6338                         goto illegal_op;
6339                     }
6340                     if (s->flags & HF_MPX_IU_MASK) {
6341                         tcg_gen_mov_i64(cpu_bndl[reg2], cpu_bndl[reg]);
6342                         tcg_gen_mov_i64(cpu_bndu[reg2], cpu_bndu[reg]);
6343                     }
6344                 } else {
6345                     gen_lea_modrm(env, s, modrm);
6346                     if (CODE64(s)) {
6347                         tcg_gen_qemu_st_i64(cpu_bndl[reg], s->A0,
6348                                             s->mem_index, MO_LEUQ);
6349                         tcg_gen_addi_tl(s->A0, s->A0, 8);
6350                         tcg_gen_qemu_st_i64(cpu_bndu[reg], s->A0,
6351                                             s->mem_index, MO_LEUQ);
6352                     } else {
6353                         tcg_gen_qemu_st_i64(cpu_bndl[reg], s->A0,
6354                                             s->mem_index, MO_LEUL);
6355                         tcg_gen_addi_tl(s->A0, s->A0, 4);
6356                         tcg_gen_qemu_st_i64(cpu_bndu[reg], s->A0,
6357                                             s->mem_index, MO_LEUL);
6358                     }
6359                 }
6360             } else if (mod != 3) {
6361                 /* bndstx */
6362                 AddressParts a = gen_lea_modrm_0(env, s, modrm);
6363                 if (reg >= 4
6364                     || (prefixes & PREFIX_LOCK)
6365                     || s->aflag == MO_16
6366                     || a.base < -1) {
6367                     goto illegal_op;
6368                 }
6369                 if (a.base >= 0) {
6370                     tcg_gen_addi_tl(s->A0, cpu_regs[a.base], a.disp);
6371                 } else {
6372                     tcg_gen_movi_tl(s->A0, 0);
6373                 }
6374                 gen_lea_v_seg(s, s->aflag, s->A0, a.def_seg, s->override);
6375                 if (a.index >= 0) {
6376                     tcg_gen_mov_tl(s->T0, cpu_regs[a.index]);
6377                 } else {
6378                     tcg_gen_movi_tl(s->T0, 0);
6379                 }
6380                 if (CODE64(s)) {
6381                     gen_helper_bndstx64(cpu_env, s->A0, s->T0,
6382                                         cpu_bndl[reg], cpu_bndu[reg]);
6383                 } else {
6384                     gen_helper_bndstx32(cpu_env, s->A0, s->T0,
6385                                         cpu_bndl[reg], cpu_bndu[reg]);
6386                 }
6387             }
6388         }
6389         gen_nop_modrm(env, s, modrm);
6390         break;
6391     case 0x119: case 0x11c ... 0x11f: /* nop (multi byte) */
6392         modrm = x86_ldub_code(env, s);
6393         gen_nop_modrm(env, s, modrm);
6394         break;
6395 
6396     case 0x120: /* mov reg, crN */
6397     case 0x122: /* mov crN, reg */
6398         if (!check_cpl0(s)) {
6399             break;
6400         }
6401         modrm = x86_ldub_code(env, s);
6402         /*
6403          * Ignore the mod bits (assume (modrm&0xc0)==0xc0).
6404          * AMD documentation (24594.pdf) and testing of Intel 386 and 486
6405          * processors all show that the mod bits are assumed to be 1's,
6406          * regardless of actual values.
6407          */
6408         rm = (modrm & 7) | REX_B(s);
6409         reg = ((modrm >> 3) & 7) | REX_R(s);
6410         switch (reg) {
6411         case 0:
6412             if ((prefixes & PREFIX_LOCK) &&
6413                 (s->cpuid_ext3_features & CPUID_EXT3_CR8LEG)) {
6414                 reg = 8;
6415             }
6416             break;
6417         case 2:
6418         case 3:
6419         case 4:
6420         case 8:
6421             break;
6422         default:
6423             goto unknown_op;
6424         }
6425         ot  = (CODE64(s) ? MO_64 : MO_32);
6426 
6427         if (tb_cflags(s->base.tb) & CF_USE_ICOUNT) {
6428             gen_io_start();
6429             s->base.is_jmp = DISAS_TOO_MANY;
6430         }
6431         if (b & 2) {
6432             gen_svm_check_intercept(s, SVM_EXIT_WRITE_CR0 + reg);
6433             gen_op_mov_v_reg(s, ot, s->T0, rm);
6434             gen_helper_write_crN(cpu_env, tcg_constant_i32(reg), s->T0);
6435             s->base.is_jmp = DISAS_EOB_NEXT;
6436         } else {
6437             gen_svm_check_intercept(s, SVM_EXIT_READ_CR0 + reg);
6438             gen_helper_read_crN(s->T0, cpu_env, tcg_constant_i32(reg));
6439             gen_op_mov_reg_v(s, ot, rm, s->T0);
6440         }
6441         break;
6442 
6443     case 0x121: /* mov reg, drN */
6444     case 0x123: /* mov drN, reg */
6445         if (check_cpl0(s)) {
6446             modrm = x86_ldub_code(env, s);
6447             /* Ignore the mod bits (assume (modrm&0xc0)==0xc0).
6448              * AMD documentation (24594.pdf) and testing of
6449              * intel 386 and 486 processors all show that the mod bits
6450              * are assumed to be 1's, regardless of actual values.
6451              */
6452             rm = (modrm & 7) | REX_B(s);
6453             reg = ((modrm >> 3) & 7) | REX_R(s);
6454             if (CODE64(s))
6455                 ot = MO_64;
6456             else
6457                 ot = MO_32;
6458             if (reg >= 8) {
6459                 goto illegal_op;
6460             }
6461             if (b & 2) {
6462                 gen_svm_check_intercept(s, SVM_EXIT_WRITE_DR0 + reg);
6463                 gen_op_mov_v_reg(s, ot, s->T0, rm);
6464                 tcg_gen_movi_i32(s->tmp2_i32, reg);
6465                 gen_helper_set_dr(cpu_env, s->tmp2_i32, s->T0);
6466                 s->base.is_jmp = DISAS_EOB_NEXT;
6467             } else {
6468                 gen_svm_check_intercept(s, SVM_EXIT_READ_DR0 + reg);
6469                 tcg_gen_movi_i32(s->tmp2_i32, reg);
6470                 gen_helper_get_dr(s->T0, cpu_env, s->tmp2_i32);
6471                 gen_op_mov_reg_v(s, ot, rm, s->T0);
6472             }
6473         }
6474         break;
6475     case 0x106: /* clts */
6476         if (check_cpl0(s)) {
6477             gen_svm_check_intercept(s, SVM_EXIT_WRITE_CR0);
6478             gen_helper_clts(cpu_env);
6479             /* abort block because static cpu state changed */
6480             s->base.is_jmp = DISAS_EOB_NEXT;
6481         }
6482         break;
6483     /* MMX/3DNow!/SSE/SSE2/SSE3/SSSE3/SSE4 support */
6484     case 0x1c3: /* MOVNTI reg, mem */
6485         if (!(s->cpuid_features & CPUID_SSE2))
6486             goto illegal_op;
6487         ot = mo_64_32(dflag);
6488         modrm = x86_ldub_code(env, s);
6489         mod = (modrm >> 6) & 3;
6490         if (mod == 3)
6491             goto illegal_op;
6492         reg = ((modrm >> 3) & 7) | REX_R(s);
6493         /* generate a generic store */
6494         gen_ldst_modrm(env, s, modrm, ot, reg, 1);
6495         break;
6496     case 0x1ae:
6497         modrm = x86_ldub_code(env, s);
6498         switch (modrm) {
6499         CASE_MODRM_MEM_OP(0): /* fxsave */
6500             if (!(s->cpuid_features & CPUID_FXSR)
6501                 || (prefixes & PREFIX_LOCK)) {
6502                 goto illegal_op;
6503             }
6504             if ((s->flags & HF_EM_MASK) || (s->flags & HF_TS_MASK)) {
6505                 gen_exception(s, EXCP07_PREX);
6506                 break;
6507             }
6508             gen_lea_modrm(env, s, modrm);
6509             gen_helper_fxsave(cpu_env, s->A0);
6510             break;
6511 
6512         CASE_MODRM_MEM_OP(1): /* fxrstor */
6513             if (!(s->cpuid_features & CPUID_FXSR)
6514                 || (prefixes & PREFIX_LOCK)) {
6515                 goto illegal_op;
6516             }
6517             if ((s->flags & HF_EM_MASK) || (s->flags & HF_TS_MASK)) {
6518                 gen_exception(s, EXCP07_PREX);
6519                 break;
6520             }
6521             gen_lea_modrm(env, s, modrm);
6522             gen_helper_fxrstor(cpu_env, s->A0);
6523             break;
6524 
6525         CASE_MODRM_MEM_OP(2): /* ldmxcsr */
6526             if ((s->flags & HF_EM_MASK) || !(s->flags & HF_OSFXSR_MASK)) {
6527                 goto illegal_op;
6528             }
6529             if (s->flags & HF_TS_MASK) {
6530                 gen_exception(s, EXCP07_PREX);
6531                 break;
6532             }
6533             gen_lea_modrm(env, s, modrm);
6534             tcg_gen_qemu_ld_i32(s->tmp2_i32, s->A0, s->mem_index, MO_LEUL);
6535             gen_helper_ldmxcsr(cpu_env, s->tmp2_i32);
6536             break;
6537 
6538         CASE_MODRM_MEM_OP(3): /* stmxcsr */
6539             if ((s->flags & HF_EM_MASK) || !(s->flags & HF_OSFXSR_MASK)) {
6540                 goto illegal_op;
6541             }
6542             if (s->flags & HF_TS_MASK) {
6543                 gen_exception(s, EXCP07_PREX);
6544                 break;
6545             }
6546             gen_helper_update_mxcsr(cpu_env);
6547             gen_lea_modrm(env, s, modrm);
6548             tcg_gen_ld32u_tl(s->T0, cpu_env, offsetof(CPUX86State, mxcsr));
6549             gen_op_st_v(s, MO_32, s->T0, s->A0);
6550             break;
6551 
6552         CASE_MODRM_MEM_OP(4): /* xsave */
6553             if ((s->cpuid_ext_features & CPUID_EXT_XSAVE) == 0
6554                 || (prefixes & (PREFIX_LOCK | PREFIX_DATA
6555                                 | PREFIX_REPZ | PREFIX_REPNZ))) {
6556                 goto illegal_op;
6557             }
6558             gen_lea_modrm(env, s, modrm);
6559             tcg_gen_concat_tl_i64(s->tmp1_i64, cpu_regs[R_EAX],
6560                                   cpu_regs[R_EDX]);
6561             gen_helper_xsave(cpu_env, s->A0, s->tmp1_i64);
6562             break;
6563 
6564         CASE_MODRM_MEM_OP(5): /* xrstor */
6565             if ((s->cpuid_ext_features & CPUID_EXT_XSAVE) == 0
6566                 || (prefixes & (PREFIX_LOCK | PREFIX_DATA
6567                                 | PREFIX_REPZ | PREFIX_REPNZ))) {
6568                 goto illegal_op;
6569             }
6570             gen_lea_modrm(env, s, modrm);
6571             tcg_gen_concat_tl_i64(s->tmp1_i64, cpu_regs[R_EAX],
6572                                   cpu_regs[R_EDX]);
6573             gen_helper_xrstor(cpu_env, s->A0, s->tmp1_i64);
6574             /* XRSTOR is how MPX is enabled, which changes how
6575                we translate.  Thus we need to end the TB.  */
6576             s->base.is_jmp = DISAS_EOB_NEXT;
6577             break;
6578 
6579         CASE_MODRM_MEM_OP(6): /* xsaveopt / clwb */
6580             if (prefixes & PREFIX_LOCK) {
6581                 goto illegal_op;
6582             }
6583             if (prefixes & PREFIX_DATA) {
6584                 /* clwb */
6585                 if (!(s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_CLWB)) {
6586                     goto illegal_op;
6587                 }
6588                 gen_nop_modrm(env, s, modrm);
6589             } else {
6590                 /* xsaveopt */
6591                 if ((s->cpuid_ext_features & CPUID_EXT_XSAVE) == 0
6592                     || (s->cpuid_xsave_features & CPUID_XSAVE_XSAVEOPT) == 0
6593                     || (prefixes & (PREFIX_REPZ | PREFIX_REPNZ))) {
6594                     goto illegal_op;
6595                 }
6596                 gen_lea_modrm(env, s, modrm);
6597                 tcg_gen_concat_tl_i64(s->tmp1_i64, cpu_regs[R_EAX],
6598                                       cpu_regs[R_EDX]);
6599                 gen_helper_xsaveopt(cpu_env, s->A0, s->tmp1_i64);
6600             }
6601             break;
6602 
6603         CASE_MODRM_MEM_OP(7): /* clflush / clflushopt */
6604             if (prefixes & PREFIX_LOCK) {
6605                 goto illegal_op;
6606             }
6607             if (prefixes & PREFIX_DATA) {
6608                 /* clflushopt */
6609                 if (!(s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_CLFLUSHOPT)) {
6610                     goto illegal_op;
6611                 }
6612             } else {
6613                 /* clflush */
6614                 if ((s->prefix & (PREFIX_REPZ | PREFIX_REPNZ))
6615                     || !(s->cpuid_features & CPUID_CLFLUSH)) {
6616                     goto illegal_op;
6617                 }
6618             }
6619             gen_nop_modrm(env, s, modrm);
6620             break;
6621 
6622         case 0xc0 ... 0xc7: /* rdfsbase (f3 0f ae /0) */
6623         case 0xc8 ... 0xcf: /* rdgsbase (f3 0f ae /1) */
6624         case 0xd0 ... 0xd7: /* wrfsbase (f3 0f ae /2) */
6625         case 0xd8 ... 0xdf: /* wrgsbase (f3 0f ae /3) */
6626             if (CODE64(s)
6627                 && (prefixes & PREFIX_REPZ)
6628                 && !(prefixes & PREFIX_LOCK)
6629                 && (s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_FSGSBASE)) {
6630                 TCGv base, treg, src, dst;
6631 
6632                 /* Preserve hflags bits by testing CR4 at runtime.  */
6633                 tcg_gen_movi_i32(s->tmp2_i32, CR4_FSGSBASE_MASK);
6634                 gen_helper_cr4_testbit(cpu_env, s->tmp2_i32);
6635 
6636                 base = cpu_seg_base[modrm & 8 ? R_GS : R_FS];
6637                 treg = cpu_regs[(modrm & 7) | REX_B(s)];
6638 
6639                 if (modrm & 0x10) {
6640                     /* wr*base */
6641                     dst = base, src = treg;
6642                 } else {
6643                     /* rd*base */
6644                     dst = treg, src = base;
6645                 }
6646 
6647                 if (s->dflag == MO_32) {
6648                     tcg_gen_ext32u_tl(dst, src);
6649                 } else {
6650                     tcg_gen_mov_tl(dst, src);
6651                 }
6652                 break;
6653             }
6654             goto unknown_op;
6655 
6656         case 0xf8: /* sfence / pcommit */
6657             if (prefixes & PREFIX_DATA) {
6658                 /* pcommit */
6659                 if (!(s->cpuid_7_0_ebx_features & CPUID_7_0_EBX_PCOMMIT)
6660                     || (prefixes & PREFIX_LOCK)) {
6661                     goto illegal_op;
6662                 }
6663                 break;
6664             }
6665             /* fallthru */
6666         case 0xf9 ... 0xff: /* sfence */
6667             if (!(s->cpuid_features & CPUID_SSE)
6668                 || (prefixes & PREFIX_LOCK)) {
6669                 goto illegal_op;
6670             }
6671             tcg_gen_mb(TCG_MO_ST_ST | TCG_BAR_SC);
6672             break;
6673         case 0xe8 ... 0xef: /* lfence */
6674             if (!(s->cpuid_features & CPUID_SSE)
6675                 || (prefixes & PREFIX_LOCK)) {
6676                 goto illegal_op;
6677             }
6678             tcg_gen_mb(TCG_MO_LD_LD | TCG_BAR_SC);
6679             break;
6680         case 0xf0 ... 0xf7: /* mfence */
6681             if (!(s->cpuid_features & CPUID_SSE2)
6682                 || (prefixes & PREFIX_LOCK)) {
6683                 goto illegal_op;
6684             }
6685             tcg_gen_mb(TCG_MO_ALL | TCG_BAR_SC);
6686             break;
6687 
6688         default:
6689             goto unknown_op;
6690         }
6691         break;
6692 
6693     case 0x10d: /* 3DNow! prefetch(w) */
6694         modrm = x86_ldub_code(env, s);
6695         mod = (modrm >> 6) & 3;
6696         if (mod == 3)
6697             goto illegal_op;
6698         gen_nop_modrm(env, s, modrm);
6699         break;
6700     case 0x1aa: /* rsm */
6701         gen_svm_check_intercept(s, SVM_EXIT_RSM);
6702         if (!(s->flags & HF_SMM_MASK))
6703             goto illegal_op;
6704 #ifdef CONFIG_USER_ONLY
6705         /* we should not be in SMM mode */
6706         g_assert_not_reached();
6707 #else
6708         gen_update_cc_op(s);
6709         gen_update_eip_next(s);
6710         gen_helper_rsm(cpu_env);
6711 #endif /* CONFIG_USER_ONLY */
6712         s->base.is_jmp = DISAS_EOB_ONLY;
6713         break;
6714     case 0x1b8: /* SSE4.2 popcnt */
6715         if ((prefixes & (PREFIX_REPZ | PREFIX_LOCK | PREFIX_REPNZ)) !=
6716              PREFIX_REPZ)
6717             goto illegal_op;
6718         if (!(s->cpuid_ext_features & CPUID_EXT_POPCNT))
6719             goto illegal_op;
6720 
6721         modrm = x86_ldub_code(env, s);
6722         reg = ((modrm >> 3) & 7) | REX_R(s);
6723 
6724         if (s->prefix & PREFIX_DATA) {
6725             ot = MO_16;
6726         } else {
6727             ot = mo_64_32(dflag);
6728         }
6729 
6730         gen_ldst_modrm(env, s, modrm, ot, OR_TMP0, 0);
6731         gen_extu(ot, s->T0);
6732         tcg_gen_mov_tl(cpu_cc_src, s->T0);
6733         tcg_gen_ctpop_tl(s->T0, s->T0);
6734         gen_op_mov_reg_v(s, ot, reg, s->T0);
6735 
6736         set_cc_op(s, CC_OP_POPCNT);
6737         break;
6738     case 0x10e ... 0x117:
6739     case 0x128 ... 0x12f:
6740     case 0x138 ... 0x13a:
6741     case 0x150 ... 0x179:
6742     case 0x17c ... 0x17f:
6743     case 0x1c2:
6744     case 0x1c4 ... 0x1c6:
6745     case 0x1d0 ... 0x1fe:
6746         disas_insn_new(s, cpu, b);
6747         break;
6748     default:
6749         goto unknown_op;
6750     }
6751     return true;
6752  illegal_op:
6753     gen_illegal_opcode(s);
6754     return true;
6755  unknown_op:
6756     gen_unknown_opcode(env, s);
6757     return true;
6758 }
6759 
6760 void tcg_x86_init(void)
6761 {
6762     static const char reg_names[CPU_NB_REGS][4] = {
6763 #ifdef TARGET_X86_64
6764         [R_EAX] = "rax",
6765         [R_EBX] = "rbx",
6766         [R_ECX] = "rcx",
6767         [R_EDX] = "rdx",
6768         [R_ESI] = "rsi",
6769         [R_EDI] = "rdi",
6770         [R_EBP] = "rbp",
6771         [R_ESP] = "rsp",
6772         [8]  = "r8",
6773         [9]  = "r9",
6774         [10] = "r10",
6775         [11] = "r11",
6776         [12] = "r12",
6777         [13] = "r13",
6778         [14] = "r14",
6779         [15] = "r15",
6780 #else
6781         [R_EAX] = "eax",
6782         [R_EBX] = "ebx",
6783         [R_ECX] = "ecx",
6784         [R_EDX] = "edx",
6785         [R_ESI] = "esi",
6786         [R_EDI] = "edi",
6787         [R_EBP] = "ebp",
6788         [R_ESP] = "esp",
6789 #endif
6790     };
6791     static const char eip_name[] = {
6792 #ifdef TARGET_X86_64
6793         "rip"
6794 #else
6795         "eip"
6796 #endif
6797     };
6798     static const char seg_base_names[6][8] = {
6799         [R_CS] = "cs_base",
6800         [R_DS] = "ds_base",
6801         [R_ES] = "es_base",
6802         [R_FS] = "fs_base",
6803         [R_GS] = "gs_base",
6804         [R_SS] = "ss_base",
6805     };
6806     static const char bnd_regl_names[4][8] = {
6807         "bnd0_lb", "bnd1_lb", "bnd2_lb", "bnd3_lb"
6808     };
6809     static const char bnd_regu_names[4][8] = {
6810         "bnd0_ub", "bnd1_ub", "bnd2_ub", "bnd3_ub"
6811     };
6812     int i;
6813 
6814     cpu_cc_op = tcg_global_mem_new_i32(cpu_env,
6815                                        offsetof(CPUX86State, cc_op), "cc_op");
6816     cpu_cc_dst = tcg_global_mem_new(cpu_env, offsetof(CPUX86State, cc_dst),
6817                                     "cc_dst");
6818     cpu_cc_src = tcg_global_mem_new(cpu_env, offsetof(CPUX86State, cc_src),
6819                                     "cc_src");
6820     cpu_cc_src2 = tcg_global_mem_new(cpu_env, offsetof(CPUX86State, cc_src2),
6821                                      "cc_src2");
6822     cpu_eip = tcg_global_mem_new(cpu_env, offsetof(CPUX86State, eip), eip_name);
6823 
6824     for (i = 0; i < CPU_NB_REGS; ++i) {
6825         cpu_regs[i] = tcg_global_mem_new(cpu_env,
6826                                          offsetof(CPUX86State, regs[i]),
6827                                          reg_names[i]);
6828     }
6829 
6830     for (i = 0; i < 6; ++i) {
6831         cpu_seg_base[i]
6832             = tcg_global_mem_new(cpu_env,
6833                                  offsetof(CPUX86State, segs[i].base),
6834                                  seg_base_names[i]);
6835     }
6836 
6837     for (i = 0; i < 4; ++i) {
6838         cpu_bndl[i]
6839             = tcg_global_mem_new_i64(cpu_env,
6840                                      offsetof(CPUX86State, bnd_regs[i].lb),
6841                                      bnd_regl_names[i]);
6842         cpu_bndu[i]
6843             = tcg_global_mem_new_i64(cpu_env,
6844                                      offsetof(CPUX86State, bnd_regs[i].ub),
6845                                      bnd_regu_names[i]);
6846     }
6847 }
6848 
6849 static void i386_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cpu)
6850 {
6851     DisasContext *dc = container_of(dcbase, DisasContext, base);
6852     CPUX86State *env = cpu->env_ptr;
6853     uint32_t flags = dc->base.tb->flags;
6854     uint32_t cflags = tb_cflags(dc->base.tb);
6855     int cpl = (flags >> HF_CPL_SHIFT) & 3;
6856     int iopl = (flags >> IOPL_SHIFT) & 3;
6857 
6858     dc->cs_base = dc->base.tb->cs_base;
6859     dc->pc_save = dc->base.pc_next;
6860     dc->flags = flags;
6861 #ifndef CONFIG_USER_ONLY
6862     dc->cpl = cpl;
6863     dc->iopl = iopl;
6864 #endif
6865 
6866     /* We make some simplifying assumptions; validate they're correct. */
6867     g_assert(PE(dc) == ((flags & HF_PE_MASK) != 0));
6868     g_assert(CPL(dc) == cpl);
6869     g_assert(IOPL(dc) == iopl);
6870     g_assert(VM86(dc) == ((flags & HF_VM_MASK) != 0));
6871     g_assert(CODE32(dc) == ((flags & HF_CS32_MASK) != 0));
6872     g_assert(CODE64(dc) == ((flags & HF_CS64_MASK) != 0));
6873     g_assert(SS32(dc) == ((flags & HF_SS32_MASK) != 0));
6874     g_assert(LMA(dc) == ((flags & HF_LMA_MASK) != 0));
6875     g_assert(ADDSEG(dc) == ((flags & HF_ADDSEG_MASK) != 0));
6876     g_assert(SVME(dc) == ((flags & HF_SVME_MASK) != 0));
6877     g_assert(GUEST(dc) == ((flags & HF_GUEST_MASK) != 0));
6878 
6879     dc->cc_op = CC_OP_DYNAMIC;
6880     dc->cc_op_dirty = false;
6881     dc->popl_esp_hack = 0;
6882     /* select memory access functions */
6883     dc->mem_index = 0;
6884 #ifdef CONFIG_SOFTMMU
6885     dc->mem_index = cpu_mmu_index(env, false);
6886 #endif
6887     dc->cpuid_features = env->features[FEAT_1_EDX];
6888     dc->cpuid_ext_features = env->features[FEAT_1_ECX];
6889     dc->cpuid_ext2_features = env->features[FEAT_8000_0001_EDX];
6890     dc->cpuid_ext3_features = env->features[FEAT_8000_0001_ECX];
6891     dc->cpuid_7_0_ebx_features = env->features[FEAT_7_0_EBX];
6892     dc->cpuid_7_0_ecx_features = env->features[FEAT_7_0_ECX];
6893     dc->cpuid_xsave_features = env->features[FEAT_XSAVE];
6894     dc->jmp_opt = !((cflags & CF_NO_GOTO_TB) ||
6895                     (flags & (HF_TF_MASK | HF_INHIBIT_IRQ_MASK)));
6896     /*
6897      * If jmp_opt, we want to handle each string instruction individually.
6898      * For icount also disable repz optimization so that each iteration
6899      * is accounted separately.
6900      */
6901     dc->repz_opt = !dc->jmp_opt && !(cflags & CF_USE_ICOUNT);
6902 
6903     dc->T0 = tcg_temp_new();
6904     dc->T1 = tcg_temp_new();
6905     dc->A0 = tcg_temp_new();
6906 
6907     dc->tmp0 = tcg_temp_new();
6908     dc->tmp1_i64 = tcg_temp_new_i64();
6909     dc->tmp2_i32 = tcg_temp_new_i32();
6910     dc->tmp3_i32 = tcg_temp_new_i32();
6911     dc->tmp4 = tcg_temp_new();
6912     dc->cc_srcT = tcg_temp_local_new();
6913 }
6914 
6915 static void i386_tr_tb_start(DisasContextBase *db, CPUState *cpu)
6916 {
6917 }
6918 
6919 static void i386_tr_insn_start(DisasContextBase *dcbase, CPUState *cpu)
6920 {
6921     DisasContext *dc = container_of(dcbase, DisasContext, base);
6922     target_ulong pc_arg = dc->base.pc_next;
6923 
6924     dc->prev_insn_end = tcg_last_op();
6925     if (TARGET_TB_PCREL) {
6926         pc_arg -= dc->cs_base;
6927         pc_arg &= ~TARGET_PAGE_MASK;
6928     }
6929     tcg_gen_insn_start(pc_arg, dc->cc_op);
6930 }
6931 
6932 static void i386_tr_translate_insn(DisasContextBase *dcbase, CPUState *cpu)
6933 {
6934     DisasContext *dc = container_of(dcbase, DisasContext, base);
6935 
6936 #ifdef TARGET_VSYSCALL_PAGE
6937     /*
6938      * Detect entry into the vsyscall page and invoke the syscall.
6939      */
6940     if ((dc->base.pc_next & TARGET_PAGE_MASK) == TARGET_VSYSCALL_PAGE) {
6941         gen_exception(dc, EXCP_VSYSCALL);
6942         dc->base.pc_next = dc->pc + 1;
6943         return;
6944     }
6945 #endif
6946 
6947     if (disas_insn(dc, cpu)) {
6948         target_ulong pc_next = dc->pc;
6949         dc->base.pc_next = pc_next;
6950 
6951         if (dc->base.is_jmp == DISAS_NEXT) {
6952             if (dc->flags & (HF_TF_MASK | HF_INHIBIT_IRQ_MASK)) {
6953                 /*
6954                  * If single step mode, we generate only one instruction and
6955                  * generate an exception.
6956                  * If irq were inhibited with HF_INHIBIT_IRQ_MASK, we clear
6957                  * the flag and abort the translation to give the irqs a
6958                  * chance to happen.
6959                  */
6960                 dc->base.is_jmp = DISAS_EOB_NEXT;
6961             } else if (!is_same_page(&dc->base, pc_next)) {
6962                 dc->base.is_jmp = DISAS_TOO_MANY;
6963             }
6964         }
6965     }
6966 }
6967 
6968 static void i386_tr_tb_stop(DisasContextBase *dcbase, CPUState *cpu)
6969 {
6970     DisasContext *dc = container_of(dcbase, DisasContext, base);
6971 
6972     switch (dc->base.is_jmp) {
6973     case DISAS_NORETURN:
6974         break;
6975     case DISAS_TOO_MANY:
6976         gen_update_cc_op(dc);
6977         gen_jmp_rel_csize(dc, 0, 0);
6978         break;
6979     case DISAS_EOB_NEXT:
6980         gen_update_cc_op(dc);
6981         gen_update_eip_cur(dc);
6982         /* fall through */
6983     case DISAS_EOB_ONLY:
6984         gen_eob(dc);
6985         break;
6986     case DISAS_EOB_INHIBIT_IRQ:
6987         gen_update_cc_op(dc);
6988         gen_update_eip_cur(dc);
6989         gen_eob_inhibit_irq(dc, true);
6990         break;
6991     case DISAS_JUMP:
6992         gen_jr(dc);
6993         break;
6994     default:
6995         g_assert_not_reached();
6996     }
6997 }
6998 
6999 static void i386_tr_disas_log(const DisasContextBase *dcbase,
7000                               CPUState *cpu, FILE *logfile)
7001 {
7002     DisasContext *dc = container_of(dcbase, DisasContext, base);
7003 
7004     fprintf(logfile, "IN: %s\n", lookup_symbol(dc->base.pc_first));
7005     target_disas(logfile, cpu, dc->base.pc_first, dc->base.tb->size);
7006 }
7007 
7008 static const TranslatorOps i386_tr_ops = {
7009     .init_disas_context = i386_tr_init_disas_context,
7010     .tb_start           = i386_tr_tb_start,
7011     .insn_start         = i386_tr_insn_start,
7012     .translate_insn     = i386_tr_translate_insn,
7013     .tb_stop            = i386_tr_tb_stop,
7014     .disas_log          = i386_tr_disas_log,
7015 };
7016 
7017 /* generate intermediate code for basic block 'tb'.  */
7018 void gen_intermediate_code(CPUState *cpu, TranslationBlock *tb, int max_insns,
7019                            target_ulong pc, void *host_pc)
7020 {
7021     DisasContext dc;
7022 
7023     translator_loop(cpu, tb, max_insns, pc, host_pc, &i386_tr_ops, &dc.base);
7024 }
7025 
7026 void restore_state_to_opc(CPUX86State *env, TranslationBlock *tb,
7027                           target_ulong *data)
7028 {
7029     int cc_op = data[1];
7030 
7031     if (TARGET_TB_PCREL) {
7032         env->eip = (env->eip & TARGET_PAGE_MASK) | data[0];
7033     } else {
7034         env->eip = data[0] - tb->cs_base;
7035     }
7036     if (cc_op != CC_OP_DYNAMIC) {
7037         env->cc_op = cc_op;
7038     }
7039 }
7040