blob: 1b961333256f6a2736e3e52197bf95337902a2aa [file] [log] [blame]
Jun Nakajima86797932011-01-29 14:24:24 -08001/*
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, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301 USA
19 */
20#include <stdarg.h>
21#include <stdlib.h>
22#include <stdio.h>
23#include <string.h>
24#include <inttypes.h>
25#include <signal.h>
26
27#include "cpu.h"
David 'Digit' Turner852088c2013-12-14 23:04:12 +010028#include "exec/exec-all.h"
Jun Nakajima86797932011-01-29 14:24:24 -080029#include "qemu-common.h"
David 'Digit' Turner34c48ff2013-12-15 00:25:03 +010030#include "sysemu/kvm.h"
David 'Digit' Turnere1e03df2013-12-15 00:42:21 +010031#include "exec/hax.h"
Jun Nakajima86797932011-01-29 14:24:24 -080032
33//#define DEBUG_MMU
34
35/* feature flags taken from "Intel Processor Identification and the CPUID
36 * Instruction" and AMD's "CPUID Specification". In cases of disagreement
37 * about feature names, the Linux name is used. */
38static const char *feature_name[] = {
39 "fpu", "vme", "de", "pse", "tsc", "msr", "pae", "mce",
40 "cx8", "apic", NULL, "sep", "mtrr", "pge", "mca", "cmov",
41 "pat", "pse36", "pn" /* Intel psn */, "clflush" /* Intel clfsh */, NULL, "ds" /* Intel dts */, "acpi", "mmx",
42 "fxsr", "sse", "sse2", "ss", "ht" /* Intel htt */, "tm", "ia64", "pbe",
43};
44static const char *ext_feature_name[] = {
45 "pni" /* Intel,AMD sse3 */, NULL, NULL, "monitor", "ds_cpl", "vmx", NULL /* Linux smx */, "est",
46 "tm2", "ssse3", "cid", NULL, NULL, "cx16", "xtpr", NULL,
47 NULL, NULL, "dca", NULL, NULL, NULL, NULL, "popcnt",
48 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
49};
50static const char *ext2_feature_name[] = {
51 "fpu", "vme", "de", "pse", "tsc", "msr", "pae", "mce",
52 "cx8" /* AMD CMPXCHG8B */, "apic", NULL, "syscall", "mtrr", "pge", "mca", "cmov",
53 "pat", "pse36", NULL, NULL /* Linux mp */, "nx" /* Intel xd */, NULL, "mmxext", "mmx",
54 "fxsr", "fxsr_opt" /* AMD ffxsr */, "pdpe1gb" /* AMD Page1GB */, "rdtscp", NULL, "lm" /* Intel 64 */, "3dnowext", "3dnow",
55};
56static const char *ext3_feature_name[] = {
57 "lahf_lm" /* AMD LahfSahf */, "cmp_legacy", "svm", "extapic" /* AMD ExtApicSpace */, "cr8legacy" /* AMD AltMovCr8 */, "abm", "sse4a", "misalignsse",
58 "3dnowprefetch", "osvw", NULL /* Linux ibs */, NULL, "skinit", "wdt", NULL, NULL,
59 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
60 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
61};
62
David 'Digit' Turnerc0052462014-02-25 18:39:29 +010063static void add_flagname_to_bitmaps(char *flagname, uint32_t *features,
64 uint32_t *ext_features,
65 uint32_t *ext2_features,
Jun Nakajima86797932011-01-29 14:24:24 -080066 uint32_t *ext3_features)
67{
68 int i;
69 int found = 0;
70
David 'Digit' Turnerc0052462014-02-25 18:39:29 +010071 for ( i = 0 ; i < 32 ; i++ )
Jun Nakajima86797932011-01-29 14:24:24 -080072 if (feature_name[i] && !strcmp (flagname, feature_name[i])) {
73 *features |= 1 << i;
74 found = 1;
75 }
David 'Digit' Turnerc0052462014-02-25 18:39:29 +010076 for ( i = 0 ; i < 32 ; i++ )
Jun Nakajima86797932011-01-29 14:24:24 -080077 if (ext_feature_name[i] && !strcmp (flagname, ext_feature_name[i])) {
78 *ext_features |= 1 << i;
79 found = 1;
80 }
David 'Digit' Turnerc0052462014-02-25 18:39:29 +010081 for ( i = 0 ; i < 32 ; i++ )
Jun Nakajima86797932011-01-29 14:24:24 -080082 if (ext2_feature_name[i] && !strcmp (flagname, ext2_feature_name[i])) {
83 *ext2_features |= 1 << i;
84 found = 1;
85 }
David 'Digit' Turnerc0052462014-02-25 18:39:29 +010086 for ( i = 0 ; i < 32 ; i++ )
Jun Nakajima86797932011-01-29 14:24:24 -080087 if (ext3_feature_name[i] && !strcmp (flagname, ext3_feature_name[i])) {
88 *ext3_features |= 1 << i;
89 found = 1;
90 }
91 if (!found) {
92 fprintf(stderr, "CPU feature %s not found\n", flagname);
93 }
94}
95
96static void kvm_trim_features(uint32_t *features, uint32_t supported,
97 const char *names[])
98{
99 int i;
100 uint32_t mask;
101
102 for (i = 0; i < 32; ++i) {
103 mask = 1U << i;
104 if ((*features & mask) && !(supported & mask)) {
105 *features &= ~mask;
106 }
107 }
108}
109
110typedef struct x86_def_t {
111 const char *name;
112 uint32_t level;
113 uint32_t vendor1, vendor2, vendor3;
114 int family;
115 int model;
116 int stepping;
117 uint32_t features, ext_features, ext2_features, ext3_features;
118 uint32_t xlevel;
119 char model_id[48];
120 int vendor_override;
121} x86_def_t;
122
123#define I486_FEATURES (CPUID_FP87 | CPUID_VME | CPUID_PSE)
124#define PENTIUM_FEATURES (I486_FEATURES | CPUID_DE | CPUID_TSC | \
125 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_MMX)
126#define PENTIUM2_FEATURES (PENTIUM_FEATURES | CPUID_PAE | CPUID_SEP | \
127 CPUID_MTRR | CPUID_PGE | CPUID_MCA | CPUID_CMOV | CPUID_PAT | \
128 CPUID_PSE36 | CPUID_FXSR)
129#define PENTIUM3_FEATURES (PENTIUM2_FEATURES | CPUID_SSE)
130#define PPRO_FEATURES (CPUID_FP87 | CPUID_DE | CPUID_PSE | CPUID_TSC | \
131 CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \
132 CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \
133 CPUID_PAE | CPUID_SEP | CPUID_APIC)
134static x86_def_t x86_defs[] = {
135#ifdef TARGET_X86_64
136 {
137 .name = "qemu64",
138 .level = 2,
139 .vendor1 = CPUID_VENDOR_AMD_1,
140 .vendor2 = CPUID_VENDOR_AMD_2,
141 .vendor3 = CPUID_VENDOR_AMD_3,
142 .family = 6,
143 .model = 2,
144 .stepping = 3,
David 'Digit' Turnerc0052462014-02-25 18:39:29 +0100145 .features = PPRO_FEATURES |
Jun Nakajima86797932011-01-29 14:24:24 -0800146 /* these features are needed for Win64 and aren't fully implemented */
147 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
148 /* this feature is needed for Solaris and isn't fully implemented */
149 CPUID_PSE36,
150 .ext_features = CPUID_EXT_SSE3,
David 'Digit' Turnerc0052462014-02-25 18:39:29 +0100151 .ext2_features = (PPRO_FEATURES & 0x0183F3FF) |
Jun Nakajima86797932011-01-29 14:24:24 -0800152 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
153 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
154 .ext3_features = CPUID_EXT3_SVM,
155 .xlevel = 0x8000000A,
156 .model_id = "QEMU Virtual CPU version " QEMU_VERSION,
157 },
158 {
159 .name = "phenom",
160 .level = 5,
161 .vendor1 = CPUID_VENDOR_AMD_1,
162 .vendor2 = CPUID_VENDOR_AMD_2,
163 .vendor3 = CPUID_VENDOR_AMD_3,
164 .family = 16,
165 .model = 2,
166 .stepping = 3,
167 /* Missing: CPUID_VME, CPUID_HT */
David 'Digit' Turnerc0052462014-02-25 18:39:29 +0100168 .features = PPRO_FEATURES |
Jun Nakajima86797932011-01-29 14:24:24 -0800169 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
170 CPUID_PSE36,
171 /* Missing: CPUID_EXT_CX16, CPUID_EXT_POPCNT */
172 .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
173 /* Missing: CPUID_EXT2_PDPE1GB, CPUID_EXT2_RDTSCP */
David 'Digit' Turnerc0052462014-02-25 18:39:29 +0100174 .ext2_features = (PPRO_FEATURES & 0x0183F3FF) |
Jun Nakajima86797932011-01-29 14:24:24 -0800175 CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX |
176 CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT | CPUID_EXT2_MMXEXT |
177 CPUID_EXT2_FFXSR,
178 /* Missing: CPUID_EXT3_LAHF_LM, CPUID_EXT3_CMP_LEG, CPUID_EXT3_EXTAPIC,
179 CPUID_EXT3_CR8LEG, CPUID_EXT3_ABM, CPUID_EXT3_SSE4A,
180 CPUID_EXT3_MISALIGNSSE, CPUID_EXT3_3DNOWPREFETCH,
181 CPUID_EXT3_OSVW, CPUID_EXT3_IBS */
182 .ext3_features = CPUID_EXT3_SVM,
183 .xlevel = 0x8000001A,
184 .model_id = "AMD Phenom(tm) 9550 Quad-Core Processor"
185 },
186 {
187 .name = "core2duo",
188 .level = 10,
189 .family = 6,
190 .model = 15,
191 .stepping = 11,
192 /* The original CPU also implements these features:
193 CPUID_VME, CPUID_DTS, CPUID_ACPI, CPUID_SS, CPUID_HT,
194 CPUID_TM, CPUID_PBE */
195 .features = PPRO_FEATURES |
196 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA |
197 CPUID_PSE36,
198 /* The original CPU also implements these ext features:
199 CPUID_EXT_DTES64, CPUID_EXT_DSCPL, CPUID_EXT_VMX, CPUID_EXT_EST,
200 CPUID_EXT_TM2, CPUID_EXT_CX16, CPUID_EXT_XTPR, CPUID_EXT_PDCM */
201 .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR | CPUID_EXT_SSSE3,
202 .ext2_features = CPUID_EXT2_LM | CPUID_EXT2_SYSCALL | CPUID_EXT2_NX,
203 /* Missing: .ext3_features = CPUID_EXT3_LAHF_LM */
204 .xlevel = 0x80000008,
205 .model_id = "Intel(R) Core(TM)2 Duo CPU T7700 @ 2.40GHz",
206 },
207#endif
208 {
209 .name = "qemu32",
210 .level = 2,
211 .family = 6,
212 .model = 3,
213 .stepping = 3,
214 .features = PPRO_FEATURES,
Jun Nakajima599662d2011-02-10 17:43:27 -0800215 .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_SSSE3,
Jun Nakajima86797932011-01-29 14:24:24 -0800216 .xlevel = 0,
217 .model_id = "QEMU Virtual CPU version " QEMU_VERSION,
218 },
219 {
220 .name = "coreduo",
221 .level = 10,
222 .family = 6,
223 .model = 14,
224 .stepping = 8,
225 /* The original CPU also implements these features:
226 CPUID_DTS, CPUID_ACPI, CPUID_SS, CPUID_HT,
227 CPUID_TM, CPUID_PBE */
228 .features = PPRO_FEATURES | CPUID_VME |
229 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA,
230 /* The original CPU also implements these ext features:
231 CPUID_EXT_VMX, CPUID_EXT_EST, CPUID_EXT_TM2, CPUID_EXT_XTPR,
232 CPUID_EXT_PDCM */
233 .ext_features = CPUID_EXT_SSE3 | CPUID_EXT_MONITOR,
234 .ext2_features = CPUID_EXT2_NX,
235 .xlevel = 0x80000008,
236 .model_id = "Genuine Intel(R) CPU T2600 @ 2.16GHz",
237 },
238 {
239 .name = "486",
240 .level = 0,
241 .family = 4,
242 .model = 0,
243 .stepping = 0,
244 .features = I486_FEATURES,
245 .xlevel = 0,
246 },
247 {
248 .name = "pentium",
249 .level = 1,
250 .family = 5,
251 .model = 4,
252 .stepping = 3,
253 .features = PENTIUM_FEATURES,
254 .xlevel = 0,
255 },
256 {
257 .name = "pentium2",
258 .level = 2,
259 .family = 6,
260 .model = 5,
261 .stepping = 2,
262 .features = PENTIUM2_FEATURES,
263 .xlevel = 0,
264 },
265 {
266 .name = "pentium3",
267 .level = 2,
268 .family = 6,
269 .model = 7,
270 .stepping = 3,
271 .features = PENTIUM3_FEATURES,
272 .xlevel = 0,
273 },
274 {
275 .name = "athlon",
276 .level = 2,
277 .vendor1 = 0x68747541, /* "Auth" */
278 .vendor2 = 0x69746e65, /* "enti" */
279 .vendor3 = 0x444d4163, /* "cAMD" */
280 .family = 6,
281 .model = 2,
282 .stepping = 3,
283 .features = PPRO_FEATURES | CPUID_PSE36 | CPUID_VME | CPUID_MTRR | CPUID_MCA,
284 .ext2_features = (PPRO_FEATURES & 0x0183F3FF) | CPUID_EXT2_MMXEXT | CPUID_EXT2_3DNOW | CPUID_EXT2_3DNOWEXT,
285 .xlevel = 0x80000008,
286 /* XXX: put another string ? */
287 .model_id = "QEMU Virtual CPU version " QEMU_VERSION,
288 },
289 {
290 .name = "n270",
291 /* original is on level 10 */
292 .level = 5,
293 .family = 6,
294 .model = 28,
295 .stepping = 2,
296 .features = PPRO_FEATURES |
297 CPUID_MTRR | CPUID_CLFLUSH | CPUID_MCA | CPUID_VME,
298 /* Missing: CPUID_DTS | CPUID_ACPI | CPUID_SS |
299 * CPUID_HT | CPUID_TM | CPUID_PBE */
300 /* Some CPUs got no CPUID_SEP */
301 .ext_features = CPUID_EXT_MONITOR |
302 CPUID_EXT_SSE3 /* PNI */ | CPUID_EXT_SSSE3,
303 /* Missing: CPUID_EXT_DSCPL | CPUID_EXT_EST |
304 * CPUID_EXT_TM2 | CPUID_EXT_XTPR */
305 .ext2_features = (PPRO_FEATURES & 0x0183F3FF) | CPUID_EXT2_NX,
306 /* Missing: .ext3_features = CPUID_EXT3_LAHF_LM */
307 .xlevel = 0x8000000A,
308 .model_id = "Intel(R) Atom(TM) CPU N270 @ 1.60GHz",
309 },
310};
311
312static int cpu_x86_find_by_name(x86_def_t *x86_cpu_def, const char *cpu_model)
313{
314 unsigned int i;
315 x86_def_t *def;
316
317 char *s = strdup(cpu_model);
318 char *featurestr, *name = strtok(s, ",");
319 uint32_t plus_features = 0, plus_ext_features = 0, plus_ext2_features = 0, plus_ext3_features = 0;
320 uint32_t minus_features = 0, minus_ext_features = 0, minus_ext2_features = 0, minus_ext3_features = 0;
321 int family = -1, model = -1, stepping = -1;
322
323 def = NULL;
324 for (i = 0; i < ARRAY_SIZE(x86_defs); i++) {
325 if (strcmp(name, x86_defs[i].name) == 0) {
326 def = &x86_defs[i];
327 break;
328 }
329 }
330 if (!def)
331 goto error;
332 memcpy(x86_cpu_def, def, sizeof(*def));
333
334 featurestr = strtok(NULL, ",");
335
336 while (featurestr) {
337 char *val;
338 if (featurestr[0] == '+') {
339 add_flagname_to_bitmaps(featurestr + 1, &plus_features, &plus_ext_features, &plus_ext2_features, &plus_ext3_features);
340 } else if (featurestr[0] == '-') {
341 add_flagname_to_bitmaps(featurestr + 1, &minus_features, &minus_ext_features, &minus_ext2_features, &minus_ext3_features);
342 } else if ((val = strchr(featurestr, '='))) {
343 *val = 0; val++;
344 if (!strcmp(featurestr, "family")) {
345 char *err;
346 family = strtol(val, &err, 10);
347 if (!*val || *err || family < 0) {
348 fprintf(stderr, "bad numerical value %s\n", val);
349 goto error;
350 }
351 x86_cpu_def->family = family;
352 } else if (!strcmp(featurestr, "model")) {
353 char *err;
354 model = strtol(val, &err, 10);
355 if (!*val || *err || model < 0 || model > 0xff) {
356 fprintf(stderr, "bad numerical value %s\n", val);
357 goto error;
358 }
359 x86_cpu_def->model = model;
360 } else if (!strcmp(featurestr, "stepping")) {
361 char *err;
362 stepping = strtol(val, &err, 10);
363 if (!*val || *err || stepping < 0 || stepping > 0xf) {
364 fprintf(stderr, "bad numerical value %s\n", val);
365 goto error;
366 }
367 x86_cpu_def->stepping = stepping;
368 } else if (!strcmp(featurestr, "vendor")) {
369 if (strlen(val) != 12) {
370 fprintf(stderr, "vendor string must be 12 chars long\n");
371 goto error;
372 }
373 x86_cpu_def->vendor1 = 0;
374 x86_cpu_def->vendor2 = 0;
375 x86_cpu_def->vendor3 = 0;
376 for(i = 0; i < 4; i++) {
377 x86_cpu_def->vendor1 |= ((uint8_t)val[i ]) << (8 * i);
378 x86_cpu_def->vendor2 |= ((uint8_t)val[i + 4]) << (8 * i);
379 x86_cpu_def->vendor3 |= ((uint8_t)val[i + 8]) << (8 * i);
380 }
381 x86_cpu_def->vendor_override = 1;
382 } else if (!strcmp(featurestr, "model_id")) {
383 pstrcpy(x86_cpu_def->model_id, sizeof(x86_cpu_def->model_id),
384 val);
385 } else {
386 fprintf(stderr, "unrecognized feature %s\n", featurestr);
387 goto error;
388 }
389 } else {
390 fprintf(stderr, "feature string `%s' not in format (+feature|-feature|feature=xyz)\n", featurestr);
391 goto error;
392 }
393 featurestr = strtok(NULL, ",");
394 }
395 x86_cpu_def->features |= plus_features;
396 x86_cpu_def->ext_features |= plus_ext_features;
397 x86_cpu_def->ext2_features |= plus_ext2_features;
398 x86_cpu_def->ext3_features |= plus_ext3_features;
399 x86_cpu_def->features &= ~minus_features;
400 x86_cpu_def->ext_features &= ~minus_ext_features;
401 x86_cpu_def->ext2_features &= ~minus_ext2_features;
402 x86_cpu_def->ext3_features &= ~minus_ext3_features;
403 free(s);
404 return 0;
405
406error:
407 free(s);
408 return -1;
409}
410
411void x86_cpu_list (FILE *f, int (*cpu_fprintf)(FILE *f, const char *fmt, ...))
412{
413 unsigned int i;
414
415 for (i = 0; i < ARRAY_SIZE(x86_defs); i++)
416 (*cpu_fprintf)(f, "x86 %16s\n", x86_defs[i].name);
417}
418
419static int cpu_x86_register (CPUX86State *env, const char *cpu_model)
420{
421 x86_def_t def1, *def = &def1;
422
423 if (cpu_x86_find_by_name(def, cpu_model) < 0)
424 return -1;
425 if (def->vendor1) {
426 env->cpuid_vendor1 = def->vendor1;
427 env->cpuid_vendor2 = def->vendor2;
428 env->cpuid_vendor3 = def->vendor3;
429 } else {
430 env->cpuid_vendor1 = CPUID_VENDOR_INTEL_1;
431 env->cpuid_vendor2 = CPUID_VENDOR_INTEL_2;
432 env->cpuid_vendor3 = CPUID_VENDOR_INTEL_3;
433 }
434 env->cpuid_vendor_override = def->vendor_override;
435 env->cpuid_level = def->level;
436 if (def->family > 0x0f)
437 env->cpuid_version = 0xf00 | ((def->family - 0x0f) << 20);
438 else
439 env->cpuid_version = def->family << 8;
440 env->cpuid_version |= ((def->model & 0xf) << 4) | ((def->model >> 4) << 16);
441 env->cpuid_version |= def->stepping;
442 env->cpuid_features = def->features;
443 env->pat = 0x0007040600070406ULL;
444 env->cpuid_ext_features = def->ext_features;
445 env->cpuid_ext2_features = def->ext2_features;
446 env->cpuid_xlevel = def->xlevel;
447 env->cpuid_ext3_features = def->ext3_features;
448 {
449 const char *model_id = def->model_id;
450 int c, len, i;
451 if (!model_id)
452 model_id = "";
453 len = strlen(model_id);
454 for(i = 0; i < 48; i++) {
455 if (i >= len)
456 c = '\0';
457 else
458 c = (uint8_t)model_id[i];
459 env->cpuid_model[i >> 2] |= c << (8 * (i & 3));
460 }
461 }
462 return 0;
463}
464
465/* NOTE: must be called outside the CPU execute loop */
466void cpu_reset(CPUX86State *env)
467{
468 int i;
469
470 if (qemu_loglevel_mask(CPU_LOG_RESET)) {
471 qemu_log("CPU Reset (CPU %d)\n", env->cpu_index);
472 log_cpu_state(env, X86_DUMP_FPU | X86_DUMP_CCOP);
473 }
474
475 memset(env, 0, offsetof(CPUX86State, breakpoints));
476
477 tlb_flush(env, 1);
478
479 env->old_exception = -1;
480
481 /* init to reset state */
482
483#ifdef CONFIG_SOFTMMU
484 env->hflags |= HF_SOFTMMU_MASK;
485#endif
486 env->hflags2 |= HF2_GIF_MASK;
487
488 cpu_x86_update_cr0(env, 0x60000010);
489 env->a20_mask = ~0x0;
490 env->smbase = 0x30000;
491
492 env->idt.limit = 0xffff;
493 env->gdt.limit = 0xffff;
494 env->ldt.limit = 0xffff;
495 env->ldt.flags = DESC_P_MASK | (2 << DESC_TYPE_SHIFT);
496 env->tr.limit = 0xffff;
497 env->tr.flags = DESC_P_MASK | (11 << DESC_TYPE_SHIFT);
498
499 cpu_x86_load_seg_cache(env, R_CS, 0xf000, 0xffff0000, 0xffff,
500 DESC_P_MASK | DESC_S_MASK | DESC_CS_MASK |
501 DESC_R_MASK | DESC_A_MASK);
502 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffff,
503 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
504 DESC_A_MASK);
505 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffff,
506 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
507 DESC_A_MASK);
508 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffff,
509 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
510 DESC_A_MASK);
511 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffff,
512 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
513 DESC_A_MASK);
514 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffff,
515 DESC_P_MASK | DESC_S_MASK | DESC_W_MASK |
516 DESC_A_MASK);
517
518 env->eip = 0xfff0;
519 env->regs[R_EDX] = env->cpuid_version;
520
521 env->eflags = 0x2;
522
523 /* FPU init */
524 for(i = 0;i < 8; i++)
525 env->fptags[i] = 1;
526 env->fpuc = 0x37f;
527
528 env->mxcsr = 0x1f80;
529
530 memset(env->dr, 0, sizeof(env->dr));
531 env->dr[6] = DR6_FIXED_1;
532 env->dr[7] = DR7_FIXED_1;
533 cpu_breakpoint_remove_all(env, BP_CPU);
534 cpu_watchpoint_remove_all(env, BP_CPU);
535}
536
537void cpu_x86_close(CPUX86State *env)
538{
David 'Digit' Turneraa8236d2014-01-10 17:02:29 +0100539 g_free(env);
Jun Nakajima86797932011-01-29 14:24:24 -0800540}
541
542/***********************************************************/
543/* x86 debug */
544
545static const char *cc_op_str[] = {
546 "DYNAMIC",
547 "EFLAGS",
548
549 "MULB",
550 "MULW",
551 "MULL",
552 "MULQ",
553
554 "ADDB",
555 "ADDW",
556 "ADDL",
557 "ADDQ",
558
559 "ADCB",
560 "ADCW",
561 "ADCL",
562 "ADCQ",
563
564 "SUBB",
565 "SUBW",
566 "SUBL",
567 "SUBQ",
568
569 "SBBB",
570 "SBBW",
571 "SBBL",
572 "SBBQ",
573
574 "LOGICB",
575 "LOGICW",
576 "LOGICL",
577 "LOGICQ",
578
579 "INCB",
580 "INCW",
581 "INCL",
582 "INCQ",
583
584 "DECB",
585 "DECW",
586 "DECL",
587 "DECQ",
588
589 "SHLB",
590 "SHLW",
591 "SHLL",
592 "SHLQ",
593
594 "SARB",
595 "SARW",
596 "SARL",
597 "SARQ",
598};
599
600static void
David 'Digit' Turnere2678e12014-01-16 15:56:43 +0100601cpu_x86_dump_seg_cache(CPUX86State *env, FILE *f,
Jun Nakajima86797932011-01-29 14:24:24 -0800602 int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
603 const char *name, struct SegmentCache *sc)
604{
605#ifdef TARGET_X86_64
606 if (env->hflags & HF_CS64_MASK) {
607 cpu_fprintf(f, "%-3s=%04x %016" PRIx64 " %08x %08x", name,
608 sc->selector, sc->base, sc->limit, sc->flags);
609 } else
610#endif
611 {
612 cpu_fprintf(f, "%-3s=%04x %08x %08x %08x", name, sc->selector,
613 (uint32_t)sc->base, sc->limit, sc->flags);
614 }
615
616 if (!(env->hflags & HF_PE_MASK) || !(sc->flags & DESC_P_MASK))
617 goto done;
618
619 cpu_fprintf(f, " DPL=%d ", (sc->flags & DESC_DPL_MASK) >> DESC_DPL_SHIFT);
620 if (sc->flags & DESC_S_MASK) {
621 if (sc->flags & DESC_CS_MASK) {
622 cpu_fprintf(f, (sc->flags & DESC_L_MASK) ? "CS64" :
623 ((sc->flags & DESC_B_MASK) ? "CS32" : "CS16"));
624 cpu_fprintf(f, " [%c%c", (sc->flags & DESC_C_MASK) ? 'C' : '-',
625 (sc->flags & DESC_R_MASK) ? 'R' : '-');
626 } else {
627 cpu_fprintf(f, (sc->flags & DESC_B_MASK) ? "DS " : "DS16");
628 cpu_fprintf(f, " [%c%c", (sc->flags & DESC_E_MASK) ? 'E' : '-',
629 (sc->flags & DESC_W_MASK) ? 'W' : '-');
630 }
631 cpu_fprintf(f, "%c]", (sc->flags & DESC_A_MASK) ? 'A' : '-');
632 } else {
633 static const char *sys_type_name[2][16] = {
634 { /* 32 bit mode */
635 "Reserved", "TSS16-avl", "LDT", "TSS16-busy",
636 "CallGate16", "TaskGate", "IntGate16", "TrapGate16",
637 "Reserved", "TSS32-avl", "Reserved", "TSS32-busy",
638 "CallGate32", "Reserved", "IntGate32", "TrapGate32"
639 },
640 { /* 64 bit mode */
641 "<hiword>", "Reserved", "LDT", "Reserved", "Reserved",
642 "Reserved", "Reserved", "Reserved", "Reserved",
643 "TSS64-avl", "Reserved", "TSS64-busy", "CallGate64",
644 "Reserved", "IntGate64", "TrapGate64"
645 }
646 };
647 cpu_fprintf(f, sys_type_name[(env->hflags & HF_LMA_MASK) ? 1 : 0]
648 [(sc->flags & DESC_TYPE_MASK)
649 >> DESC_TYPE_SHIFT]);
650 }
651done:
652 cpu_fprintf(f, "\n");
653}
654
David 'Digit' Turnere2678e12014-01-16 15:56:43 +0100655void cpu_dump_state(CPUX86State *env, FILE *f,
Jun Nakajima86797932011-01-29 14:24:24 -0800656 int (*cpu_fprintf)(FILE *f, const char *fmt, ...),
657 int flags)
658{
659 int eflags, i, nb;
660 char cc_op_name[32];
661 static const char *seg_name[6] = { "ES", "CS", "SS", "DS", "FS", "GS" };
662
663 if (kvm_enabled())
664 kvm_arch_get_registers(env);
665
Jun Nakajimaa381ef02011-12-17 19:13:25 -0800666#ifdef CONFIG_HAX
667 if (hax_enabled())
668 hax_arch_get_registers(env);
669#endif
670
Jun Nakajima86797932011-01-29 14:24:24 -0800671 eflags = env->eflags;
672#ifdef TARGET_X86_64
673 if (env->hflags & HF_CS64_MASK) {
674 cpu_fprintf(f,
675 "RAX=%016" PRIx64 " RBX=%016" PRIx64 " RCX=%016" PRIx64 " RDX=%016" PRIx64 "\n"
676 "RSI=%016" PRIx64 " RDI=%016" PRIx64 " RBP=%016" PRIx64 " RSP=%016" PRIx64 "\n"
677 "R8 =%016" PRIx64 " R9 =%016" PRIx64 " R10=%016" PRIx64 " R11=%016" PRIx64 "\n"
678 "R12=%016" PRIx64 " R13=%016" PRIx64 " R14=%016" PRIx64 " R15=%016" PRIx64 "\n"
679 "RIP=%016" PRIx64 " RFL=%08x [%c%c%c%c%c%c%c] CPL=%d II=%d A20=%d SMM=%d HLT=%d\n",
680 env->regs[R_EAX],
681 env->regs[R_EBX],
682 env->regs[R_ECX],
683 env->regs[R_EDX],
684 env->regs[R_ESI],
685 env->regs[R_EDI],
686 env->regs[R_EBP],
687 env->regs[R_ESP],
688 env->regs[8],
689 env->regs[9],
690 env->regs[10],
691 env->regs[11],
692 env->regs[12],
693 env->regs[13],
694 env->regs[14],
695 env->regs[15],
696 env->eip, eflags,
697 eflags & DF_MASK ? 'D' : '-',
698 eflags & CC_O ? 'O' : '-',
699 eflags & CC_S ? 'S' : '-',
700 eflags & CC_Z ? 'Z' : '-',
701 eflags & CC_A ? 'A' : '-',
702 eflags & CC_P ? 'P' : '-',
703 eflags & CC_C ? 'C' : '-',
704 env->hflags & HF_CPL_MASK,
705 (env->hflags >> HF_INHIBIT_IRQ_SHIFT) & 1,
706 (int)(env->a20_mask >> 20) & 1,
707 (env->hflags >> HF_SMM_SHIFT) & 1,
708 env->halted);
709 } else
710#endif
711 {
712 cpu_fprintf(f, "EAX=%08x EBX=%08x ECX=%08x EDX=%08x\n"
713 "ESI=%08x EDI=%08x EBP=%08x ESP=%08x\n"
714 "EIP=%08x EFL=%08x [%c%c%c%c%c%c%c] CPL=%d II=%d A20=%d SMM=%d HLT=%d\n",
715 (uint32_t)env->regs[R_EAX],
716 (uint32_t)env->regs[R_EBX],
717 (uint32_t)env->regs[R_ECX],
718 (uint32_t)env->regs[R_EDX],
719 (uint32_t)env->regs[R_ESI],
720 (uint32_t)env->regs[R_EDI],
721 (uint32_t)env->regs[R_EBP],
722 (uint32_t)env->regs[R_ESP],
723 (uint32_t)env->eip, eflags,
724 eflags & DF_MASK ? 'D' : '-',
725 eflags & CC_O ? 'O' : '-',
726 eflags & CC_S ? 'S' : '-',
727 eflags & CC_Z ? 'Z' : '-',
728 eflags & CC_A ? 'A' : '-',
729 eflags & CC_P ? 'P' : '-',
730 eflags & CC_C ? 'C' : '-',
731 env->hflags & HF_CPL_MASK,
732 (env->hflags >> HF_INHIBIT_IRQ_SHIFT) & 1,
733 (int)(env->a20_mask >> 20) & 1,
734 (env->hflags >> HF_SMM_SHIFT) & 1,
735 env->halted);
736 }
737
738 for(i = 0; i < 6; i++) {
739 cpu_x86_dump_seg_cache(env, f, cpu_fprintf, seg_name[i],
740 &env->segs[i]);
741 }
742 cpu_x86_dump_seg_cache(env, f, cpu_fprintf, "LDT", &env->ldt);
743 cpu_x86_dump_seg_cache(env, f, cpu_fprintf, "TR", &env->tr);
744
745#ifdef TARGET_X86_64
746 if (env->hflags & HF_LMA_MASK) {
747 cpu_fprintf(f, "GDT= %016" PRIx64 " %08x\n",
748 env->gdt.base, env->gdt.limit);
749 cpu_fprintf(f, "IDT= %016" PRIx64 " %08x\n",
750 env->idt.base, env->idt.limit);
751 cpu_fprintf(f, "CR0=%08x CR2=%016" PRIx64 " CR3=%016" PRIx64 " CR4=%08x\n",
752 (uint32_t)env->cr[0],
753 env->cr[2],
754 env->cr[3],
755 (uint32_t)env->cr[4]);
756 for(i = 0; i < 4; i++)
757 cpu_fprintf(f, "DR%d=%016" PRIx64 " ", i, env->dr[i]);
758 cpu_fprintf(f, "\nDR6=%016" PRIx64 " DR7=%016" PRIx64 "\n",
759 env->dr[6], env->dr[7]);
760 } else
761#endif
762 {
763 cpu_fprintf(f, "GDT= %08x %08x\n",
764 (uint32_t)env->gdt.base, env->gdt.limit);
765 cpu_fprintf(f, "IDT= %08x %08x\n",
766 (uint32_t)env->idt.base, env->idt.limit);
767 cpu_fprintf(f, "CR0=%08x CR2=%08x CR3=%08x CR4=%08x\n",
768 (uint32_t)env->cr[0],
769 (uint32_t)env->cr[2],
770 (uint32_t)env->cr[3],
771 (uint32_t)env->cr[4]);
772 for(i = 0; i < 4; i++)
773 cpu_fprintf(f, "DR%d=%08x ", i, env->dr[i]);
774 cpu_fprintf(f, "\nDR6=%08x DR7=%08x\n", env->dr[6], env->dr[7]);
775 }
776 if (flags & X86_DUMP_CCOP) {
777 if ((unsigned)env->cc_op < CC_OP_NB)
778 snprintf(cc_op_name, sizeof(cc_op_name), "%s", cc_op_str[env->cc_op]);
779 else
780 snprintf(cc_op_name, sizeof(cc_op_name), "[%d]", env->cc_op);
781#ifdef TARGET_X86_64
782 if (env->hflags & HF_CS64_MASK) {
783 cpu_fprintf(f, "CCS=%016" PRIx64 " CCD=%016" PRIx64 " CCO=%-8s\n",
784 env->cc_src, env->cc_dst,
785 cc_op_name);
786 } else
787#endif
788 {
789 cpu_fprintf(f, "CCS=%08x CCD=%08x CCO=%-8s\n",
790 (uint32_t)env->cc_src, (uint32_t)env->cc_dst,
791 cc_op_name);
792 }
793 }
794 if (flags & X86_DUMP_FPU) {
795 int fptag;
796 fptag = 0;
797 for(i = 0; i < 8; i++) {
798 fptag |= ((!env->fptags[i]) << i);
799 }
800 cpu_fprintf(f, "FCW=%04x FSW=%04x [ST=%d] FTW=%02x MXCSR=%08x\n",
801 env->fpuc,
802 (env->fpus & ~0x3800) | (env->fpstt & 0x7) << 11,
803 env->fpstt,
804 fptag,
805 env->mxcsr);
806 for(i=0;i<8;i++) {
807#if defined(USE_X86LDOUBLE)
808 union {
809 long double d;
810 struct {
811 uint64_t lower;
812 uint16_t upper;
813 } l;
814 } tmp;
815 tmp.d = env->fpregs[i].d;
816 cpu_fprintf(f, "FPR%d=%016" PRIx64 " %04x",
817 i, tmp.l.lower, tmp.l.upper);
818#else
819 cpu_fprintf(f, "FPR%d=%016" PRIx64,
820 i, env->fpregs[i].mmx.q);
821#endif
822 if ((i & 1) == 1)
823 cpu_fprintf(f, "\n");
824 else
825 cpu_fprintf(f, " ");
826 }
827 if (env->hflags & HF_CS64_MASK)
828 nb = 16;
829 else
830 nb = 8;
831 for(i=0;i<nb;i++) {
832 cpu_fprintf(f, "XMM%02d=%08x%08x%08x%08x",
833 i,
834 env->xmm_regs[i].XMM_L(3),
835 env->xmm_regs[i].XMM_L(2),
836 env->xmm_regs[i].XMM_L(1),
837 env->xmm_regs[i].XMM_L(0));
838 if ((i & 1) == 1)
839 cpu_fprintf(f, "\n");
840 else
841 cpu_fprintf(f, " ");
842 }
843 }
844}
845
846/***********************************************************/
847/* x86 mmu */
848/* XXX: add PGE support */
849
850void cpu_x86_set_a20(CPUX86State *env, int a20_state)
851{
852 a20_state = (a20_state != 0);
853 if (a20_state != ((env->a20_mask >> 20) & 1)) {
854#if defined(DEBUG_MMU)
855 printf("A20 update: a20=%d\n", a20_state);
856#endif
857 /* if the cpu is currently executing code, we must unlink it and
858 all the potentially executing TB */
859 cpu_interrupt(env, CPU_INTERRUPT_EXITTB);
860
861 /* when a20 is changed, all the MMU mappings are invalid, so
862 we must flush everything */
863 tlb_flush(env, 1);
864 env->a20_mask = (~0x100000) | (a20_state << 20);
865 }
866}
867
868void cpu_x86_update_cr0(CPUX86State *env, uint32_t new_cr0)
869{
870 int pe_state;
871
872#if defined(DEBUG_MMU)
873 printf("CR0 update: CR0=0x%08x\n", new_cr0);
874#endif
875 if ((new_cr0 & (CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK)) !=
876 (env->cr[0] & (CR0_PG_MASK | CR0_WP_MASK | CR0_PE_MASK))) {
877 tlb_flush(env, 1);
878 }
879
880#ifdef TARGET_X86_64
881 if (!(env->cr[0] & CR0_PG_MASK) && (new_cr0 & CR0_PG_MASK) &&
882 (env->efer & MSR_EFER_LME)) {
883 /* enter in long mode */
884 /* XXX: generate an exception */
885 if (!(env->cr[4] & CR4_PAE_MASK))
886 return;
887 env->efer |= MSR_EFER_LMA;
888 env->hflags |= HF_LMA_MASK;
889 } else if ((env->cr[0] & CR0_PG_MASK) && !(new_cr0 & CR0_PG_MASK) &&
890 (env->efer & MSR_EFER_LMA)) {
891 /* exit long mode */
892 env->efer &= ~MSR_EFER_LMA;
893 env->hflags &= ~(HF_LMA_MASK | HF_CS64_MASK);
894 env->eip &= 0xffffffff;
895 }
896#endif
897 env->cr[0] = new_cr0 | CR0_ET_MASK;
898
899 /* update PE flag in hidden flags */
900 pe_state = (env->cr[0] & CR0_PE_MASK);
901 env->hflags = (env->hflags & ~HF_PE_MASK) | (pe_state << HF_PE_SHIFT);
902 /* ensure that ADDSEG is always set in real mode */
903 env->hflags |= ((pe_state ^ 1) << HF_ADDSEG_SHIFT);
904 /* update FPU flags */
905 env->hflags = (env->hflags & ~(HF_MP_MASK | HF_EM_MASK | HF_TS_MASK)) |
906 ((new_cr0 << (HF_MP_SHIFT - 1)) & (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK));
907}
908
909/* XXX: in legacy PAE mode, generate a GPF if reserved bits are set in
910 the PDPT */
911void cpu_x86_update_cr3(CPUX86State *env, target_ulong new_cr3)
912{
913 env->cr[3] = new_cr3;
914 if (env->cr[0] & CR0_PG_MASK) {
915#if defined(DEBUG_MMU)
916 printf("CR3 update: CR3=" TARGET_FMT_lx "\n", new_cr3);
917#endif
918 tlb_flush(env, 0);
919 }
920}
921
922void cpu_x86_update_cr4(CPUX86State *env, uint32_t new_cr4)
923{
924#if defined(DEBUG_MMU)
925 printf("CR4 update: CR4=%08x\n", (uint32_t)env->cr[4]);
926#endif
927 if ((new_cr4 & (CR4_PGE_MASK | CR4_PAE_MASK | CR4_PSE_MASK)) !=
928 (env->cr[4] & (CR4_PGE_MASK | CR4_PAE_MASK | CR4_PSE_MASK))) {
929 tlb_flush(env, 1);
930 }
931 /* SSE handling */
932 if (!(env->cpuid_features & CPUID_SSE))
933 new_cr4 &= ~CR4_OSFXSR_MASK;
934 if (new_cr4 & CR4_OSFXSR_MASK)
935 env->hflags |= HF_OSFXSR_MASK;
936 else
937 env->hflags &= ~HF_OSFXSR_MASK;
938
939 env->cr[4] = new_cr4;
940}
941
942#if defined(CONFIG_USER_ONLY)
943
944int cpu_x86_handle_mmu_fault(CPUX86State *env, target_ulong addr,
945 int is_write, int mmu_idx, int is_softmmu)
946{
947 /* user mode only emulation */
948 is_write &= 1;
949 env->cr[2] = addr;
950 env->error_code = (is_write << PG_ERROR_W_BIT);
951 env->error_code |= PG_ERROR_U_MASK;
952 env->exception_index = EXCP0E_PAGE;
953 return 1;
954}
955
David 'Digit' Turnere2678e12014-01-16 15:56:43 +0100956hwaddr cpu_get_phys_page_debug(CPUX86State *env, target_ulong addr)
Jun Nakajima86797932011-01-29 14:24:24 -0800957{
958 return addr;
959}
960
961#else
962
963/* XXX: This value should match the one returned by CPUID
964 * and in exec.c */
David 'Digit' Turner81911b02014-02-10 17:53:45 +0100965#if defined(TARGET_X86_64)
Jun Nakajima86797932011-01-29 14:24:24 -0800966# define PHYS_ADDR_MASK 0xfffffff000LL
David 'Digit' Turner81911b02014-02-10 17:53:45 +0100967#else
Jun Nakajima86797932011-01-29 14:24:24 -0800968# define PHYS_ADDR_MASK 0xffffff000LL
Jun Nakajima86797932011-01-29 14:24:24 -0800969#endif
970
971/* return value:
972 -1 = cannot handle fault
973 0 = nothing more to do
974 1 = generate PF fault
975 2 = soft MMU activation required for this block
976*/
977int cpu_x86_handle_mmu_fault(CPUX86State *env, target_ulong addr,
978 int is_write1, int mmu_idx, int is_softmmu)
979{
980 uint64_t ptep, pte;
981 target_ulong pde_addr, pte_addr;
982 int error_code, is_dirty, prot, page_size, ret, is_write, is_user;
David 'Digit' Turnerbcde1092014-01-09 23:19:19 +0100983 hwaddr paddr;
Jun Nakajima86797932011-01-29 14:24:24 -0800984 uint32_t page_offset;
985 target_ulong vaddr, virt_addr;
986
987 is_user = mmu_idx == MMU_USER_IDX;
988#if defined(DEBUG_MMU)
989 printf("MMU fault: addr=" TARGET_FMT_lx " w=%d u=%d eip=" TARGET_FMT_lx "\n",
990 addr, is_write1, is_user, env->eip);
991#endif
992 is_write = is_write1 & 1;
993
994 if (!(env->cr[0] & CR0_PG_MASK)) {
995 pte = addr;
996 virt_addr = addr & TARGET_PAGE_MASK;
997 prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
998 page_size = 4096;
999 goto do_mapping;
1000 }
1001
1002 if (env->cr[4] & CR4_PAE_MASK) {
1003 uint64_t pde, pdpe;
1004 target_ulong pdpe_addr;
1005
1006#ifdef TARGET_X86_64
1007 if (env->hflags & HF_LMA_MASK) {
1008 uint64_t pml4e_addr, pml4e;
1009 int32_t sext;
1010
1011 /* test virtual address sign extension */
1012 sext = (int64_t)addr >> 47;
1013 if (sext != 0 && sext != -1) {
1014 env->error_code = 0;
1015 env->exception_index = EXCP0D_GPF;
1016 return 1;
1017 }
1018
1019 pml4e_addr = ((env->cr[3] & ~0xfff) + (((addr >> 39) & 0x1ff) << 3)) &
1020 env->a20_mask;
1021 pml4e = ldq_phys(pml4e_addr);
1022 if (!(pml4e & PG_PRESENT_MASK)) {
1023 error_code = 0;
1024 goto do_fault;
1025 }
1026 if (!(env->efer & MSR_EFER_NXE) && (pml4e & PG_NX_MASK)) {
1027 error_code = PG_ERROR_RSVD_MASK;
1028 goto do_fault;
1029 }
1030 if (!(pml4e & PG_ACCESSED_MASK)) {
1031 pml4e |= PG_ACCESSED_MASK;
1032 stl_phys_notdirty(pml4e_addr, pml4e);
1033 }
1034 ptep = pml4e ^ PG_NX_MASK;
1035 pdpe_addr = ((pml4e & PHYS_ADDR_MASK) + (((addr >> 30) & 0x1ff) << 3)) &
1036 env->a20_mask;
1037 pdpe = ldq_phys(pdpe_addr);
1038 if (!(pdpe & PG_PRESENT_MASK)) {
1039 error_code = 0;
1040 goto do_fault;
1041 }
1042 if (!(env->efer & MSR_EFER_NXE) && (pdpe & PG_NX_MASK)) {
1043 error_code = PG_ERROR_RSVD_MASK;
1044 goto do_fault;
1045 }
1046 ptep &= pdpe ^ PG_NX_MASK;
1047 if (!(pdpe & PG_ACCESSED_MASK)) {
1048 pdpe |= PG_ACCESSED_MASK;
1049 stl_phys_notdirty(pdpe_addr, pdpe);
1050 }
1051 } else
1052#endif
1053 {
1054 /* XXX: load them when cr3 is loaded ? */
1055 pdpe_addr = ((env->cr[3] & ~0x1f) + ((addr >> 27) & 0x18)) &
1056 env->a20_mask;
1057 pdpe = ldq_phys(pdpe_addr);
1058 if (!(pdpe & PG_PRESENT_MASK)) {
1059 error_code = 0;
1060 goto do_fault;
1061 }
1062 ptep = PG_NX_MASK | PG_USER_MASK | PG_RW_MASK;
1063 }
1064
1065 pde_addr = ((pdpe & PHYS_ADDR_MASK) + (((addr >> 21) & 0x1ff) << 3)) &
1066 env->a20_mask;
1067 pde = ldq_phys(pde_addr);
1068 if (!(pde & PG_PRESENT_MASK)) {
1069 error_code = 0;
1070 goto do_fault;
1071 }
1072 if (!(env->efer & MSR_EFER_NXE) && (pde & PG_NX_MASK)) {
1073 error_code = PG_ERROR_RSVD_MASK;
1074 goto do_fault;
1075 }
1076 ptep &= pde ^ PG_NX_MASK;
1077 if (pde & PG_PSE_MASK) {
1078 /* 2 MB page */
1079 page_size = 2048 * 1024;
1080 ptep ^= PG_NX_MASK;
1081 if ((ptep & PG_NX_MASK) && is_write1 == 2)
1082 goto do_fault_protect;
1083 if (is_user) {
1084 if (!(ptep & PG_USER_MASK))
1085 goto do_fault_protect;
1086 if (is_write && !(ptep & PG_RW_MASK))
1087 goto do_fault_protect;
1088 } else {
1089 if ((env->cr[0] & CR0_WP_MASK) &&
1090 is_write && !(ptep & PG_RW_MASK))
1091 goto do_fault_protect;
1092 }
1093 is_dirty = is_write && !(pde & PG_DIRTY_MASK);
1094 if (!(pde & PG_ACCESSED_MASK) || is_dirty) {
1095 pde |= PG_ACCESSED_MASK;
1096 if (is_dirty)
1097 pde |= PG_DIRTY_MASK;
1098 stl_phys_notdirty(pde_addr, pde);
1099 }
1100 /* align to page_size */
1101 pte = pde & ((PHYS_ADDR_MASK & ~(page_size - 1)) | 0xfff);
1102 virt_addr = addr & ~(page_size - 1);
1103 } else {
1104 /* 4 KB page */
1105 if (!(pde & PG_ACCESSED_MASK)) {
1106 pde |= PG_ACCESSED_MASK;
1107 stl_phys_notdirty(pde_addr, pde);
1108 }
1109 pte_addr = ((pde & PHYS_ADDR_MASK) + (((addr >> 12) & 0x1ff) << 3)) &
1110 env->a20_mask;
1111 pte = ldq_phys(pte_addr);
1112 if (!(pte & PG_PRESENT_MASK)) {
1113 error_code = 0;
1114 goto do_fault;
1115 }
1116 if (!(env->efer & MSR_EFER_NXE) && (pte & PG_NX_MASK)) {
1117 error_code = PG_ERROR_RSVD_MASK;
1118 goto do_fault;
1119 }
1120 /* combine pde and pte nx, user and rw protections */
1121 ptep &= pte ^ PG_NX_MASK;
1122 ptep ^= PG_NX_MASK;
1123 if ((ptep & PG_NX_MASK) && is_write1 == 2)
1124 goto do_fault_protect;
1125 if (is_user) {
1126 if (!(ptep & PG_USER_MASK))
1127 goto do_fault_protect;
1128 if (is_write && !(ptep & PG_RW_MASK))
1129 goto do_fault_protect;
1130 } else {
1131 if ((env->cr[0] & CR0_WP_MASK) &&
1132 is_write && !(ptep & PG_RW_MASK))
1133 goto do_fault_protect;
1134 }
1135 is_dirty = is_write && !(pte & PG_DIRTY_MASK);
1136 if (!(pte & PG_ACCESSED_MASK) || is_dirty) {
1137 pte |= PG_ACCESSED_MASK;
1138 if (is_dirty)
1139 pte |= PG_DIRTY_MASK;
1140 stl_phys_notdirty(pte_addr, pte);
1141 }
1142 page_size = 4096;
1143 virt_addr = addr & ~0xfff;
1144 pte = pte & (PHYS_ADDR_MASK | 0xfff);
1145 }
1146 } else {
1147 uint32_t pde;
1148
1149 /* page directory entry */
1150 pde_addr = ((env->cr[3] & ~0xfff) + ((addr >> 20) & 0xffc)) &
1151 env->a20_mask;
1152 pde = ldl_phys(pde_addr);
1153 if (!(pde & PG_PRESENT_MASK)) {
1154 error_code = 0;
1155 goto do_fault;
1156 }
1157 /* if PSE bit is set, then we use a 4MB page */
1158 if ((pde & PG_PSE_MASK) && (env->cr[4] & CR4_PSE_MASK)) {
1159 page_size = 4096 * 1024;
1160 if (is_user) {
1161 if (!(pde & PG_USER_MASK))
1162 goto do_fault_protect;
1163 if (is_write && !(pde & PG_RW_MASK))
1164 goto do_fault_protect;
1165 } else {
1166 if ((env->cr[0] & CR0_WP_MASK) &&
1167 is_write && !(pde & PG_RW_MASK))
1168 goto do_fault_protect;
1169 }
1170 is_dirty = is_write && !(pde & PG_DIRTY_MASK);
1171 if (!(pde & PG_ACCESSED_MASK) || is_dirty) {
1172 pde |= PG_ACCESSED_MASK;
1173 if (is_dirty)
1174 pde |= PG_DIRTY_MASK;
1175 stl_phys_notdirty(pde_addr, pde);
1176 }
1177
1178 pte = pde & ~( (page_size - 1) & ~0xfff); /* align to page_size */
1179 ptep = pte;
1180 virt_addr = addr & ~(page_size - 1);
1181 } else {
1182 if (!(pde & PG_ACCESSED_MASK)) {
1183 pde |= PG_ACCESSED_MASK;
1184 stl_phys_notdirty(pde_addr, pde);
1185 }
1186
1187 /* page directory entry */
1188 pte_addr = ((pde & ~0xfff) + ((addr >> 10) & 0xffc)) &
1189 env->a20_mask;
1190 pte = ldl_phys(pte_addr);
1191 if (!(pte & PG_PRESENT_MASK)) {
1192 error_code = 0;
1193 goto do_fault;
1194 }
1195 /* combine pde and pte user and rw protections */
1196 ptep = pte & pde;
1197 if (is_user) {
1198 if (!(ptep & PG_USER_MASK))
1199 goto do_fault_protect;
1200 if (is_write && !(ptep & PG_RW_MASK))
1201 goto do_fault_protect;
1202 } else {
1203 if ((env->cr[0] & CR0_WP_MASK) &&
1204 is_write && !(ptep & PG_RW_MASK))
1205 goto do_fault_protect;
1206 }
1207 is_dirty = is_write && !(pte & PG_DIRTY_MASK);
1208 if (!(pte & PG_ACCESSED_MASK) || is_dirty) {
1209 pte |= PG_ACCESSED_MASK;
1210 if (is_dirty)
1211 pte |= PG_DIRTY_MASK;
1212 stl_phys_notdirty(pte_addr, pte);
1213 }
1214 page_size = 4096;
1215 virt_addr = addr & ~0xfff;
1216 }
1217 }
1218 /* the page can be put in the TLB */
1219 prot = PAGE_READ;
1220 if (!(ptep & PG_NX_MASK))
1221 prot |= PAGE_EXEC;
1222 if (pte & PG_DIRTY_MASK) {
1223 /* only set write access if already dirty... otherwise wait
1224 for dirty access */
1225 if (is_user) {
1226 if (ptep & PG_RW_MASK)
1227 prot |= PAGE_WRITE;
1228 } else {
1229 if (!(env->cr[0] & CR0_WP_MASK) ||
1230 (ptep & PG_RW_MASK))
1231 prot |= PAGE_WRITE;
1232 }
1233 }
1234 do_mapping:
1235 pte = pte & env->a20_mask;
1236
1237 /* Even if 4MB pages, we map only one 4KB page in the cache to
1238 avoid filling it too fast */
1239 page_offset = (addr & TARGET_PAGE_MASK) & (page_size - 1);
1240 paddr = (pte & TARGET_PAGE_MASK) + page_offset;
1241 vaddr = virt_addr + page_offset;
1242
1243 ret = tlb_set_page_exec(env, vaddr, paddr, prot, mmu_idx, is_softmmu);
1244 return ret;
1245 do_fault_protect:
1246 error_code = PG_ERROR_P_MASK;
1247 do_fault:
1248 error_code |= (is_write << PG_ERROR_W_BIT);
1249 if (is_user)
1250 error_code |= PG_ERROR_U_MASK;
1251 if (is_write1 == 2 &&
1252 (env->efer & MSR_EFER_NXE) &&
1253 (env->cr[4] & CR4_PAE_MASK))
1254 error_code |= PG_ERROR_I_D_MASK;
1255 if (env->intercept_exceptions & (1 << EXCP0E_PAGE)) {
1256 /* cr2 is not modified in case of exceptions */
David 'Digit' Turnerc0052462014-02-25 18:39:29 +01001257 stq_phys(env->vm_vmcb + offsetof(struct vmcb, control.exit_info_2),
Jun Nakajima86797932011-01-29 14:24:24 -08001258 addr);
1259 } else {
1260 env->cr[2] = addr;
1261 }
1262 env->error_code = error_code;
1263 env->exception_index = EXCP0E_PAGE;
1264 return 1;
1265}
1266
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001267hwaddr cpu_get_phys_page_debug(CPUX86State *env, target_ulong addr)
Jun Nakajima86797932011-01-29 14:24:24 -08001268{
1269 target_ulong pde_addr, pte_addr;
1270 uint64_t pte;
David 'Digit' Turnerbcde1092014-01-09 23:19:19 +01001271 hwaddr paddr;
Jun Nakajima86797932011-01-29 14:24:24 -08001272 uint32_t page_offset;
1273 int page_size;
1274
1275 if (env->cr[4] & CR4_PAE_MASK) {
1276 target_ulong pdpe_addr;
1277 uint64_t pde, pdpe;
1278
1279#ifdef TARGET_X86_64
1280 if (env->hflags & HF_LMA_MASK) {
1281 uint64_t pml4e_addr, pml4e;
1282 int32_t sext;
1283
1284 /* test virtual address sign extension */
1285 sext = (int64_t)addr >> 47;
1286 if (sext != 0 && sext != -1)
1287 return -1;
1288
1289 pml4e_addr = ((env->cr[3] & ~0xfff) + (((addr >> 39) & 0x1ff) << 3)) &
1290 env->a20_mask;
1291 pml4e = ldq_phys(pml4e_addr);
1292 if (!(pml4e & PG_PRESENT_MASK))
1293 return -1;
1294
1295 pdpe_addr = ((pml4e & ~0xfff) + (((addr >> 30) & 0x1ff) << 3)) &
1296 env->a20_mask;
1297 pdpe = ldq_phys(pdpe_addr);
1298 if (!(pdpe & PG_PRESENT_MASK))
1299 return -1;
1300 } else
1301#endif
1302 {
1303 pdpe_addr = ((env->cr[3] & ~0x1f) + ((addr >> 27) & 0x18)) &
1304 env->a20_mask;
1305 pdpe = ldq_phys(pdpe_addr);
1306 if (!(pdpe & PG_PRESENT_MASK))
1307 return -1;
1308 }
1309
1310 pde_addr = ((pdpe & ~0xfff) + (((addr >> 21) & 0x1ff) << 3)) &
1311 env->a20_mask;
1312 pde = ldq_phys(pde_addr);
1313 if (!(pde & PG_PRESENT_MASK)) {
1314 return -1;
1315 }
1316 if (pde & PG_PSE_MASK) {
1317 /* 2 MB page */
1318 page_size = 2048 * 1024;
1319 pte = pde & ~( (page_size - 1) & ~0xfff); /* align to page_size */
1320 } else {
1321 /* 4 KB page */
1322 pte_addr = ((pde & ~0xfff) + (((addr >> 12) & 0x1ff) << 3)) &
1323 env->a20_mask;
1324 page_size = 4096;
1325 pte = ldq_phys(pte_addr);
1326 }
1327 if (!(pte & PG_PRESENT_MASK))
1328 return -1;
1329 } else {
1330 uint32_t pde;
1331
1332 if (!(env->cr[0] & CR0_PG_MASK)) {
1333 pte = addr;
1334 page_size = 4096;
1335 } else {
1336 /* page directory entry */
1337 pde_addr = ((env->cr[3] & ~0xfff) + ((addr >> 20) & 0xffc)) & env->a20_mask;
1338 pde = ldl_phys(pde_addr);
1339 if (!(pde & PG_PRESENT_MASK))
1340 return -1;
1341 if ((pde & PG_PSE_MASK) && (env->cr[4] & CR4_PSE_MASK)) {
1342 pte = pde & ~0x003ff000; /* align to 4MB */
1343 page_size = 4096 * 1024;
1344 } else {
1345 /* page directory entry */
1346 pte_addr = ((pde & ~0xfff) + ((addr >> 10) & 0xffc)) & env->a20_mask;
1347 pte = ldl_phys(pte_addr);
1348 if (!(pte & PG_PRESENT_MASK))
1349 return -1;
1350 page_size = 4096;
1351 }
1352 }
1353 pte = pte & env->a20_mask;
1354 }
1355
1356 page_offset = (addr & TARGET_PAGE_MASK) & (page_size - 1);
1357 paddr = (pte & TARGET_PAGE_MASK) + page_offset;
1358 return paddr;
1359}
1360
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001361void hw_breakpoint_insert(CPUX86State *env, int index)
Jun Nakajima86797932011-01-29 14:24:24 -08001362{
1363 int type, err = 0;
1364
1365 switch (hw_breakpoint_type(env->dr[7], index)) {
1366 case 0:
1367 if (hw_breakpoint_enabled(env->dr[7], index))
1368 err = cpu_breakpoint_insert(env, env->dr[index], BP_CPU,
1369 &env->cpu_breakpoint[index]);
1370 break;
1371 case 1:
1372 type = BP_CPU | BP_MEM_WRITE;
1373 goto insert_wp;
1374 case 2:
1375 /* No support for I/O watchpoints yet */
1376 break;
1377 case 3:
1378 type = BP_CPU | BP_MEM_ACCESS;
1379 insert_wp:
1380 err = cpu_watchpoint_insert(env, env->dr[index],
1381 hw_breakpoint_len(env->dr[7], index),
1382 type, &env->cpu_watchpoint[index]);
1383 break;
1384 }
1385 if (err)
1386 env->cpu_breakpoint[index] = NULL;
1387}
1388
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001389void hw_breakpoint_remove(CPUX86State *env, int index)
Jun Nakajima86797932011-01-29 14:24:24 -08001390{
1391 if (!env->cpu_breakpoint[index])
1392 return;
1393 switch (hw_breakpoint_type(env->dr[7], index)) {
1394 case 0:
1395 if (hw_breakpoint_enabled(env->dr[7], index))
1396 cpu_breakpoint_remove_by_ref(env, env->cpu_breakpoint[index]);
1397 break;
1398 case 1:
1399 case 3:
1400 cpu_watchpoint_remove_by_ref(env, env->cpu_watchpoint[index]);
1401 break;
1402 case 2:
1403 /* No support for I/O watchpoints yet */
1404 break;
1405 }
1406}
1407
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001408int check_hw_breakpoints(CPUX86State *env, int force_dr6_update)
Jun Nakajima86797932011-01-29 14:24:24 -08001409{
1410 target_ulong dr6;
1411 int reg, type;
1412 int hit_enabled = 0;
1413
1414 dr6 = env->dr[6] & ~0xf;
1415 for (reg = 0; reg < 4; reg++) {
1416 type = hw_breakpoint_type(env->dr[7], reg);
1417 if ((type == 0 && env->dr[reg] == env->eip) ||
1418 ((type & 1) && env->cpu_watchpoint[reg] &&
1419 (env->cpu_watchpoint[reg]->flags & BP_WATCHPOINT_HIT))) {
1420 dr6 |= 1 << reg;
1421 if (hw_breakpoint_enabled(env->dr[7], reg))
1422 hit_enabled = 1;
1423 }
1424 }
1425 if (hit_enabled || force_dr6_update)
1426 env->dr[6] = dr6;
1427 return hit_enabled;
1428}
1429
1430static CPUDebugExcpHandler *prev_debug_excp_handler;
1431
1432void raise_exception(int exception_index);
1433
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001434static void breakpoint_handler(CPUX86State *env)
Jun Nakajima86797932011-01-29 14:24:24 -08001435{
1436 CPUBreakpoint *bp;
1437
1438 if (env->watchpoint_hit) {
1439 if (env->watchpoint_hit->flags & BP_CPU) {
1440 env->watchpoint_hit = NULL;
1441 if (check_hw_breakpoints(env, 0))
1442 raise_exception(EXCP01_DB);
1443 else
1444 cpu_resume_from_signal(env, NULL);
1445 }
1446 } else {
1447 QTAILQ_FOREACH(bp, &env->breakpoints, entry)
1448 if (bp->pc == env->eip) {
1449 if (bp->flags & BP_CPU) {
1450 check_hw_breakpoints(env, 1);
1451 raise_exception(EXCP01_DB);
1452 }
1453 break;
1454 }
1455 }
1456 if (prev_debug_excp_handler)
1457 prev_debug_excp_handler(env);
1458}
1459
1460
1461/* This should come from sysemu.h - if we could include it here... */
1462void qemu_system_reset_request(void);
1463
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001464void cpu_inject_x86_mce(CPUX86State *cenv, int bank, uint64_t status,
Jun Nakajima86797932011-01-29 14:24:24 -08001465 uint64_t mcg_status, uint64_t addr, uint64_t misc)
1466{
1467 uint64_t mcg_cap = cenv->mcg_cap;
1468 unsigned bank_num = mcg_cap & 0xff;
1469 uint64_t *banks = cenv->mce_banks;
1470
1471 if (bank >= bank_num || !(status & MCI_STATUS_VAL))
1472 return;
1473
1474 /*
1475 * if MSR_MCG_CTL is not all 1s, the uncorrected error
1476 * reporting is disabled
1477 */
1478 if ((status & MCI_STATUS_UC) && (mcg_cap & MCG_CTL_P) &&
1479 cenv->mcg_ctl != ~(uint64_t)0)
1480 return;
1481 banks += 4 * bank;
1482 /*
1483 * if MSR_MCi_CTL is not all 1s, the uncorrected error
1484 * reporting is disabled for the bank
1485 */
1486 if ((status & MCI_STATUS_UC) && banks[0] != ~(uint64_t)0)
1487 return;
1488 if (status & MCI_STATUS_UC) {
1489 if ((cenv->mcg_status & MCG_STATUS_MCIP) ||
1490 !(cenv->cr[4] & CR4_MCE_MASK)) {
1491 fprintf(stderr, "injects mce exception while previous "
1492 "one is in progress!\n");
1493 qemu_log_mask(CPU_LOG_RESET, "Triple fault\n");
1494 qemu_system_reset_request();
1495 return;
1496 }
1497 if (banks[1] & MCI_STATUS_VAL)
1498 status |= MCI_STATUS_OVER;
1499 banks[2] = addr;
1500 banks[3] = misc;
1501 cenv->mcg_status = mcg_status;
1502 banks[1] = status;
1503 cpu_interrupt(cenv, CPU_INTERRUPT_MCE);
1504 } else if (!(banks[1] & MCI_STATUS_VAL)
1505 || !(banks[1] & MCI_STATUS_UC)) {
1506 if (banks[1] & MCI_STATUS_VAL)
1507 status |= MCI_STATUS_OVER;
1508 banks[2] = addr;
1509 banks[3] = misc;
1510 banks[1] = status;
1511 } else
1512 banks[1] |= MCI_STATUS_OVER;
1513}
1514#endif /* !CONFIG_USER_ONLY */
1515
1516static void mce_init(CPUX86State *cenv)
1517{
1518 unsigned int bank, bank_num;
1519
1520 if (((cenv->cpuid_version >> 8)&0xf) >= 6
1521 && (cenv->cpuid_features&(CPUID_MCE|CPUID_MCA)) == (CPUID_MCE|CPUID_MCA)) {
1522 cenv->mcg_cap = MCE_CAP_DEF | MCE_BANKS_DEF;
1523 cenv->mcg_ctl = ~(uint64_t)0;
1524 bank_num = cenv->mcg_cap & 0xff;
David 'Digit' Turneraa8236d2014-01-10 17:02:29 +01001525 cenv->mce_banks = g_malloc0(bank_num * sizeof(uint64_t) * 4);
Jun Nakajima86797932011-01-29 14:24:24 -08001526 for (bank = 0; bank < bank_num; bank++)
1527 cenv->mce_banks[bank*4] = ~(uint64_t)0;
1528 }
1529}
1530
1531static void host_cpuid(uint32_t function, uint32_t count,
1532 uint32_t *eax, uint32_t *ebx,
1533 uint32_t *ecx, uint32_t *edx)
1534{
1535#if defined(CONFIG_KVM)
1536 uint32_t vec[4];
1537
1538#ifdef __x86_64__
1539 asm volatile("cpuid"
1540 : "=a"(vec[0]), "=b"(vec[1]),
1541 "=c"(vec[2]), "=d"(vec[3])
1542 : "0"(function), "c"(count) : "cc");
1543#else
1544 asm volatile("pusha \n\t"
1545 "cpuid \n\t"
1546 "mov %%eax, 0(%2) \n\t"
1547 "mov %%ebx, 4(%2) \n\t"
1548 "mov %%ecx, 8(%2) \n\t"
1549 "mov %%edx, 12(%2) \n\t"
1550 "popa"
1551 : : "a"(function), "c"(count), "S"(vec)
1552 : "memory", "cc");
1553#endif
1554
1555 if (eax)
1556 *eax = vec[0];
1557 if (ebx)
1558 *ebx = vec[1];
1559 if (ecx)
1560 *ecx = vec[2];
1561 if (edx)
1562 *edx = vec[3];
1563#endif
1564}
1565
1566void cpu_x86_cpuid(CPUX86State *env, uint32_t index, uint32_t count,
1567 uint32_t *eax, uint32_t *ebx,
1568 uint32_t *ecx, uint32_t *edx)
1569{
1570 /* test if maximum index reached */
1571 if (index & 0x80000000) {
1572 if (index > env->cpuid_xlevel)
1573 index = env->cpuid_level;
1574 } else {
1575 if (index > env->cpuid_level)
1576 index = env->cpuid_level;
1577 }
1578
1579 switch(index) {
1580 case 0:
1581 *eax = env->cpuid_level;
1582 *ebx = env->cpuid_vendor1;
1583 *edx = env->cpuid_vendor2;
1584 *ecx = env->cpuid_vendor3;
1585
1586 /* sysenter isn't supported on compatibility mode on AMD. and syscall
1587 * isn't supported in compatibility mode on Intel. so advertise the
1588 * actuall cpu, and say goodbye to migration between different vendors
1589 * is you use compatibility mode. */
1590 if (kvm_enabled() && !env->cpuid_vendor_override)
1591 host_cpuid(0, 0, NULL, ebx, ecx, edx);
1592 break;
1593 case 1:
1594 *eax = env->cpuid_version;
Maciek Molerusaab4f052011-08-31 16:39:55 +02001595 if (kvm_enabled() && !env->cpuid_vendor_override) {
1596 /* take only subset of ext features which processor can handle */
1597 uint32_t unused;
1598 host_cpuid(1, 0, NULL, &unused, ecx, &unused);
1599 } else {
1600 *ecx = UINT32_MAX;
1601 }
Jun Nakajima86797932011-01-29 14:24:24 -08001602 *ebx = (env->cpuid_apic_id << 24) | 8 << 8; /* CLFLUSH size in quad words, Linux wants it. */
Maciek Molerusaab4f052011-08-31 16:39:55 +02001603 *ecx &= env->cpuid_ext_features;
Jun Nakajima86797932011-01-29 14:24:24 -08001604 *edx = env->cpuid_features;
1605
1606 /* "Hypervisor present" bit required for Microsoft SVVP */
1607 if (kvm_enabled())
1608 *ecx |= (1 << 31);
1609 break;
1610 case 2:
1611 /* cache info: needed for Pentium Pro compatibility */
1612 *eax = 1;
1613 *ebx = 0;
1614 *ecx = 0;
1615 *edx = 0x2c307d;
1616 break;
1617 case 4:
1618 /* cache info: needed for Core compatibility */
1619 switch (count) {
1620 case 0: /* L1 dcache info */
1621 *eax = 0x0000121;
1622 *ebx = 0x1c0003f;
1623 *ecx = 0x000003f;
1624 *edx = 0x0000001;
1625 break;
1626 case 1: /* L1 icache info */
1627 *eax = 0x0000122;
1628 *ebx = 0x1c0003f;
1629 *ecx = 0x000003f;
1630 *edx = 0x0000001;
1631 break;
1632 case 2: /* L2 cache info */
1633 *eax = 0x0000143;
1634 *ebx = 0x3c0003f;
1635 *ecx = 0x0000fff;
1636 *edx = 0x0000001;
1637 break;
1638 default: /* end of info */
1639 *eax = 0;
1640 *ebx = 0;
1641 *ecx = 0;
1642 *edx = 0;
1643 break;
1644 }
1645 break;
1646 case 5:
1647 /* mwait info: needed for Core compatibility */
1648 *eax = 0; /* Smallest monitor-line size in bytes */
1649 *ebx = 0; /* Largest monitor-line size in bytes */
1650 *ecx = CPUID_MWAIT_EMX | CPUID_MWAIT_IBE;
1651 *edx = 0;
1652 break;
1653 case 6:
1654 /* Thermal and Power Leaf */
1655 *eax = 0;
1656 *ebx = 0;
1657 *ecx = 0;
1658 *edx = 0;
1659 break;
1660 case 9:
1661 /* Direct Cache Access Information Leaf */
1662 *eax = 0; /* Bits 0-31 in DCA_CAP MSR */
1663 *ebx = 0;
1664 *ecx = 0;
1665 *edx = 0;
1666 break;
1667 case 0xA:
1668 /* Architectural Performance Monitoring Leaf */
1669 *eax = 0;
1670 *ebx = 0;
1671 *ecx = 0;
1672 *edx = 0;
1673 break;
1674 case 0x80000000:
1675 *eax = env->cpuid_xlevel;
1676 *ebx = env->cpuid_vendor1;
1677 *edx = env->cpuid_vendor2;
1678 *ecx = env->cpuid_vendor3;
1679 break;
1680 case 0x80000001:
1681 *eax = env->cpuid_features;
1682 *ebx = 0;
1683 *ecx = env->cpuid_ext3_features;
1684 *edx = env->cpuid_ext2_features;
1685
1686 if (kvm_enabled()) {
1687 uint32_t h_eax, h_edx;
1688
1689 host_cpuid(index, 0, &h_eax, NULL, NULL, &h_edx);
1690
1691 /* disable CPU features that the host does not support */
1692
1693 /* long mode */
1694 if ((h_edx & 0x20000000) == 0 /* || !lm_capable_kernel */)
1695 *edx &= ~0x20000000;
1696 /* syscall */
1697 if ((h_edx & 0x00000800) == 0)
1698 *edx &= ~0x00000800;
1699 /* nx */
1700 if ((h_edx & 0x00100000) == 0)
1701 *edx &= ~0x00100000;
1702
1703 /* disable CPU features that KVM cannot support */
1704
1705 /* svm */
1706 *ecx &= ~4UL;
1707 /* 3dnow */
1708 *edx &= ~0xc0000000;
1709 }
1710 break;
1711 case 0x80000002:
1712 case 0x80000003:
1713 case 0x80000004:
1714 *eax = env->cpuid_model[(index - 0x80000002) * 4 + 0];
1715 *ebx = env->cpuid_model[(index - 0x80000002) * 4 + 1];
1716 *ecx = env->cpuid_model[(index - 0x80000002) * 4 + 2];
1717 *edx = env->cpuid_model[(index - 0x80000002) * 4 + 3];
1718 break;
1719 case 0x80000005:
1720 /* cache info (L1 cache) */
1721 *eax = 0x01ff01ff;
1722 *ebx = 0x01ff01ff;
1723 *ecx = 0x40020140;
1724 *edx = 0x40020140;
1725 break;
1726 case 0x80000006:
1727 /* cache info (L2 cache) */
1728 *eax = 0;
1729 *ebx = 0x42004200;
1730 *ecx = 0x02008140;
1731 *edx = 0;
1732 break;
1733 case 0x80000008:
1734 /* virtual & phys address size in low 2 bytes. */
David 'Digit' Turnerc0052462014-02-25 18:39:29 +01001735/* XXX: This value must match the one used in the MMU code. */
Jun Nakajima86797932011-01-29 14:24:24 -08001736 if (env->cpuid_ext2_features & CPUID_EXT2_LM) {
1737 /* 64 bit processor */
Jun Nakajima86797932011-01-29 14:24:24 -08001738/* XXX: The physical address space is limited to 42 bits in exec.c. */
1739 *eax = 0x00003028; /* 48 bits virtual, 40 bits physical */
Jun Nakajima86797932011-01-29 14:24:24 -08001740 } else {
Jun Nakajima86797932011-01-29 14:24:24 -08001741 if (env->cpuid_features & CPUID_PSE36)
1742 *eax = 0x00000024; /* 36 bits physical */
1743 else
1744 *eax = 0x00000020; /* 32 bits physical */
Jun Nakajima86797932011-01-29 14:24:24 -08001745 }
1746 *ebx = 0;
1747 *ecx = 0;
1748 *edx = 0;
1749 break;
1750 case 0x8000000A:
1751 *eax = 0x00000001; /* SVM Revision */
1752 *ebx = 0x00000010; /* nr of ASIDs */
1753 *ecx = 0;
1754 *edx = 0; /* optional features */
1755 break;
1756 default:
1757 /* reserved values: zero */
1758 *eax = 0;
1759 *ebx = 0;
1760 *ecx = 0;
1761 *edx = 0;
1762 break;
1763 }
1764}
1765
1766CPUX86State *cpu_x86_init(const char *cpu_model)
1767{
1768 CPUX86State *env;
1769 static int inited;
1770
David 'Digit' Turneraa8236d2014-01-10 17:02:29 +01001771 env = g_malloc0(sizeof(CPUX86State));
Jun Nakajima86797932011-01-29 14:24:24 -08001772 cpu_exec_init(env);
1773 env->cpu_model_str = cpu_model;
1774
1775 /* init various static tables */
1776 if (!inited) {
1777 inited = 1;
1778 optimize_flags_init();
1779#ifndef CONFIG_USER_ONLY
1780 prev_debug_excp_handler =
1781 cpu_set_debug_excp_handler(breakpoint_handler);
1782#endif
1783 }
1784 if (cpu_x86_register(env, cpu_model) < 0) {
1785 cpu_x86_close(env);
1786 return NULL;
1787 }
1788 mce_init(env);
1789 cpu_reset(env);
Jun Nakajima86797932011-01-29 14:24:24 -08001790
1791 qemu_init_vcpu(env);
1792
1793 if (kvm_enabled()) {
1794 kvm_trim_features(&env->cpuid_features,
1795 kvm_arch_get_supported_cpuid(env, 1, R_EDX),
1796 feature_name);
1797 kvm_trim_features(&env->cpuid_ext_features,
1798 kvm_arch_get_supported_cpuid(env, 1, R_ECX),
1799 ext_feature_name);
1800 kvm_trim_features(&env->cpuid_ext2_features,
1801 kvm_arch_get_supported_cpuid(env, 0x80000001, R_EDX),
1802 ext2_feature_name);
1803 kvm_trim_features(&env->cpuid_ext3_features,
1804 kvm_arch_get_supported_cpuid(env, 0x80000001, R_ECX),
1805 ext3_feature_name);
1806 }
1807
1808 return env;
1809}
1810
1811#if !defined(CONFIG_USER_ONLY)
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001812void do_cpu_init(CPUX86State *env)
Jun Nakajima86797932011-01-29 14:24:24 -08001813{
1814 int sipi = env->interrupt_request & CPU_INTERRUPT_SIPI;
1815 cpu_reset(env);
1816 env->interrupt_request = sipi;
1817 apic_init_reset(env);
1818}
1819
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001820void do_cpu_sipi(CPUX86State *env)
Jun Nakajima86797932011-01-29 14:24:24 -08001821{
1822 apic_sipi(env);
1823}
1824#else
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001825void do_cpu_init(CPUX86State *env)
Jun Nakajima86797932011-01-29 14:24:24 -08001826{
1827}
David 'Digit' Turnere2678e12014-01-16 15:56:43 +01001828void do_cpu_sipi(CPUX86State *env)
Jun Nakajima86797932011-01-29 14:24:24 -08001829{
1830}
1831#endif