xref: /openbmc/qemu/target/i386/helper.c (revision 646c5478)
1 /*
2  *  i386 helpers (without register variable usage)
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 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 
20 #include "qemu/osdep.h"
21 #include "cpu.h"
22 #include "exec/exec-all.h"
23 #include "sysemu/kvm.h"
24 #include "kvm_i386.h"
25 #ifndef CONFIG_USER_ONLY
26 #include "sysemu/sysemu.h"
27 #include "monitor/monitor.h"
28 #include "hw/i386/apic_internal.h"
29 #endif
30 
31 static void cpu_x86_version(CPUX86State *env, int *family, int *model)
32 {
33     int cpuver = env->cpuid_version;
34 
35     if (family == NULL || model == NULL) {
36         return;
37     }
38 
39     *family = (cpuver >> 8) & 0x0f;
40     *model = ((cpuver >> 12) & 0xf0) + ((cpuver >> 4) & 0x0f);
41 }
42 
43 /* Broadcast MCA signal for processor version 06H_EH and above */
44 int cpu_x86_support_mca_broadcast(CPUX86State *env)
45 {
46     int family = 0;
47     int model = 0;
48 
49     cpu_x86_version(env, &family, &model);
50     if ((family == 6 && model >= 14) || family > 6) {
51         return 1;
52     }
53 
54     return 0;
55 }
56 
57 /***********************************************************/
58 /* x86 debug */
59 
60 static const char *cc_op_str[CC_OP_NB] = {
61     "DYNAMIC",
62     "EFLAGS",
63 
64     "MULB",
65     "MULW",
66     "MULL",
67     "MULQ",
68 
69     "ADDB",
70     "ADDW",
71     "ADDL",
72     "ADDQ",
73 
74     "ADCB",
75     "ADCW",
76     "ADCL",
77     "ADCQ",
78 
79     "SUBB",
80     "SUBW",
81     "SUBL",
82     "SUBQ",
83 
84     "SBBB",
85     "SBBW",
86     "SBBL",
87     "SBBQ",
88 
89     "LOGICB",
90     "LOGICW",
91     "LOGICL",
92     "LOGICQ",
93 
94     "INCB",
95     "INCW",
96     "INCL",
97     "INCQ",
98 
99     "DECB",
100     "DECW",
101     "DECL",
102     "DECQ",
103 
104     "SHLB",
105     "SHLW",
106     "SHLL",
107     "SHLQ",
108 
109     "SARB",
110     "SARW",
111     "SARL",
112     "SARQ",
113 
114     "BMILGB",
115     "BMILGW",
116     "BMILGL",
117     "BMILGQ",
118 
119     "ADCX",
120     "ADOX",
121     "ADCOX",
122 
123     "CLR",
124 };
125 
126 static void
127 cpu_x86_dump_seg_cache(CPUX86State *env, FILE *f, fprintf_function cpu_fprintf,
128                        const char *name, struct SegmentCache *sc)
129 {
130 #ifdef TARGET_X86_64
131     if (env->hflags & HF_CS64_MASK) {
132         cpu_fprintf(f, "%-3s=%04x %016" PRIx64 " %08x %08x", name,
133                     sc->selector, sc->base, sc->limit, sc->flags & 0x00ffff00);
134     } else
135 #endif
136     {
137         cpu_fprintf(f, "%-3s=%04x %08x %08x %08x", name, sc->selector,
138                     (uint32_t)sc->base, sc->limit, sc->flags & 0x00ffff00);
139     }
140 
141     if (!(env->hflags & HF_PE_MASK) || !(sc->flags & DESC_P_MASK))
142         goto done;
143 
144     cpu_fprintf(f, " DPL=%d ", (sc->flags & DESC_DPL_MASK) >> DESC_DPL_SHIFT);
145     if (sc->flags & DESC_S_MASK) {
146         if (sc->flags & DESC_CS_MASK) {
147             cpu_fprintf(f, (sc->flags & DESC_L_MASK) ? "CS64" :
148                            ((sc->flags & DESC_B_MASK) ? "CS32" : "CS16"));
149             cpu_fprintf(f, " [%c%c", (sc->flags & DESC_C_MASK) ? 'C' : '-',
150                         (sc->flags & DESC_R_MASK) ? 'R' : '-');
151         } else {
152             cpu_fprintf(f,
153                         (sc->flags & DESC_B_MASK || env->hflags & HF_LMA_MASK)
154                         ? "DS  " : "DS16");
155             cpu_fprintf(f, " [%c%c", (sc->flags & DESC_E_MASK) ? 'E' : '-',
156                         (sc->flags & DESC_W_MASK) ? 'W' : '-');
157         }
158         cpu_fprintf(f, "%c]", (sc->flags & DESC_A_MASK) ? 'A' : '-');
159     } else {
160         static const char *sys_type_name[2][16] = {
161             { /* 32 bit mode */
162                 "Reserved", "TSS16-avl", "LDT", "TSS16-busy",
163                 "CallGate16", "TaskGate", "IntGate16", "TrapGate16",
164                 "Reserved", "TSS32-avl", "Reserved", "TSS32-busy",
165                 "CallGate32", "Reserved", "IntGate32", "TrapGate32"
166             },
167             { /* 64 bit mode */
168                 "<hiword>", "Reserved", "LDT", "Reserved", "Reserved",
169                 "Reserved", "Reserved", "Reserved", "Reserved",
170                 "TSS64-avl", "Reserved", "TSS64-busy", "CallGate64",
171                 "Reserved", "IntGate64", "TrapGate64"
172             }
173         };
174         cpu_fprintf(f, "%s",
175                     sys_type_name[(env->hflags & HF_LMA_MASK) ? 1 : 0]
176                                  [(sc->flags & DESC_TYPE_MASK)
177                                   >> DESC_TYPE_SHIFT]);
178     }
179 done:
180     cpu_fprintf(f, "\n");
181 }
182 
183 #ifndef CONFIG_USER_ONLY
184 
185 /* ARRAY_SIZE check is not required because
186  * DeliveryMode(dm) has a size of 3 bit.
187  */
188 static inline const char *dm2str(uint32_t dm)
189 {
190     static const char *str[] = {
191         "Fixed",
192         "...",
193         "SMI",
194         "...",
195         "NMI",
196         "INIT",
197         "...",
198         "ExtINT"
199     };
200     return str[dm];
201 }
202 
203 static void dump_apic_lvt(FILE *f, fprintf_function cpu_fprintf,
204                           const char *name, uint32_t lvt, bool is_timer)
205 {
206     uint32_t dm = (lvt & APIC_LVT_DELIV_MOD) >> APIC_LVT_DELIV_MOD_SHIFT;
207     cpu_fprintf(f,
208                 "%s\t 0x%08x %s %-5s %-6s %-7s %-12s %-6s",
209                 name, lvt,
210                 lvt & APIC_LVT_INT_POLARITY ? "active-lo" : "active-hi",
211                 lvt & APIC_LVT_LEVEL_TRIGGER ? "level" : "edge",
212                 lvt & APIC_LVT_MASKED ? "masked" : "",
213                 lvt & APIC_LVT_DELIV_STS ? "pending" : "",
214                 !is_timer ?
215                     "" : lvt & APIC_LVT_TIMER_PERIODIC ?
216                             "periodic" : lvt & APIC_LVT_TIMER_TSCDEADLINE ?
217                                             "tsc-deadline" : "one-shot",
218                 dm2str(dm));
219     if (dm != APIC_DM_NMI) {
220         cpu_fprintf(f, " (vec %u)\n", lvt & APIC_VECTOR_MASK);
221     } else {
222         cpu_fprintf(f, "\n");
223     }
224 }
225 
226 /* ARRAY_SIZE check is not required because
227  * destination shorthand has a size of 2 bit.
228  */
229 static inline const char *shorthand2str(uint32_t shorthand)
230 {
231     const char *str[] = {
232         "no-shorthand", "self", "all-self", "all"
233     };
234     return str[shorthand];
235 }
236 
237 static inline uint8_t divider_conf(uint32_t divide_conf)
238 {
239     uint8_t divide_val = ((divide_conf & 0x8) >> 1) | (divide_conf & 0x3);
240 
241     return divide_val == 7 ? 1 : 2 << divide_val;
242 }
243 
244 static inline void mask2str(char *str, uint32_t val, uint8_t size)
245 {
246     while (size--) {
247         *str++ = (val >> size) & 1 ? '1' : '0';
248     }
249     *str = 0;
250 }
251 
252 #define MAX_LOGICAL_APIC_ID_MASK_SIZE 16
253 
254 static void dump_apic_icr(FILE *f, fprintf_function cpu_fprintf,
255                           APICCommonState *s, CPUX86State *env)
256 {
257     uint32_t icr = s->icr[0], icr2 = s->icr[1];
258     uint8_t dest_shorthand = \
259         (icr & APIC_ICR_DEST_SHORT) >> APIC_ICR_DEST_SHORT_SHIFT;
260     bool logical_mod = icr & APIC_ICR_DEST_MOD;
261     char apic_id_str[MAX_LOGICAL_APIC_ID_MASK_SIZE + 1];
262     uint32_t dest_field;
263     bool x2apic;
264 
265     cpu_fprintf(f, "ICR\t 0x%08x %s %s %s %s\n",
266                 icr,
267                 logical_mod ? "logical" : "physical",
268                 icr & APIC_ICR_TRIGGER_MOD ? "level" : "edge",
269                 icr & APIC_ICR_LEVEL ? "assert" : "de-assert",
270                 shorthand2str(dest_shorthand));
271 
272     cpu_fprintf(f, "ICR2\t 0x%08x", icr2);
273     if (dest_shorthand != 0) {
274         cpu_fprintf(f, "\n");
275         return;
276     }
277     x2apic = env->features[FEAT_1_ECX] & CPUID_EXT_X2APIC;
278     dest_field = x2apic ? icr2 : icr2 >> APIC_ICR_DEST_SHIFT;
279 
280     if (!logical_mod) {
281         if (x2apic) {
282             cpu_fprintf(f, " cpu %u (X2APIC ID)\n", dest_field);
283         } else {
284             cpu_fprintf(f, " cpu %u (APIC ID)\n",
285                         dest_field & APIC_LOGDEST_XAPIC_ID);
286         }
287         return;
288     }
289 
290     if (s->dest_mode == 0xf) { /* flat mode */
291         mask2str(apic_id_str, icr2 >> APIC_ICR_DEST_SHIFT, 8);
292         cpu_fprintf(f, " mask %s (APIC ID)\n", apic_id_str);
293     } else if (s->dest_mode == 0) { /* cluster mode */
294         if (x2apic) {
295             mask2str(apic_id_str, dest_field & APIC_LOGDEST_X2APIC_ID, 16);
296             cpu_fprintf(f, " cluster %u mask %s (X2APIC ID)\n",
297                         dest_field >> APIC_LOGDEST_X2APIC_SHIFT, apic_id_str);
298         } else {
299             mask2str(apic_id_str, dest_field & APIC_LOGDEST_XAPIC_ID, 4);
300             cpu_fprintf(f, " cluster %u mask %s (APIC ID)\n",
301                         dest_field >> APIC_LOGDEST_XAPIC_SHIFT, apic_id_str);
302         }
303     }
304 }
305 
306 static void dump_apic_interrupt(FILE *f, fprintf_function cpu_fprintf,
307                                 const char *name, uint32_t *ireg_tab,
308                                 uint32_t *tmr_tab)
309 {
310     int i, empty = true;
311 
312     cpu_fprintf(f, "%s\t ", name);
313     for (i = 0; i < 256; i++) {
314         if (apic_get_bit(ireg_tab, i)) {
315             cpu_fprintf(f, "%u%s ", i,
316                         apic_get_bit(tmr_tab, i) ? "(level)" : "");
317             empty = false;
318         }
319     }
320     cpu_fprintf(f, "%s\n", empty ? "(none)" : "");
321 }
322 
323 void x86_cpu_dump_local_apic_state(CPUState *cs, FILE *f,
324                                    fprintf_function cpu_fprintf, int flags)
325 {
326     X86CPU *cpu = X86_CPU(cs);
327     APICCommonState *s = APIC_COMMON(cpu->apic_state);
328     uint32_t *lvt = s->lvt;
329 
330     cpu_fprintf(f, "dumping local APIC state for CPU %-2u\n\n",
331                 CPU(cpu)->cpu_index);
332     dump_apic_lvt(f, cpu_fprintf, "LVT0", lvt[APIC_LVT_LINT0], false);
333     dump_apic_lvt(f, cpu_fprintf, "LVT1", lvt[APIC_LVT_LINT1], false);
334     dump_apic_lvt(f, cpu_fprintf, "LVTPC", lvt[APIC_LVT_PERFORM], false);
335     dump_apic_lvt(f, cpu_fprintf, "LVTERR", lvt[APIC_LVT_ERROR], false);
336     dump_apic_lvt(f, cpu_fprintf, "LVTTHMR", lvt[APIC_LVT_THERMAL], false);
337     dump_apic_lvt(f, cpu_fprintf, "LVTT", lvt[APIC_LVT_TIMER], true);
338 
339     cpu_fprintf(f, "Timer\t DCR=0x%x (divide by %u) initial_count = %u\n",
340                 s->divide_conf & APIC_DCR_MASK,
341                 divider_conf(s->divide_conf),
342                 s->initial_count);
343 
344     cpu_fprintf(f, "SPIV\t 0x%08x APIC %s, focus=%s, spurious vec %u\n",
345                 s->spurious_vec,
346                 s->spurious_vec & APIC_SPURIO_ENABLED ? "enabled" : "disabled",
347                 s->spurious_vec & APIC_SPURIO_FOCUS ? "on" : "off",
348                 s->spurious_vec & APIC_VECTOR_MASK);
349 
350     dump_apic_icr(f, cpu_fprintf, s, &cpu->env);
351 
352     cpu_fprintf(f, "ESR\t 0x%08x\n", s->esr);
353 
354     dump_apic_interrupt(f, cpu_fprintf, "ISR", s->isr, s->tmr);
355     dump_apic_interrupt(f, cpu_fprintf, "IRR", s->irr, s->tmr);
356 
357     cpu_fprintf(f, "\nAPR 0x%02x TPR 0x%02x DFR 0x%02x LDR 0x%02x",
358                 s->arb_id, s->tpr, s->dest_mode, s->log_dest);
359     if (s->dest_mode == 0) {
360         cpu_fprintf(f, "(cluster %u: id %u)",
361                     s->log_dest >> APIC_LOGDEST_XAPIC_SHIFT,
362                     s->log_dest & APIC_LOGDEST_XAPIC_ID);
363     }
364     cpu_fprintf(f, " PPR 0x%02x\n", apic_get_ppr(s));
365 }
366 #else
367 void x86_cpu_dump_local_apic_state(CPUState *cs, FILE *f,
368                                    fprintf_function cpu_fprintf, int flags)
369 {
370 }
371 #endif /* !CONFIG_USER_ONLY */
372 
373 #define DUMP_CODE_BYTES_TOTAL    50
374 #define DUMP_CODE_BYTES_BACKWARD 20
375 
376 void x86_cpu_dump_state(CPUState *cs, FILE *f, fprintf_function cpu_fprintf,
377                         int flags)
378 {
379     X86CPU *cpu = X86_CPU(cs);
380     CPUX86State *env = &cpu->env;
381     int eflags, i, nb;
382     char cc_op_name[32];
383     static const char *seg_name[6] = { "ES", "CS", "SS", "DS", "FS", "GS" };
384 
385     eflags = cpu_compute_eflags(env);
386 #ifdef TARGET_X86_64
387     if (env->hflags & HF_CS64_MASK) {
388         cpu_fprintf(f,
389                     "RAX=%016" PRIx64 " RBX=%016" PRIx64 " RCX=%016" PRIx64 " RDX=%016" PRIx64 "\n"
390                     "RSI=%016" PRIx64 " RDI=%016" PRIx64 " RBP=%016" PRIx64 " RSP=%016" PRIx64 "\n"
391                     "R8 =%016" PRIx64 " R9 =%016" PRIx64 " R10=%016" PRIx64 " R11=%016" PRIx64 "\n"
392                     "R12=%016" PRIx64 " R13=%016" PRIx64 " R14=%016" PRIx64 " R15=%016" PRIx64 "\n"
393                     "RIP=%016" PRIx64 " RFL=%08x [%c%c%c%c%c%c%c] CPL=%d II=%d A20=%d SMM=%d HLT=%d\n",
394                     env->regs[R_EAX],
395                     env->regs[R_EBX],
396                     env->regs[R_ECX],
397                     env->regs[R_EDX],
398                     env->regs[R_ESI],
399                     env->regs[R_EDI],
400                     env->regs[R_EBP],
401                     env->regs[R_ESP],
402                     env->regs[8],
403                     env->regs[9],
404                     env->regs[10],
405                     env->regs[11],
406                     env->regs[12],
407                     env->regs[13],
408                     env->regs[14],
409                     env->regs[15],
410                     env->eip, eflags,
411                     eflags & DF_MASK ? 'D' : '-',
412                     eflags & CC_O ? 'O' : '-',
413                     eflags & CC_S ? 'S' : '-',
414                     eflags & CC_Z ? 'Z' : '-',
415                     eflags & CC_A ? 'A' : '-',
416                     eflags & CC_P ? 'P' : '-',
417                     eflags & CC_C ? 'C' : '-',
418                     env->hflags & HF_CPL_MASK,
419                     (env->hflags >> HF_INHIBIT_IRQ_SHIFT) & 1,
420                     (env->a20_mask >> 20) & 1,
421                     (env->hflags >> HF_SMM_SHIFT) & 1,
422                     cs->halted);
423     } else
424 #endif
425     {
426         cpu_fprintf(f, "EAX=%08x EBX=%08x ECX=%08x EDX=%08x\n"
427                     "ESI=%08x EDI=%08x EBP=%08x ESP=%08x\n"
428                     "EIP=%08x EFL=%08x [%c%c%c%c%c%c%c] CPL=%d II=%d A20=%d SMM=%d HLT=%d\n",
429                     (uint32_t)env->regs[R_EAX],
430                     (uint32_t)env->regs[R_EBX],
431                     (uint32_t)env->regs[R_ECX],
432                     (uint32_t)env->regs[R_EDX],
433                     (uint32_t)env->regs[R_ESI],
434                     (uint32_t)env->regs[R_EDI],
435                     (uint32_t)env->regs[R_EBP],
436                     (uint32_t)env->regs[R_ESP],
437                     (uint32_t)env->eip, eflags,
438                     eflags & DF_MASK ? 'D' : '-',
439                     eflags & CC_O ? 'O' : '-',
440                     eflags & CC_S ? 'S' : '-',
441                     eflags & CC_Z ? 'Z' : '-',
442                     eflags & CC_A ? 'A' : '-',
443                     eflags & CC_P ? 'P' : '-',
444                     eflags & CC_C ? 'C' : '-',
445                     env->hflags & HF_CPL_MASK,
446                     (env->hflags >> HF_INHIBIT_IRQ_SHIFT) & 1,
447                     (env->a20_mask >> 20) & 1,
448                     (env->hflags >> HF_SMM_SHIFT) & 1,
449                     cs->halted);
450     }
451 
452     for(i = 0; i < 6; i++) {
453         cpu_x86_dump_seg_cache(env, f, cpu_fprintf, seg_name[i],
454                                &env->segs[i]);
455     }
456     cpu_x86_dump_seg_cache(env, f, cpu_fprintf, "LDT", &env->ldt);
457     cpu_x86_dump_seg_cache(env, f, cpu_fprintf, "TR", &env->tr);
458 
459 #ifdef TARGET_X86_64
460     if (env->hflags & HF_LMA_MASK) {
461         cpu_fprintf(f, "GDT=     %016" PRIx64 " %08x\n",
462                     env->gdt.base, env->gdt.limit);
463         cpu_fprintf(f, "IDT=     %016" PRIx64 " %08x\n",
464                     env->idt.base, env->idt.limit);
465         cpu_fprintf(f, "CR0=%08x CR2=%016" PRIx64 " CR3=%016" PRIx64 " CR4=%08x\n",
466                     (uint32_t)env->cr[0],
467                     env->cr[2],
468                     env->cr[3],
469                     (uint32_t)env->cr[4]);
470         for(i = 0; i < 4; i++)
471             cpu_fprintf(f, "DR%d=%016" PRIx64 " ", i, env->dr[i]);
472         cpu_fprintf(f, "\nDR6=%016" PRIx64 " DR7=%016" PRIx64 "\n",
473                     env->dr[6], env->dr[7]);
474     } else
475 #endif
476     {
477         cpu_fprintf(f, "GDT=     %08x %08x\n",
478                     (uint32_t)env->gdt.base, env->gdt.limit);
479         cpu_fprintf(f, "IDT=     %08x %08x\n",
480                     (uint32_t)env->idt.base, env->idt.limit);
481         cpu_fprintf(f, "CR0=%08x CR2=%08x CR3=%08x CR4=%08x\n",
482                     (uint32_t)env->cr[0],
483                     (uint32_t)env->cr[2],
484                     (uint32_t)env->cr[3],
485                     (uint32_t)env->cr[4]);
486         for(i = 0; i < 4; i++) {
487             cpu_fprintf(f, "DR%d=" TARGET_FMT_lx " ", i, env->dr[i]);
488         }
489         cpu_fprintf(f, "\nDR6=" TARGET_FMT_lx " DR7=" TARGET_FMT_lx "\n",
490                     env->dr[6], env->dr[7]);
491     }
492     if (flags & CPU_DUMP_CCOP) {
493         if ((unsigned)env->cc_op < CC_OP_NB)
494             snprintf(cc_op_name, sizeof(cc_op_name), "%s", cc_op_str[env->cc_op]);
495         else
496             snprintf(cc_op_name, sizeof(cc_op_name), "[%d]", env->cc_op);
497 #ifdef TARGET_X86_64
498         if (env->hflags & HF_CS64_MASK) {
499             cpu_fprintf(f, "CCS=%016" PRIx64 " CCD=%016" PRIx64 " CCO=%-8s\n",
500                         env->cc_src, env->cc_dst,
501                         cc_op_name);
502         } else
503 #endif
504         {
505             cpu_fprintf(f, "CCS=%08x CCD=%08x CCO=%-8s\n",
506                         (uint32_t)env->cc_src, (uint32_t)env->cc_dst,
507                         cc_op_name);
508         }
509     }
510     cpu_fprintf(f, "EFER=%016" PRIx64 "\n", env->efer);
511     if (flags & CPU_DUMP_FPU) {
512         int fptag;
513         fptag = 0;
514         for(i = 0; i < 8; i++) {
515             fptag |= ((!env->fptags[i]) << i);
516         }
517         cpu_fprintf(f, "FCW=%04x FSW=%04x [ST=%d] FTW=%02x MXCSR=%08x\n",
518                     env->fpuc,
519                     (env->fpus & ~0x3800) | (env->fpstt & 0x7) << 11,
520                     env->fpstt,
521                     fptag,
522                     env->mxcsr);
523         for(i=0;i<8;i++) {
524             CPU_LDoubleU u;
525             u.d = env->fpregs[i].d;
526             cpu_fprintf(f, "FPR%d=%016" PRIx64 " %04x",
527                         i, u.l.lower, u.l.upper);
528             if ((i & 1) == 1)
529                 cpu_fprintf(f, "\n");
530             else
531                 cpu_fprintf(f, " ");
532         }
533         if (env->hflags & HF_CS64_MASK)
534             nb = 16;
535         else
536             nb = 8;
537         for(i=0;i<nb;i++) {
538             cpu_fprintf(f, "XMM%02d=%08x%08x%08x%08x",
539                         i,
540                         env->xmm_regs[i].ZMM_L(3),
541                         env->xmm_regs[i].ZMM_L(2),
542                         env->xmm_regs[i].ZMM_L(1),
543                         env->xmm_regs[i].ZMM_L(0));
544             if ((i & 1) == 1)
545                 cpu_fprintf(f, "\n");
546             else
547                 cpu_fprintf(f, " ");
548         }
549     }
550     if (flags & CPU_DUMP_CODE) {
551         target_ulong base = env->segs[R_CS].base + env->eip;
552         target_ulong offs = MIN(env->eip, DUMP_CODE_BYTES_BACKWARD);
553         uint8_t code;
554         char codestr[3];
555 
556         cpu_fprintf(f, "Code=");
557         for (i = 0; i < DUMP_CODE_BYTES_TOTAL; i++) {
558             if (cpu_memory_rw_debug(cs, base - offs + i, &code, 1, 0) == 0) {
559                 snprintf(codestr, sizeof(codestr), "%02x", code);
560             } else {
561                 snprintf(codestr, sizeof(codestr), "??");
562             }
563             cpu_fprintf(f, "%s%s%s%s", i > 0 ? " " : "",
564                         i == offs ? "<" : "", codestr, i == offs ? ">" : "");
565         }
566         cpu_fprintf(f, "\n");
567     }
568 }
569 
570 /***********************************************************/
571 /* x86 mmu */
572 /* XXX: add PGE support */
573 
574 void x86_cpu_set_a20(X86CPU *cpu, int a20_state)
575 {
576     CPUX86State *env = &cpu->env;
577 
578     a20_state = (a20_state != 0);
579     if (a20_state != ((env->a20_mask >> 20) & 1)) {
580         CPUState *cs = CPU(cpu);
581 
582         qemu_log_mask(CPU_LOG_MMU, "A20 update: a20=%d\n", a20_state);
583         /* if the cpu is currently executing code, we must unlink it and
584            all the potentially executing TB */
585         cpu_interrupt(cs, CPU_INTERRUPT_EXITTB);
586 
587         /* when a20 is changed, all the MMU mappings are invalid, so
588            we must flush everything */
589         tlb_flush(cs, 1);
590         env->a20_mask = ~(1 << 20) | (a20_state << 20);
591     }
592 }
593 
594 void cpu_x86_update_cr0(CPUX86State *env, uint32_t new_cr0)
595 {
596     X86CPU *cpu = x86_env_get_cpu(env);
597     int pe_state;
598 
599     qemu_log_mask(CPU_LOG_MMU, "CR0 update: CR0=0x%08x\n", new_cr0);
600     if ((new_cr0 & (CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK)) !=
601         (env->cr[0] & (CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK))) {
602         tlb_flush(CPU(cpu), 1);
603     }
604 
605 #ifdef TARGET_X86_64
606     if (!(env->cr[0] & CR0_PG_MASK) && (new_cr0 & CR0_PG_MASK) &&
607         (env->efer & MSR_EFER_LME)) {
608         /* enter in long mode */
609         /* XXX: generate an exception */
610         if (!(env->cr[4] & CR4_PAE_MASK))
611             return;
612         env->efer |= MSR_EFER_LMA;
613         env->hflags |= HF_LMA_MASK;
614     } else if ((env->cr[0] & CR0_PG_MASK) && !(new_cr0 & CR0_PG_MASK) &&
615                (env->efer & MSR_EFER_LMA)) {
616         /* exit long mode */
617         env->efer &= ~MSR_EFER_LMA;
618         env->hflags &= ~(HF_LMA_MASK | HF_CS64_MASK);
619         env->eip &= 0xffffffff;
620     }
621 #endif
622     env->cr[0] = new_cr0 | CR0_ET_MASK;
623 
624     /* update PE flag in hidden flags */
625     pe_state = (env->cr[0] & CR0_PE_MASK);
626     env->hflags = (env->hflags & ~HF_PE_MASK) | (pe_state << HF_PE_SHIFT);
627     /* ensure that ADDSEG is always set in real mode */
628     env->hflags |= ((pe_state ^ 1) << HF_ADDSEG_SHIFT);
629     /* update FPU flags */
630     env->hflags = (env->hflags & ~(HF_MP_MASK | HF_EM_MASK | HF_TS_MASK)) |
631         ((new_cr0 << (HF_MP_SHIFT - 1)) & (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK));
632 }
633 
634 /* XXX: in legacy PAE mode, generate a GPF if reserved bits are set in
635    the PDPT */
636 void cpu_x86_update_cr3(CPUX86State *env, target_ulong new_cr3)
637 {
638     X86CPU *cpu = x86_env_get_cpu(env);
639 
640     env->cr[3] = new_cr3;
641     if (env->cr[0] & CR0_PG_MASK) {
642         qemu_log_mask(CPU_LOG_MMU,
643                         "CR3 update: CR3=" TARGET_FMT_lx "\n", new_cr3);
644         tlb_flush(CPU(cpu), 0);
645     }
646 }
647 
648 void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4)
649 {
650     X86CPU *cpu = x86_env_get_cpu(env);
651     uint32_t hflags;
652 
653 #if defined(DEBUG_MMU)
654     printf("CR4 update: %08x -> %08x\n", (uint32_t)env->cr[4], new_cr4);
655 #endif
656     if ((new_cr4 ^ env->cr[4]) &
657         (CR4_PGE_MASK | CR4_PAE_MASK | CR4_PSE_MASK |
658          CR4_SMEP_MASK | CR4_SMAP_MASK | CR4_LA57_MASK)) {
659         tlb_flush(CPU(cpu), 1);
660     }
661 
662     /* Clear bits we're going to recompute.  */
663     hflags = env->hflags & ~(HF_OSFXSR_MASK | HF_SMAP_MASK);
664 
665     /* SSE handling */
666     if (!(env->features[FEAT_1_EDX] & CPUID_SSE)) {
667         new_cr4 &= ~CR4_OSFXSR_MASK;
668     }
669     if (new_cr4 & CR4_OSFXSR_MASK) {
670         hflags |= HF_OSFXSR_MASK;
671     }
672 
673     if (!(env->features[FEAT_7_0_EBX] & CPUID_7_0_EBX_SMAP)) {
674         new_cr4 &= ~CR4_SMAP_MASK;
675     }
676     if (new_cr4 & CR4_SMAP_MASK) {
677         hflags |= HF_SMAP_MASK;
678     }
679 
680     if (!(env->features[FEAT_7_0_ECX] & CPUID_7_0_ECX_PKU)) {
681         new_cr4 &= ~CR4_PKE_MASK;
682     }
683 
684     env->cr[4] = new_cr4;
685     env->hflags = hflags;
686 
687     cpu_sync_bndcs_hflags(env);
688 }
689 
690 #if defined(CONFIG_USER_ONLY)
691 
692 int x86_cpu_handle_mmu_fault(CPUState *cs, vaddr addr,
693                              int is_write, int mmu_idx)
694 {
695     X86CPU *cpu = X86_CPU(cs);
696     CPUX86State *env = &cpu->env;
697 
698     /* user mode only emulation */
699     is_write &= 1;
700     env->cr[2] = addr;
701     env->error_code = (is_write << PG_ERROR_W_BIT);
702     env->error_code |= PG_ERROR_U_MASK;
703     cs->exception_index = EXCP0E_PAGE;
704     env->exception_is_int = 0;
705     env->exception_next_eip = -1;
706     return 1;
707 }
708 
709 #else
710 
711 /* return value:
712  * -1 = cannot handle fault
713  * 0  = nothing more to do
714  * 1  = generate PF fault
715  */
716 int x86_cpu_handle_mmu_fault(CPUState *cs, vaddr addr,
717                              int is_write1, int mmu_idx)
718 {
719     X86CPU *cpu = X86_CPU(cs);
720     CPUX86State *env = &cpu->env;
721     uint64_t ptep, pte;
722     target_ulong pde_addr, pte_addr;
723     int error_code = 0;
724     int is_dirty, prot, page_size, is_write, is_user;
725     hwaddr paddr;
726     uint64_t rsvd_mask = PG_HI_RSVD_MASK;
727     uint32_t page_offset;
728     target_ulong vaddr;
729 
730     is_user = mmu_idx == MMU_USER_IDX;
731 #if defined(DEBUG_MMU)
732     printf("MMU fault: addr=%" VADDR_PRIx " w=%d u=%d eip=" TARGET_FMT_lx "\n",
733            addr, is_write1, is_user, env->eip);
734 #endif
735     is_write = is_write1 & 1;
736 
737     if (!(env->cr[0] & CR0_PG_MASK)) {
738         pte = addr;
739 #ifdef TARGET_X86_64
740         if (!(env->hflags & HF_LMA_MASK)) {
741             /* Without long mode we can only address 32bits in real mode */
742             pte = (uint32_t)pte;
743         }
744 #endif
745         prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
746         page_size = 4096;
747         goto do_mapping;
748     }
749 
750     if (!(env->efer & MSR_EFER_NXE)) {
751         rsvd_mask |= PG_NX_MASK;
752     }
753 
754     if (env->cr[4] & CR4_PAE_MASK) {
755         uint64_t pde, pdpe;
756         target_ulong pdpe_addr;
757 
758 #ifdef TARGET_X86_64
759         if (env->hflags & HF_LMA_MASK) {
760             bool la57 = env->cr[4] & CR4_LA57_MASK;
761             uint64_t pml5e_addr, pml5e;
762             uint64_t pml4e_addr, pml4e;
763             int32_t sext;
764 
765             /* test virtual address sign extension */
766             sext = la57 ? (int64_t)addr >> 56 : (int64_t)addr >> 47;
767             if (sext != 0 && sext != -1) {
768                 env->error_code = 0;
769                 cs->exception_index = EXCP0D_GPF;
770                 return 1;
771             }
772 
773             if (la57) {
774                 pml5e_addr = ((env->cr[3] & ~0xfff) +
775                         (((addr >> 48) & 0x1ff) << 3)) & env->a20_mask;
776                 pml5e = x86_ldq_phys(cs, pml5e_addr);
777                 if (!(pml5e & PG_PRESENT_MASK)) {
778                     goto do_fault;
779                 }
780                 if (pml5e & (rsvd_mask | PG_PSE_MASK)) {
781                     goto do_fault_rsvd;
782                 }
783                 if (!(pml5e & PG_ACCESSED_MASK)) {
784                     pml5e |= PG_ACCESSED_MASK;
785                     x86_stl_phys_notdirty(cs, pml5e_addr, pml5e);
786                 }
787                 ptep = pml5e ^ PG_NX_MASK;
788             } else {
789                 pml5e = env->cr[3];
790                 ptep = PG_NX_MASK | PG_USER_MASK | PG_RW_MASK;
791             }
792 
793             pml4e_addr = ((pml5e & PG_ADDRESS_MASK) +
794                     (((addr >> 39) & 0x1ff) << 3)) & env->a20_mask;
795             pml4e = x86_ldq_phys(cs, pml4e_addr);
796             if (!(pml4e & PG_PRESENT_MASK)) {
797                 goto do_fault;
798             }
799             if (pml4e & (rsvd_mask | PG_PSE_MASK)) {
800                 goto do_fault_rsvd;
801             }
802             if (!(pml4e & PG_ACCESSED_MASK)) {
803                 pml4e |= PG_ACCESSED_MASK;
804                 x86_stl_phys_notdirty(cs, pml4e_addr, pml4e);
805             }
806             ptep &= pml4e ^ PG_NX_MASK;
807             pdpe_addr = ((pml4e & PG_ADDRESS_MASK) + (((addr >> 30) & 0x1ff) << 3)) &
808                 env->a20_mask;
809             pdpe = x86_ldq_phys(cs, pdpe_addr);
810             if (!(pdpe & PG_PRESENT_MASK)) {
811                 goto do_fault;
812             }
813             if (pdpe & rsvd_mask) {
814                 goto do_fault_rsvd;
815             }
816             ptep &= pdpe ^ PG_NX_MASK;
817             if (!(pdpe & PG_ACCESSED_MASK)) {
818                 pdpe |= PG_ACCESSED_MASK;
819                 x86_stl_phys_notdirty(cs, pdpe_addr, pdpe);
820             }
821             if (pdpe & PG_PSE_MASK) {
822                 /* 1 GB page */
823                 page_size = 1024 * 1024 * 1024;
824                 pte_addr = pdpe_addr;
825                 pte = pdpe;
826                 goto do_check_protect;
827             }
828         } else
829 #endif
830         {
831             /* XXX: load them when cr3 is loaded ? */
832             pdpe_addr = ((env->cr[3] & ~0x1f) + ((addr >> 27) & 0x18)) &
833                 env->a20_mask;
834             pdpe = x86_ldq_phys(cs, pdpe_addr);
835             if (!(pdpe & PG_PRESENT_MASK)) {
836                 goto do_fault;
837             }
838             rsvd_mask |= PG_HI_USER_MASK;
839             if (pdpe & (rsvd_mask | PG_NX_MASK)) {
840                 goto do_fault_rsvd;
841             }
842             ptep = PG_NX_MASK | PG_USER_MASK | PG_RW_MASK;
843         }
844 
845         pde_addr = ((pdpe & PG_ADDRESS_MASK) + (((addr >> 21) & 0x1ff) << 3)) &
846             env->a20_mask;
847         pde = x86_ldq_phys(cs, pde_addr);
848         if (!(pde & PG_PRESENT_MASK)) {
849             goto do_fault;
850         }
851         if (pde & rsvd_mask) {
852             goto do_fault_rsvd;
853         }
854         ptep &= pde ^ PG_NX_MASK;
855         if (pde & PG_PSE_MASK) {
856             /* 2 MB page */
857             page_size = 2048 * 1024;
858             pte_addr = pde_addr;
859             pte = pde;
860             goto do_check_protect;
861         }
862         /* 4 KB page */
863         if (!(pde & PG_ACCESSED_MASK)) {
864             pde |= PG_ACCESSED_MASK;
865             x86_stl_phys_notdirty(cs, pde_addr, pde);
866         }
867         pte_addr = ((pde & PG_ADDRESS_MASK) + (((addr >> 12) & 0x1ff) << 3)) &
868             env->a20_mask;
869         pte = x86_ldq_phys(cs, pte_addr);
870         if (!(pte & PG_PRESENT_MASK)) {
871             goto do_fault;
872         }
873         if (pte & rsvd_mask) {
874             goto do_fault_rsvd;
875         }
876         /* combine pde and pte nx, user and rw protections */
877         ptep &= pte ^ PG_NX_MASK;
878         page_size = 4096;
879     } else {
880         uint32_t pde;
881 
882         /* page directory entry */
883         pde_addr = ((env->cr[3] & ~0xfff) + ((addr >> 20) & 0xffc)) &
884             env->a20_mask;
885         pde = x86_ldl_phys(cs, pde_addr);
886         if (!(pde & PG_PRESENT_MASK)) {
887             goto do_fault;
888         }
889         ptep = pde | PG_NX_MASK;
890 
891         /* if PSE bit is set, then we use a 4MB page */
892         if ((pde & PG_PSE_MASK) && (env->cr[4] & CR4_PSE_MASK)) {
893             page_size = 4096 * 1024;
894             pte_addr = pde_addr;
895 
896             /* Bits 20-13 provide bits 39-32 of the address, bit 21 is reserved.
897              * Leave bits 20-13 in place for setting accessed/dirty bits below.
898              */
899             pte = pde | ((pde & 0x1fe000LL) << (32 - 13));
900             rsvd_mask = 0x200000;
901             goto do_check_protect_pse36;
902         }
903 
904         if (!(pde & PG_ACCESSED_MASK)) {
905             pde |= PG_ACCESSED_MASK;
906             x86_stl_phys_notdirty(cs, pde_addr, pde);
907         }
908 
909         /* page directory entry */
910         pte_addr = ((pde & ~0xfff) + ((addr >> 10) & 0xffc)) &
911             env->a20_mask;
912         pte = x86_ldl_phys(cs, pte_addr);
913         if (!(pte & PG_PRESENT_MASK)) {
914             goto do_fault;
915         }
916         /* combine pde and pte user and rw protections */
917         ptep &= pte | PG_NX_MASK;
918         page_size = 4096;
919         rsvd_mask = 0;
920     }
921 
922 do_check_protect:
923     rsvd_mask |= (page_size - 1) & PG_ADDRESS_MASK & ~PG_PSE_PAT_MASK;
924 do_check_protect_pse36:
925     if (pte & rsvd_mask) {
926         goto do_fault_rsvd;
927     }
928     ptep ^= PG_NX_MASK;
929 
930     /* can the page can be put in the TLB?  prot will tell us */
931     if (is_user && !(ptep & PG_USER_MASK)) {
932         goto do_fault_protect;
933     }
934 
935     prot = 0;
936     if (mmu_idx != MMU_KSMAP_IDX || !(ptep & PG_USER_MASK)) {
937         prot |= PAGE_READ;
938         if ((ptep & PG_RW_MASK) || (!is_user && !(env->cr[0] & CR0_WP_MASK))) {
939             prot |= PAGE_WRITE;
940         }
941     }
942     if (!(ptep & PG_NX_MASK) &&
943         (mmu_idx == MMU_USER_IDX ||
944          !((env->cr[4] & CR4_SMEP_MASK) && (ptep & PG_USER_MASK)))) {
945         prot |= PAGE_EXEC;
946     }
947     if ((env->cr[4] & CR4_PKE_MASK) && (env->hflags & HF_LMA_MASK) &&
948         (ptep & PG_USER_MASK) && env->pkru) {
949         uint32_t pk = (pte & PG_PKRU_MASK) >> PG_PKRU_BIT;
950         uint32_t pkru_ad = (env->pkru >> pk * 2) & 1;
951         uint32_t pkru_wd = (env->pkru >> pk * 2) & 2;
952         uint32_t pkru_prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
953 
954         if (pkru_ad) {
955             pkru_prot &= ~(PAGE_READ | PAGE_WRITE);
956         } else if (pkru_wd && (is_user || env->cr[0] & CR0_WP_MASK)) {
957             pkru_prot &= ~PAGE_WRITE;
958         }
959 
960         prot &= pkru_prot;
961         if ((pkru_prot & (1 << is_write1)) == 0) {
962             assert(is_write1 != 2);
963             error_code |= PG_ERROR_PK_MASK;
964             goto do_fault_protect;
965         }
966     }
967 
968     if ((prot & (1 << is_write1)) == 0) {
969         goto do_fault_protect;
970     }
971 
972     /* yes, it can! */
973     is_dirty = is_write && !(pte & PG_DIRTY_MASK);
974     if (!(pte & PG_ACCESSED_MASK) || is_dirty) {
975         pte |= PG_ACCESSED_MASK;
976         if (is_dirty) {
977             pte |= PG_DIRTY_MASK;
978         }
979         x86_stl_phys_notdirty(cs, pte_addr, pte);
980     }
981 
982     if (!(pte & PG_DIRTY_MASK)) {
983         /* only set write access if already dirty... otherwise wait
984            for dirty access */
985         assert(!is_write);
986         prot &= ~PAGE_WRITE;
987     }
988 
989  do_mapping:
990     pte = pte & env->a20_mask;
991 
992     /* align to page_size */
993     pte &= PG_ADDRESS_MASK & ~(page_size - 1);
994 
995     /* Even if 4MB pages, we map only one 4KB page in the cache to
996        avoid filling it too fast */
997     vaddr = addr & TARGET_PAGE_MASK;
998     page_offset = vaddr & (page_size - 1);
999     paddr = pte + page_offset;
1000 
1001     assert(prot & (1 << is_write1));
1002     tlb_set_page_with_attrs(cs, vaddr, paddr, cpu_get_mem_attrs(env),
1003                             prot, mmu_idx, page_size);
1004     return 0;
1005  do_fault_rsvd:
1006     error_code |= PG_ERROR_RSVD_MASK;
1007  do_fault_protect:
1008     error_code |= PG_ERROR_P_MASK;
1009  do_fault:
1010     error_code |= (is_write << PG_ERROR_W_BIT);
1011     if (is_user)
1012         error_code |= PG_ERROR_U_MASK;
1013     if (is_write1 == 2 &&
1014         (((env->efer & MSR_EFER_NXE) &&
1015           (env->cr[4] & CR4_PAE_MASK)) ||
1016          (env->cr[4] & CR4_SMEP_MASK)))
1017         error_code |= PG_ERROR_I_D_MASK;
1018     if (env->intercept_exceptions & (1 << EXCP0E_PAGE)) {
1019         /* cr2 is not modified in case of exceptions */
1020         x86_stq_phys(cs,
1021                  env->vm_vmcb + offsetof(struct vmcb, control.exit_info_2),
1022                  addr);
1023     } else {
1024         env->cr[2] = addr;
1025     }
1026     env->error_code = error_code;
1027     cs->exception_index = EXCP0E_PAGE;
1028     return 1;
1029 }
1030 
1031 hwaddr x86_cpu_get_phys_page_debug(CPUState *cs, vaddr addr)
1032 {
1033     X86CPU *cpu = X86_CPU(cs);
1034     CPUX86State *env = &cpu->env;
1035     target_ulong pde_addr, pte_addr;
1036     uint64_t pte;
1037     uint32_t page_offset;
1038     int page_size;
1039 
1040     if (!(env->cr[0] & CR0_PG_MASK)) {
1041         pte = addr & env->a20_mask;
1042         page_size = 4096;
1043     } else if (env->cr[4] & CR4_PAE_MASK) {
1044         target_ulong pdpe_addr;
1045         uint64_t pde, pdpe;
1046 
1047 #ifdef TARGET_X86_64
1048         if (env->hflags & HF_LMA_MASK) {
1049             bool la57 = env->cr[4] & CR4_LA57_MASK;
1050             uint64_t pml5e_addr, pml5e;
1051             uint64_t pml4e_addr, pml4e;
1052             int32_t sext;
1053 
1054             /* test virtual address sign extension */
1055             sext = la57 ? (int64_t)addr >> 56 : (int64_t)addr >> 47;
1056             if (sext != 0 && sext != -1) {
1057                 return -1;
1058             }
1059 
1060             if (la57) {
1061                 pml5e_addr = ((env->cr[3] & ~0xfff) +
1062                         (((addr >> 48) & 0x1ff) << 3)) & env->a20_mask;
1063                 pml5e = x86_ldq_phys(cs, pml5e_addr);
1064                 if (!(pml5e & PG_PRESENT_MASK)) {
1065                     return -1;
1066                 }
1067             } else {
1068                 pml5e = env->cr[3];
1069             }
1070 
1071             pml4e_addr = ((pml5e & PG_ADDRESS_MASK) +
1072                     (((addr >> 39) & 0x1ff) << 3)) & env->a20_mask;
1073             pml4e = x86_ldq_phys(cs, pml4e_addr);
1074             if (!(pml4e & PG_PRESENT_MASK)) {
1075                 return -1;
1076             }
1077             pdpe_addr = ((pml4e & PG_ADDRESS_MASK) +
1078                          (((addr >> 30) & 0x1ff) << 3)) & env->a20_mask;
1079             pdpe = x86_ldq_phys(cs, pdpe_addr);
1080             if (!(pdpe & PG_PRESENT_MASK)) {
1081                 return -1;
1082             }
1083             if (pdpe & PG_PSE_MASK) {
1084                 page_size = 1024 * 1024 * 1024;
1085                 pte = pdpe;
1086                 goto out;
1087             }
1088 
1089         } else
1090 #endif
1091         {
1092             pdpe_addr = ((env->cr[3] & ~0x1f) + ((addr >> 27) & 0x18)) &
1093                 env->a20_mask;
1094             pdpe = x86_ldq_phys(cs, pdpe_addr);
1095             if (!(pdpe & PG_PRESENT_MASK))
1096                 return -1;
1097         }
1098 
1099         pde_addr = ((pdpe & PG_ADDRESS_MASK) +
1100                     (((addr >> 21) & 0x1ff) << 3)) & env->a20_mask;
1101         pde = x86_ldq_phys(cs, pde_addr);
1102         if (!(pde & PG_PRESENT_MASK)) {
1103             return -1;
1104         }
1105         if (pde & PG_PSE_MASK) {
1106             /* 2 MB page */
1107             page_size = 2048 * 1024;
1108             pte = pde;
1109         } else {
1110             /* 4 KB page */
1111             pte_addr = ((pde & PG_ADDRESS_MASK) +
1112                         (((addr >> 12) & 0x1ff) << 3)) & env->a20_mask;
1113             page_size = 4096;
1114             pte = x86_ldq_phys(cs, pte_addr);
1115         }
1116         if (!(pte & PG_PRESENT_MASK)) {
1117             return -1;
1118         }
1119     } else {
1120         uint32_t pde;
1121 
1122         /* page directory entry */
1123         pde_addr = ((env->cr[3] & ~0xfff) + ((addr >> 20) & 0xffc)) & env->a20_mask;
1124         pde = x86_ldl_phys(cs, pde_addr);
1125         if (!(pde & PG_PRESENT_MASK))
1126             return -1;
1127         if ((pde & PG_PSE_MASK) && (env->cr[4] & CR4_PSE_MASK)) {
1128             pte = pde | ((pde & 0x1fe000LL) << (32 - 13));
1129             page_size = 4096 * 1024;
1130         } else {
1131             /* page directory entry */
1132             pte_addr = ((pde & ~0xfff) + ((addr >> 10) & 0xffc)) & env->a20_mask;
1133             pte = x86_ldl_phys(cs, pte_addr);
1134             if (!(pte & PG_PRESENT_MASK)) {
1135                 return -1;
1136             }
1137             page_size = 4096;
1138         }
1139         pte = pte & env->a20_mask;
1140     }
1141 
1142 #ifdef TARGET_X86_64
1143 out:
1144 #endif
1145     pte &= PG_ADDRESS_MASK & ~(page_size - 1);
1146     page_offset = (addr & TARGET_PAGE_MASK) & (page_size - 1);
1147     return pte | page_offset;
1148 }
1149 
1150 typedef struct MCEInjectionParams {
1151     Monitor *mon;
1152     int bank;
1153     uint64_t status;
1154     uint64_t mcg_status;
1155     uint64_t addr;
1156     uint64_t misc;
1157     int flags;
1158 } MCEInjectionParams;
1159 
1160 static void do_inject_x86_mce(CPUState *cs, run_on_cpu_data data)
1161 {
1162     MCEInjectionParams *params = data.host_ptr;
1163     X86CPU *cpu = X86_CPU(cs);
1164     CPUX86State *cenv = &cpu->env;
1165     uint64_t *banks = cenv->mce_banks + 4 * params->bank;
1166 
1167     cpu_synchronize_state(cs);
1168 
1169     /*
1170      * If there is an MCE exception being processed, ignore this SRAO MCE
1171      * unless unconditional injection was requested.
1172      */
1173     if (!(params->flags & MCE_INJECT_UNCOND_AO)
1174         && !(params->status & MCI_STATUS_AR)
1175         && (cenv->mcg_status & MCG_STATUS_MCIP)) {
1176         return;
1177     }
1178 
1179     if (params->status & MCI_STATUS_UC) {
1180         /*
1181          * if MSR_MCG_CTL is not all 1s, the uncorrected error
1182          * reporting is disabled
1183          */
1184         if ((cenv->mcg_cap & MCG_CTL_P) && cenv->mcg_ctl != ~(uint64_t)0) {
1185             monitor_printf(params->mon,
1186                            "CPU %d: Uncorrected error reporting disabled\n",
1187                            cs->cpu_index);
1188             return;
1189         }
1190 
1191         /*
1192          * if MSR_MCi_CTL is not all 1s, the uncorrected error
1193          * reporting is disabled for the bank
1194          */
1195         if (banks[0] != ~(uint64_t)0) {
1196             monitor_printf(params->mon,
1197                            "CPU %d: Uncorrected error reporting disabled for"
1198                            " bank %d\n",
1199                            cs->cpu_index, params->bank);
1200             return;
1201         }
1202 
1203         if ((cenv->mcg_status & MCG_STATUS_MCIP) ||
1204             !(cenv->cr[4] & CR4_MCE_MASK)) {
1205             monitor_printf(params->mon,
1206                            "CPU %d: Previous MCE still in progress, raising"
1207                            " triple fault\n",
1208                            cs->cpu_index);
1209             qemu_log_mask(CPU_LOG_RESET, "Triple fault\n");
1210             qemu_system_reset_request();
1211             return;
1212         }
1213         if (banks[1] & MCI_STATUS_VAL) {
1214             params->status |= MCI_STATUS_OVER;
1215         }
1216         banks[2] = params->addr;
1217         banks[3] = params->misc;
1218         cenv->mcg_status = params->mcg_status;
1219         banks[1] = params->status;
1220         cpu_interrupt(cs, CPU_INTERRUPT_MCE);
1221     } else if (!(banks[1] & MCI_STATUS_VAL)
1222                || !(banks[1] & MCI_STATUS_UC)) {
1223         if (banks[1] & MCI_STATUS_VAL) {
1224             params->status |= MCI_STATUS_OVER;
1225         }
1226         banks[2] = params->addr;
1227         banks[3] = params->misc;
1228         banks[1] = params->status;
1229     } else {
1230         banks[1] |= MCI_STATUS_OVER;
1231     }
1232 }
1233 
1234 void cpu_x86_inject_mce(Monitor *mon, X86CPU *cpu, int bank,
1235                         uint64_t status, uint64_t mcg_status, uint64_t addr,
1236                         uint64_t misc, int flags)
1237 {
1238     CPUState *cs = CPU(cpu);
1239     CPUX86State *cenv = &cpu->env;
1240     MCEInjectionParams params = {
1241         .mon = mon,
1242         .bank = bank,
1243         .status = status,
1244         .mcg_status = mcg_status,
1245         .addr = addr,
1246         .misc = misc,
1247         .flags = flags,
1248     };
1249     unsigned bank_num = cenv->mcg_cap & 0xff;
1250 
1251     if (!cenv->mcg_cap) {
1252         monitor_printf(mon, "MCE injection not supported\n");
1253         return;
1254     }
1255     if (bank >= bank_num) {
1256         monitor_printf(mon, "Invalid MCE bank number\n");
1257         return;
1258     }
1259     if (!(status & MCI_STATUS_VAL)) {
1260         monitor_printf(mon, "Invalid MCE status code\n");
1261         return;
1262     }
1263     if ((flags & MCE_INJECT_BROADCAST)
1264         && !cpu_x86_support_mca_broadcast(cenv)) {
1265         monitor_printf(mon, "Guest CPU does not support MCA broadcast\n");
1266         return;
1267     }
1268 
1269     run_on_cpu(cs, do_inject_x86_mce, RUN_ON_CPU_HOST_PTR(&params));
1270     if (flags & MCE_INJECT_BROADCAST) {
1271         CPUState *other_cs;
1272 
1273         params.bank = 1;
1274         params.status = MCI_STATUS_VAL | MCI_STATUS_UC;
1275         params.mcg_status = MCG_STATUS_MCIP | MCG_STATUS_RIPV;
1276         params.addr = 0;
1277         params.misc = 0;
1278         CPU_FOREACH(other_cs) {
1279             if (other_cs == cs) {
1280                 continue;
1281             }
1282             run_on_cpu(other_cs, do_inject_x86_mce, RUN_ON_CPU_HOST_PTR(&params));
1283         }
1284     }
1285 }
1286 
1287 void cpu_report_tpr_access(CPUX86State *env, TPRAccess access)
1288 {
1289     X86CPU *cpu = x86_env_get_cpu(env);
1290     CPUState *cs = CPU(cpu);
1291 
1292     if (kvm_enabled()) {
1293         env->tpr_access_type = access;
1294 
1295         cpu_interrupt(cs, CPU_INTERRUPT_TPR);
1296     } else {
1297         cpu_restore_state(cs, cs->mem_io_pc);
1298 
1299         apic_handle_tpr_access_report(cpu->apic_state, env->eip, access);
1300     }
1301 }
1302 #endif /* !CONFIG_USER_ONLY */
1303 
1304 int cpu_x86_get_descr_debug(CPUX86State *env, unsigned int selector,
1305                             target_ulong *base, unsigned int *limit,
1306                             unsigned int *flags)
1307 {
1308     X86CPU *cpu = x86_env_get_cpu(env);
1309     CPUState *cs = CPU(cpu);
1310     SegmentCache *dt;
1311     target_ulong ptr;
1312     uint32_t e1, e2;
1313     int index;
1314 
1315     if (selector & 0x4)
1316         dt = &env->ldt;
1317     else
1318         dt = &env->gdt;
1319     index = selector & ~7;
1320     ptr = dt->base + index;
1321     if ((index + 7) > dt->limit
1322         || cpu_memory_rw_debug(cs, ptr, (uint8_t *)&e1, sizeof(e1), 0) != 0
1323         || cpu_memory_rw_debug(cs, ptr+4, (uint8_t *)&e2, sizeof(e2), 0) != 0)
1324         return 0;
1325 
1326     *base = ((e1 >> 16) | ((e2 & 0xff) << 16) | (e2 & 0xff000000));
1327     *limit = (e1 & 0xffff) | (e2 & 0x000f0000);
1328     if (e2 & DESC_G_MASK)
1329         *limit = (*limit << 12) | 0xfff;
1330     *flags = e2;
1331 
1332     return 1;
1333 }
1334 
1335 #if !defined(CONFIG_USER_ONLY)
1336 void do_cpu_init(X86CPU *cpu)
1337 {
1338     CPUState *cs = CPU(cpu);
1339     CPUX86State *env = &cpu->env;
1340     CPUX86State *save = g_new(CPUX86State, 1);
1341     int sipi = cs->interrupt_request & CPU_INTERRUPT_SIPI;
1342 
1343     *save = *env;
1344 
1345     cpu_reset(cs);
1346     cs->interrupt_request = sipi;
1347     memcpy(&env->start_init_save, &save->start_init_save,
1348            offsetof(CPUX86State, end_init_save) -
1349            offsetof(CPUX86State, start_init_save));
1350     g_free(save);
1351 
1352     if (kvm_enabled()) {
1353         kvm_arch_do_init_vcpu(cpu);
1354     }
1355     apic_init_reset(cpu->apic_state);
1356 }
1357 
1358 void do_cpu_sipi(X86CPU *cpu)
1359 {
1360     apic_sipi(cpu->apic_state);
1361 }
1362 #else
1363 void do_cpu_init(X86CPU *cpu)
1364 {
1365 }
1366 void do_cpu_sipi(X86CPU *cpu)
1367 {
1368 }
1369 #endif
1370 
1371 /* Frob eflags into and out of the CPU temporary format.  */
1372 
1373 void x86_cpu_exec_enter(CPUState *cs)
1374 {
1375     X86CPU *cpu = X86_CPU(cs);
1376     CPUX86State *env = &cpu->env;
1377 
1378     CC_SRC = env->eflags & (CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
1379     env->df = 1 - (2 * ((env->eflags >> 10) & 1));
1380     CC_OP = CC_OP_EFLAGS;
1381     env->eflags &= ~(DF_MASK | CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C);
1382 }
1383 
1384 void x86_cpu_exec_exit(CPUState *cs)
1385 {
1386     X86CPU *cpu = X86_CPU(cs);
1387     CPUX86State *env = &cpu->env;
1388 
1389     env->eflags = cpu_compute_eflags(env);
1390 }
1391 
1392 #ifndef CONFIG_USER_ONLY
1393 uint8_t x86_ldub_phys(CPUState *cs, hwaddr addr)
1394 {
1395     X86CPU *cpu = X86_CPU(cs);
1396     CPUX86State *env = &cpu->env;
1397 
1398     return address_space_ldub(cs->as, addr,
1399                               cpu_get_mem_attrs(env),
1400                               NULL);
1401 }
1402 
1403 uint32_t x86_lduw_phys(CPUState *cs, hwaddr addr)
1404 {
1405     X86CPU *cpu = X86_CPU(cs);
1406     CPUX86State *env = &cpu->env;
1407 
1408     return address_space_lduw(cs->as, addr,
1409                               cpu_get_mem_attrs(env),
1410                               NULL);
1411 }
1412 
1413 uint32_t x86_ldl_phys(CPUState *cs, hwaddr addr)
1414 {
1415     X86CPU *cpu = X86_CPU(cs);
1416     CPUX86State *env = &cpu->env;
1417 
1418     return address_space_ldl(cs->as, addr,
1419                              cpu_get_mem_attrs(env),
1420                              NULL);
1421 }
1422 
1423 uint64_t x86_ldq_phys(CPUState *cs, hwaddr addr)
1424 {
1425     X86CPU *cpu = X86_CPU(cs);
1426     CPUX86State *env = &cpu->env;
1427 
1428     return address_space_ldq(cs->as, addr,
1429                              cpu_get_mem_attrs(env),
1430                              NULL);
1431 }
1432 
1433 void x86_stb_phys(CPUState *cs, hwaddr addr, uint8_t val)
1434 {
1435     X86CPU *cpu = X86_CPU(cs);
1436     CPUX86State *env = &cpu->env;
1437 
1438     address_space_stb(cs->as, addr, val,
1439                       cpu_get_mem_attrs(env),
1440                       NULL);
1441 }
1442 
1443 void x86_stl_phys_notdirty(CPUState *cs, hwaddr addr, uint32_t val)
1444 {
1445     X86CPU *cpu = X86_CPU(cs);
1446     CPUX86State *env = &cpu->env;
1447 
1448     address_space_stl_notdirty(cs->as, addr, val,
1449                                cpu_get_mem_attrs(env),
1450                                NULL);
1451 }
1452 
1453 void x86_stw_phys(CPUState *cs, hwaddr addr, uint32_t val)
1454 {
1455     X86CPU *cpu = X86_CPU(cs);
1456     CPUX86State *env = &cpu->env;
1457 
1458     address_space_stw(cs->as, addr, val,
1459                       cpu_get_mem_attrs(env),
1460                       NULL);
1461 }
1462 
1463 void x86_stl_phys(CPUState *cs, hwaddr addr, uint32_t val)
1464 {
1465     X86CPU *cpu = X86_CPU(cs);
1466     CPUX86State *env = &cpu->env;
1467 
1468     address_space_stl(cs->as, addr, val,
1469                       cpu_get_mem_attrs(env),
1470                       NULL);
1471 }
1472 
1473 void x86_stq_phys(CPUState *cs, hwaddr addr, uint64_t val)
1474 {
1475     X86CPU *cpu = X86_CPU(cs);
1476     CPUX86State *env = &cpu->env;
1477 
1478     address_space_stq(cs->as, addr, val,
1479                       cpu_get_mem_attrs(env),
1480                       NULL);
1481 }
1482 #endif
1483