root / target-i386 / machine.c @ 94909d9f
History | View | Annotate | Download (9.2 kB)
1 | 8dd3dca3 | aurel32 | #include "hw/hw.h" |
---|---|---|---|
2 | 8dd3dca3 | aurel32 | #include "hw/boards.h" |
3 | 8dd3dca3 | aurel32 | #include "hw/pc.h" |
4 | 8dd3dca3 | aurel32 | #include "hw/isa.h" |
5 | 8dd3dca3 | aurel32 | |
6 | 8dd3dca3 | aurel32 | #include "exec-all.h" |
7 | 8dd3dca3 | aurel32 | |
8 | 8dd3dca3 | aurel32 | void register_machines(void) |
9 | 8dd3dca3 | aurel32 | { |
10 | 8dd3dca3 | aurel32 | qemu_register_machine(&pc_machine); |
11 | 8dd3dca3 | aurel32 | qemu_register_machine(&isapc_machine); |
12 | e37630ca | aliguori | #ifdef CONFIG_XEN
|
13 | e37630ca | aliguori | qemu_register_machine(&xenpv_machine); |
14 | e37630ca | aliguori | #endif
|
15 | 8dd3dca3 | aurel32 | } |
16 | 8dd3dca3 | aurel32 | |
17 | 8dd3dca3 | aurel32 | static void cpu_put_seg(QEMUFile *f, SegmentCache *dt) |
18 | 8dd3dca3 | aurel32 | { |
19 | 8dd3dca3 | aurel32 | qemu_put_be32(f, dt->selector); |
20 | 8dd3dca3 | aurel32 | qemu_put_betl(f, dt->base); |
21 | 8dd3dca3 | aurel32 | qemu_put_be32(f, dt->limit); |
22 | 8dd3dca3 | aurel32 | qemu_put_be32(f, dt->flags); |
23 | 8dd3dca3 | aurel32 | } |
24 | 8dd3dca3 | aurel32 | |
25 | 8dd3dca3 | aurel32 | static void cpu_get_seg(QEMUFile *f, SegmentCache *dt) |
26 | 8dd3dca3 | aurel32 | { |
27 | 8dd3dca3 | aurel32 | dt->selector = qemu_get_be32(f); |
28 | 8dd3dca3 | aurel32 | dt->base = qemu_get_betl(f); |
29 | 8dd3dca3 | aurel32 | dt->limit = qemu_get_be32(f); |
30 | 8dd3dca3 | aurel32 | dt->flags = qemu_get_be32(f); |
31 | 8dd3dca3 | aurel32 | } |
32 | 8dd3dca3 | aurel32 | |
33 | 8dd3dca3 | aurel32 | void cpu_save(QEMUFile *f, void *opaque) |
34 | 8dd3dca3 | aurel32 | { |
35 | 8dd3dca3 | aurel32 | CPUState *env = opaque; |
36 | 8dd3dca3 | aurel32 | uint16_t fptag, fpus, fpuc, fpregs_format; |
37 | 8dd3dca3 | aurel32 | uint32_t hflags; |
38 | 7caa33f7 | aurel32 | int32_t a20_mask; |
39 | 8dd3dca3 | aurel32 | int i;
|
40 | 8dd3dca3 | aurel32 | |
41 | 8dd3dca3 | aurel32 | for(i = 0; i < CPU_NB_REGS; i++) |
42 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->regs[i]); |
43 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->eip); |
44 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->eflags); |
45 | 8dd3dca3 | aurel32 | hflags = env->hflags; /* XXX: suppress most of the redundant hflags */
|
46 | 8dd3dca3 | aurel32 | qemu_put_be32s(f, &hflags); |
47 | 8dd3dca3 | aurel32 | |
48 | 8dd3dca3 | aurel32 | /* FPU */
|
49 | 8dd3dca3 | aurel32 | fpuc = env->fpuc; |
50 | 8dd3dca3 | aurel32 | fpus = (env->fpus & ~0x3800) | (env->fpstt & 0x7) << 11; |
51 | 8dd3dca3 | aurel32 | fptag = 0;
|
52 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) { |
53 | 8dd3dca3 | aurel32 | fptag |= ((!env->fptags[i]) << i); |
54 | 8dd3dca3 | aurel32 | } |
55 | 8dd3dca3 | aurel32 | |
56 | 8dd3dca3 | aurel32 | qemu_put_be16s(f, &fpuc); |
57 | 8dd3dca3 | aurel32 | qemu_put_be16s(f, &fpus); |
58 | 8dd3dca3 | aurel32 | qemu_put_be16s(f, &fptag); |
59 | 8dd3dca3 | aurel32 | |
60 | 8dd3dca3 | aurel32 | #ifdef USE_X86LDOUBLE
|
61 | 8dd3dca3 | aurel32 | fpregs_format = 0;
|
62 | 8dd3dca3 | aurel32 | #else
|
63 | 8dd3dca3 | aurel32 | fpregs_format = 1;
|
64 | 8dd3dca3 | aurel32 | #endif
|
65 | 8dd3dca3 | aurel32 | qemu_put_be16s(f, &fpregs_format); |
66 | 8dd3dca3 | aurel32 | |
67 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) { |
68 | 8dd3dca3 | aurel32 | #ifdef USE_X86LDOUBLE
|
69 | 8dd3dca3 | aurel32 | { |
70 | 8dd3dca3 | aurel32 | uint64_t mant; |
71 | 8dd3dca3 | aurel32 | uint16_t exp; |
72 | 8dd3dca3 | aurel32 | /* we save the real CPU data (in case of MMX usage only 'mant'
|
73 | 8dd3dca3 | aurel32 | contains the MMX register */
|
74 | 8dd3dca3 | aurel32 | cpu_get_fp80(&mant, &exp, env->fpregs[i].d); |
75 | 8dd3dca3 | aurel32 | qemu_put_be64(f, mant); |
76 | 8dd3dca3 | aurel32 | qemu_put_be16(f, exp); |
77 | 8dd3dca3 | aurel32 | } |
78 | 8dd3dca3 | aurel32 | #else
|
79 | 8dd3dca3 | aurel32 | /* if we use doubles for float emulation, we save the doubles to
|
80 | 8dd3dca3 | aurel32 | avoid losing information in case of MMX usage. It can give
|
81 | 8dd3dca3 | aurel32 | problems if the image is restored on a CPU where long
|
82 | 8dd3dca3 | aurel32 | doubles are used instead. */
|
83 | 8dd3dca3 | aurel32 | qemu_put_be64(f, env->fpregs[i].mmx.MMX_Q(0));
|
84 | 8dd3dca3 | aurel32 | #endif
|
85 | 8dd3dca3 | aurel32 | } |
86 | 8dd3dca3 | aurel32 | |
87 | 8dd3dca3 | aurel32 | for(i = 0; i < 6; i++) |
88 | 8dd3dca3 | aurel32 | cpu_put_seg(f, &env->segs[i]); |
89 | 8dd3dca3 | aurel32 | cpu_put_seg(f, &env->ldt); |
90 | 8dd3dca3 | aurel32 | cpu_put_seg(f, &env->tr); |
91 | 8dd3dca3 | aurel32 | cpu_put_seg(f, &env->gdt); |
92 | 8dd3dca3 | aurel32 | cpu_put_seg(f, &env->idt); |
93 | 8dd3dca3 | aurel32 | |
94 | f5049756 | aliguori | qemu_put_be32s(f, &env->sysenter_cs); |
95 | 2436b61a | balrog | qemu_put_betls(f, &env->sysenter_esp); |
96 | 2436b61a | balrog | qemu_put_betls(f, &env->sysenter_eip); |
97 | 8dd3dca3 | aurel32 | |
98 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->cr[0]);
|
99 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->cr[2]);
|
100 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->cr[3]);
|
101 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->cr[4]);
|
102 | 8dd3dca3 | aurel32 | |
103 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) |
104 | 8dd3dca3 | aurel32 | qemu_put_betls(f, &env->dr[i]); |
105 | 8dd3dca3 | aurel32 | |
106 | 8dd3dca3 | aurel32 | /* MMU */
|
107 | 7caa33f7 | aurel32 | a20_mask = (int32_t) env->a20_mask; |
108 | b6c4f71f | blueswir1 | qemu_put_sbe32s(f, &a20_mask); |
109 | 8dd3dca3 | aurel32 | |
110 | 8dd3dca3 | aurel32 | /* XMM */
|
111 | 8dd3dca3 | aurel32 | qemu_put_be32s(f, &env->mxcsr); |
112 | 8dd3dca3 | aurel32 | for(i = 0; i < CPU_NB_REGS; i++) { |
113 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->xmm_regs[i].XMM_Q(0));
|
114 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->xmm_regs[i].XMM_Q(1));
|
115 | 8dd3dca3 | aurel32 | } |
116 | 8dd3dca3 | aurel32 | |
117 | 8dd3dca3 | aurel32 | #ifdef TARGET_X86_64
|
118 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->efer); |
119 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->star); |
120 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->lstar); |
121 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->cstar); |
122 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->fmask); |
123 | 8dd3dca3 | aurel32 | qemu_put_be64s(f, &env->kernelgsbase); |
124 | 8dd3dca3 | aurel32 | #endif
|
125 | 8dd3dca3 | aurel32 | qemu_put_be32s(f, &env->smbase); |
126 | 5cc1d1e6 | bellard | |
127 | 5cc1d1e6 | bellard | qemu_put_be64s(f, &env->pat); |
128 | 5cc1d1e6 | bellard | qemu_put_be32s(f, &env->hflags2); |
129 | 5cc1d1e6 | bellard | |
130 | 5cc1d1e6 | bellard | qemu_put_be64s(f, &env->vm_hsave); |
131 | 5cc1d1e6 | bellard | qemu_put_be64s(f, &env->vm_vmcb); |
132 | 5cc1d1e6 | bellard | qemu_put_be64s(f, &env->tsc_offset); |
133 | 5cc1d1e6 | bellard | qemu_put_be64s(f, &env->intercept); |
134 | 5cc1d1e6 | bellard | qemu_put_be16s(f, &env->intercept_cr_read); |
135 | 5cc1d1e6 | bellard | qemu_put_be16s(f, &env->intercept_cr_write); |
136 | 5cc1d1e6 | bellard | qemu_put_be16s(f, &env->intercept_dr_read); |
137 | 5cc1d1e6 | bellard | qemu_put_be16s(f, &env->intercept_dr_write); |
138 | 5cc1d1e6 | bellard | qemu_put_be32s(f, &env->intercept_exceptions); |
139 | 5cc1d1e6 | bellard | qemu_put_8s(f, &env->v_tpr); |
140 | dd5e3b17 | aliguori | |
141 | dd5e3b17 | aliguori | /* MTRRs */
|
142 | dd5e3b17 | aliguori | for(i = 0; i < 11; i++) |
143 | dd5e3b17 | aliguori | qemu_put_be64s(f, &env->mtrr_fixed[i]); |
144 | dd5e3b17 | aliguori | qemu_put_be64s(f, &env->mtrr_deftype); |
145 | dd5e3b17 | aliguori | for(i = 0; i < 8; i++) { |
146 | dd5e3b17 | aliguori | qemu_put_be64s(f, &env->mtrr_var[i].base); |
147 | dd5e3b17 | aliguori | qemu_put_be64s(f, &env->mtrr_var[i].mask); |
148 | dd5e3b17 | aliguori | } |
149 | 8dd3dca3 | aurel32 | } |
150 | 8dd3dca3 | aurel32 | |
151 | 8dd3dca3 | aurel32 | #ifdef USE_X86LDOUBLE
|
152 | 8dd3dca3 | aurel32 | /* XXX: add that in a FPU generic layer */
|
153 | 8dd3dca3 | aurel32 | union x86_longdouble {
|
154 | 8dd3dca3 | aurel32 | uint64_t mant; |
155 | 8dd3dca3 | aurel32 | uint16_t exp; |
156 | 8dd3dca3 | aurel32 | }; |
157 | 8dd3dca3 | aurel32 | |
158 | 8dd3dca3 | aurel32 | #define MANTD1(fp) (fp & ((1LL << 52) - 1)) |
159 | 8dd3dca3 | aurel32 | #define EXPBIAS1 1023 |
160 | 8dd3dca3 | aurel32 | #define EXPD1(fp) ((fp >> 52) & 0x7FF) |
161 | 8dd3dca3 | aurel32 | #define SIGND1(fp) ((fp >> 32) & 0x80000000) |
162 | 8dd3dca3 | aurel32 | |
163 | 8dd3dca3 | aurel32 | static void fp64_to_fp80(union x86_longdouble *p, uint64_t temp) |
164 | 8dd3dca3 | aurel32 | { |
165 | 8dd3dca3 | aurel32 | int e;
|
166 | 8dd3dca3 | aurel32 | /* mantissa */
|
167 | 8dd3dca3 | aurel32 | p->mant = (MANTD1(temp) << 11) | (1LL << 63); |
168 | 8dd3dca3 | aurel32 | /* exponent + sign */
|
169 | 8dd3dca3 | aurel32 | e = EXPD1(temp) - EXPBIAS1 + 16383;
|
170 | 8dd3dca3 | aurel32 | e |= SIGND1(temp) >> 16;
|
171 | 8dd3dca3 | aurel32 | p->exp = e; |
172 | 8dd3dca3 | aurel32 | } |
173 | 8dd3dca3 | aurel32 | #endif
|
174 | 8dd3dca3 | aurel32 | |
175 | 8dd3dca3 | aurel32 | int cpu_load(QEMUFile *f, void *opaque, int version_id) |
176 | 8dd3dca3 | aurel32 | { |
177 | 8dd3dca3 | aurel32 | CPUState *env = opaque; |
178 | 8dd3dca3 | aurel32 | int i, guess_mmx;
|
179 | 8dd3dca3 | aurel32 | uint32_t hflags; |
180 | 8dd3dca3 | aurel32 | uint16_t fpus, fpuc, fptag, fpregs_format; |
181 | 7caa33f7 | aurel32 | int32_t a20_mask; |
182 | 8dd3dca3 | aurel32 | |
183 | 9656f324 | pbrook | if (version_id != 3 && version_id != 4 && version_id != 5 |
184 | dd5e3b17 | aliguori | && version_id != 6 && version_id != 7 && version_id != 8) |
185 | 8dd3dca3 | aurel32 | return -EINVAL;
|
186 | 8dd3dca3 | aurel32 | for(i = 0; i < CPU_NB_REGS; i++) |
187 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->regs[i]); |
188 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->eip); |
189 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->eflags); |
190 | 8dd3dca3 | aurel32 | qemu_get_be32s(f, &hflags); |
191 | 8dd3dca3 | aurel32 | |
192 | 8dd3dca3 | aurel32 | qemu_get_be16s(f, &fpuc); |
193 | 8dd3dca3 | aurel32 | qemu_get_be16s(f, &fpus); |
194 | 8dd3dca3 | aurel32 | qemu_get_be16s(f, &fptag); |
195 | 8dd3dca3 | aurel32 | qemu_get_be16s(f, &fpregs_format); |
196 | 8dd3dca3 | aurel32 | |
197 | 8dd3dca3 | aurel32 | /* NOTE: we cannot always restore the FPU state if the image come
|
198 | 8dd3dca3 | aurel32 | from a host with a different 'USE_X86LDOUBLE' define. We guess
|
199 | 8dd3dca3 | aurel32 | if we are in an MMX state to restore correctly in that case. */
|
200 | 8dd3dca3 | aurel32 | guess_mmx = ((fptag == 0xff) && (fpus & 0x3800) == 0); |
201 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) { |
202 | 8dd3dca3 | aurel32 | uint64_t mant; |
203 | 8dd3dca3 | aurel32 | uint16_t exp; |
204 | 8dd3dca3 | aurel32 | |
205 | 8dd3dca3 | aurel32 | switch(fpregs_format) {
|
206 | 8dd3dca3 | aurel32 | case 0: |
207 | 8dd3dca3 | aurel32 | mant = qemu_get_be64(f); |
208 | 8dd3dca3 | aurel32 | exp = qemu_get_be16(f); |
209 | 8dd3dca3 | aurel32 | #ifdef USE_X86LDOUBLE
|
210 | 8dd3dca3 | aurel32 | env->fpregs[i].d = cpu_set_fp80(mant, exp); |
211 | 8dd3dca3 | aurel32 | #else
|
212 | 8dd3dca3 | aurel32 | /* difficult case */
|
213 | 8dd3dca3 | aurel32 | if (guess_mmx)
|
214 | 8dd3dca3 | aurel32 | env->fpregs[i].mmx.MMX_Q(0) = mant;
|
215 | 8dd3dca3 | aurel32 | else
|
216 | 8dd3dca3 | aurel32 | env->fpregs[i].d = cpu_set_fp80(mant, exp); |
217 | 8dd3dca3 | aurel32 | #endif
|
218 | 8dd3dca3 | aurel32 | break;
|
219 | 8dd3dca3 | aurel32 | case 1: |
220 | 8dd3dca3 | aurel32 | mant = qemu_get_be64(f); |
221 | 8dd3dca3 | aurel32 | #ifdef USE_X86LDOUBLE
|
222 | 8dd3dca3 | aurel32 | { |
223 | 8dd3dca3 | aurel32 | union x86_longdouble *p;
|
224 | 8dd3dca3 | aurel32 | /* difficult case */
|
225 | 8dd3dca3 | aurel32 | p = (void *)&env->fpregs[i];
|
226 | 8dd3dca3 | aurel32 | if (guess_mmx) {
|
227 | 8dd3dca3 | aurel32 | p->mant = mant; |
228 | 8dd3dca3 | aurel32 | p->exp = 0xffff;
|
229 | 8dd3dca3 | aurel32 | } else {
|
230 | 8dd3dca3 | aurel32 | fp64_to_fp80(p, mant); |
231 | 8dd3dca3 | aurel32 | } |
232 | 8dd3dca3 | aurel32 | } |
233 | 8dd3dca3 | aurel32 | #else
|
234 | 8dd3dca3 | aurel32 | env->fpregs[i].mmx.MMX_Q(0) = mant;
|
235 | 8dd3dca3 | aurel32 | #endif
|
236 | 8dd3dca3 | aurel32 | break;
|
237 | 8dd3dca3 | aurel32 | default:
|
238 | 8dd3dca3 | aurel32 | return -EINVAL;
|
239 | 8dd3dca3 | aurel32 | } |
240 | 8dd3dca3 | aurel32 | } |
241 | 8dd3dca3 | aurel32 | |
242 | 8dd3dca3 | aurel32 | env->fpuc = fpuc; |
243 | 8dd3dca3 | aurel32 | /* XXX: restore FPU round state */
|
244 | 8dd3dca3 | aurel32 | env->fpstt = (fpus >> 11) & 7; |
245 | 8dd3dca3 | aurel32 | env->fpus = fpus & ~0x3800;
|
246 | 8dd3dca3 | aurel32 | fptag ^= 0xff;
|
247 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) { |
248 | 8dd3dca3 | aurel32 | env->fptags[i] = (fptag >> i) & 1;
|
249 | 8dd3dca3 | aurel32 | } |
250 | 8dd3dca3 | aurel32 | |
251 | 8dd3dca3 | aurel32 | for(i = 0; i < 6; i++) |
252 | 8dd3dca3 | aurel32 | cpu_get_seg(f, &env->segs[i]); |
253 | 8dd3dca3 | aurel32 | cpu_get_seg(f, &env->ldt); |
254 | 8dd3dca3 | aurel32 | cpu_get_seg(f, &env->tr); |
255 | 8dd3dca3 | aurel32 | cpu_get_seg(f, &env->gdt); |
256 | 8dd3dca3 | aurel32 | cpu_get_seg(f, &env->idt); |
257 | 8dd3dca3 | aurel32 | |
258 | 8dd3dca3 | aurel32 | qemu_get_be32s(f, &env->sysenter_cs); |
259 | 2436b61a | balrog | if (version_id >= 7) { |
260 | 2436b61a | balrog | qemu_get_betls(f, &env->sysenter_esp); |
261 | 2436b61a | balrog | qemu_get_betls(f, &env->sysenter_eip); |
262 | 2436b61a | balrog | } else {
|
263 | e5ceb244 | aliguori | env->sysenter_esp = qemu_get_be32(f); |
264 | e5ceb244 | aliguori | env->sysenter_eip = qemu_get_be32(f); |
265 | 2436b61a | balrog | } |
266 | 8dd3dca3 | aurel32 | |
267 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->cr[0]);
|
268 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->cr[2]);
|
269 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->cr[3]);
|
270 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->cr[4]);
|
271 | 8dd3dca3 | aurel32 | |
272 | 8dd3dca3 | aurel32 | for(i = 0; i < 8; i++) |
273 | 8dd3dca3 | aurel32 | qemu_get_betls(f, &env->dr[i]); |
274 | 01df040b | aliguori | cpu_breakpoint_remove_all(env, BP_CPU); |
275 | 01df040b | aliguori | cpu_watchpoint_remove_all(env, BP_CPU); |
276 | 01df040b | aliguori | for (i = 0; i < 4; i++) |
277 | 01df040b | aliguori | hw_breakpoint_insert(env, i); |
278 | 8dd3dca3 | aurel32 | |
279 | 8dd3dca3 | aurel32 | /* MMU */
|
280 | b6c4f71f | blueswir1 | qemu_get_sbe32s(f, &a20_mask); |
281 | 7caa33f7 | aurel32 | env->a20_mask = a20_mask; |
282 | 8dd3dca3 | aurel32 | |
283 | 8dd3dca3 | aurel32 | qemu_get_be32s(f, &env->mxcsr); |
284 | 8dd3dca3 | aurel32 | for(i = 0; i < CPU_NB_REGS; i++) { |
285 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->xmm_regs[i].XMM_Q(0));
|
286 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->xmm_regs[i].XMM_Q(1));
|
287 | 8dd3dca3 | aurel32 | } |
288 | 8dd3dca3 | aurel32 | |
289 | 8dd3dca3 | aurel32 | #ifdef TARGET_X86_64
|
290 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->efer); |
291 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->star); |
292 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->lstar); |
293 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->cstar); |
294 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->fmask); |
295 | 8dd3dca3 | aurel32 | qemu_get_be64s(f, &env->kernelgsbase); |
296 | 8dd3dca3 | aurel32 | #endif
|
297 | 5cc1d1e6 | bellard | if (version_id >= 4) { |
298 | 8dd3dca3 | aurel32 | qemu_get_be32s(f, &env->smbase); |
299 | 5cc1d1e6 | bellard | } |
300 | 5cc1d1e6 | bellard | if (version_id >= 5) { |
301 | 5cc1d1e6 | bellard | qemu_get_be64s(f, &env->pat); |
302 | 5cc1d1e6 | bellard | qemu_get_be32s(f, &env->hflags2); |
303 | 9656f324 | pbrook | if (version_id < 6) |
304 | 9656f324 | pbrook | qemu_get_be32s(f, &env->halted); |
305 | 5cc1d1e6 | bellard | |
306 | 5cc1d1e6 | bellard | qemu_get_be64s(f, &env->vm_hsave); |
307 | 5cc1d1e6 | bellard | qemu_get_be64s(f, &env->vm_vmcb); |
308 | 5cc1d1e6 | bellard | qemu_get_be64s(f, &env->tsc_offset); |
309 | 5cc1d1e6 | bellard | qemu_get_be64s(f, &env->intercept); |
310 | 5cc1d1e6 | bellard | qemu_get_be16s(f, &env->intercept_cr_read); |
311 | 5cc1d1e6 | bellard | qemu_get_be16s(f, &env->intercept_cr_write); |
312 | 5cc1d1e6 | bellard | qemu_get_be16s(f, &env->intercept_dr_read); |
313 | 5cc1d1e6 | bellard | qemu_get_be16s(f, &env->intercept_dr_write); |
314 | 5cc1d1e6 | bellard | qemu_get_be32s(f, &env->intercept_exceptions); |
315 | 5cc1d1e6 | bellard | qemu_get_8s(f, &env->v_tpr); |
316 | 5cc1d1e6 | bellard | } |
317 | dd5e3b17 | aliguori | |
318 | dd5e3b17 | aliguori | if (version_id >= 8) { |
319 | dd5e3b17 | aliguori | /* MTRRs */
|
320 | dd5e3b17 | aliguori | for(i = 0; i < 11; i++) |
321 | dd5e3b17 | aliguori | qemu_get_be64s(f, &env->mtrr_fixed[i]); |
322 | dd5e3b17 | aliguori | qemu_get_be64s(f, &env->mtrr_deftype); |
323 | dd5e3b17 | aliguori | for(i = 0; i < 8; i++) { |
324 | dd5e3b17 | aliguori | qemu_get_be64s(f, &env->mtrr_var[i].base); |
325 | dd5e3b17 | aliguori | qemu_get_be64s(f, &env->mtrr_var[i].mask); |
326 | dd5e3b17 | aliguori | } |
327 | dd5e3b17 | aliguori | } |
328 | dd5e3b17 | aliguori | |
329 | 5cc1d1e6 | bellard | /* XXX: ensure compatiblity for halted bit ? */
|
330 | 5cc1d1e6 | bellard | /* XXX: compute redundant hflags bits */
|
331 | 8dd3dca3 | aurel32 | env->hflags = hflags; |
332 | 8dd3dca3 | aurel32 | tlb_flush(env, 1);
|
333 | 8dd3dca3 | aurel32 | return 0; |
334 | 8dd3dca3 | aurel32 | } |