Lines Matching +full:cs +full:- +full:0
2 * x86 SMM helpers (sysemu-only)
22 #include "exec/helper-proto.h"
24 #include "tcg/helper-tcg.h"
30 #define SMM_REVISION_ID 0x00020064
32 #define SMM_REVISION_ID 0x00020000
37 CPUX86State *env = &cpu->env; in do_smm_enter()
38 CPUState *cs = CPU(cpu); in do_smm_enter() local
46 env->msr_smi_count++; in do_smm_enter()
47 env->hflags |= HF_SMM_MASK; in do_smm_enter()
48 if (env->hflags2 & HF2_NMI_MASK) { in do_smm_enter()
49 env->hflags2 |= HF2_SMM_INSIDE_NMI_MASK; in do_smm_enter()
51 env->hflags2 |= HF2_NMI_MASK; in do_smm_enter()
54 sm_state = env->smbase + 0x8000; in do_smm_enter()
57 for (i = 0; i < 6; i++) { in do_smm_enter()
58 dt = &env->segs[i]; in do_smm_enter()
59 offset = 0x7e00 + i * 16; in do_smm_enter()
60 x86_stw_phys(cs, sm_state + offset, dt->selector); in do_smm_enter()
61 x86_stw_phys(cs, sm_state + offset + 2, (dt->flags >> 8) & 0xf0ff); in do_smm_enter()
62 x86_stl_phys(cs, sm_state + offset + 4, dt->limit); in do_smm_enter()
63 x86_stq_phys(cs, sm_state + offset + 8, dt->base); in do_smm_enter()
66 x86_stq_phys(cs, sm_state + 0x7e68, env->gdt.base); in do_smm_enter()
67 x86_stl_phys(cs, sm_state + 0x7e64, env->gdt.limit); in do_smm_enter()
69 x86_stw_phys(cs, sm_state + 0x7e70, env->ldt.selector); in do_smm_enter()
70 x86_stq_phys(cs, sm_state + 0x7e78, env->ldt.base); in do_smm_enter()
71 x86_stl_phys(cs, sm_state + 0x7e74, env->ldt.limit); in do_smm_enter()
72 x86_stw_phys(cs, sm_state + 0x7e72, (env->ldt.flags >> 8) & 0xf0ff); in do_smm_enter()
74 x86_stq_phys(cs, sm_state + 0x7e88, env->idt.base); in do_smm_enter()
75 x86_stl_phys(cs, sm_state + 0x7e84, env->idt.limit); in do_smm_enter()
77 x86_stw_phys(cs, sm_state + 0x7e90, env->tr.selector); in do_smm_enter()
78 x86_stq_phys(cs, sm_state + 0x7e98, env->tr.base); in do_smm_enter()
79 x86_stl_phys(cs, sm_state + 0x7e94, env->tr.limit); in do_smm_enter()
80 x86_stw_phys(cs, sm_state + 0x7e92, (env->tr.flags >> 8) & 0xf0ff); in do_smm_enter()
83 is saved at offset 7ED0. Vol 3, 34.4.1.1, Table 32-2, has in do_smm_enter()
84 7EA0-7ED7 as "reserved". What's this, and what's really in do_smm_enter()
86 x86_stq_phys(cs, sm_state + 0x7ed0, env->efer); in do_smm_enter()
88 x86_stq_phys(cs, sm_state + 0x7ff8, env->regs[R_EAX]); in do_smm_enter()
89 x86_stq_phys(cs, sm_state + 0x7ff0, env->regs[R_ECX]); in do_smm_enter()
90 x86_stq_phys(cs, sm_state + 0x7fe8, env->regs[R_EDX]); in do_smm_enter()
91 x86_stq_phys(cs, sm_state + 0x7fe0, env->regs[R_EBX]); in do_smm_enter()
92 x86_stq_phys(cs, sm_state + 0x7fd8, env->regs[R_ESP]); in do_smm_enter()
93 x86_stq_phys(cs, sm_state + 0x7fd0, env->regs[R_EBP]); in do_smm_enter()
94 x86_stq_phys(cs, sm_state + 0x7fc8, env->regs[R_ESI]); in do_smm_enter()
95 x86_stq_phys(cs, sm_state + 0x7fc0, env->regs[R_EDI]); in do_smm_enter()
97 x86_stq_phys(cs, sm_state + 0x7ff8 - i * 8, env->regs[i]); in do_smm_enter()
99 x86_stq_phys(cs, sm_state + 0x7f78, env->eip); in do_smm_enter()
100 x86_stl_phys(cs, sm_state + 0x7f70, cpu_compute_eflags(env)); in do_smm_enter()
101 x86_stl_phys(cs, sm_state + 0x7f68, env->dr[6]); in do_smm_enter()
102 x86_stl_phys(cs, sm_state + 0x7f60, env->dr[7]); in do_smm_enter()
104 x86_stl_phys(cs, sm_state + 0x7f48, env->cr[4]); in do_smm_enter()
105 x86_stq_phys(cs, sm_state + 0x7f50, env->cr[3]); in do_smm_enter()
106 x86_stl_phys(cs, sm_state + 0x7f58, env->cr[0]); in do_smm_enter()
108 x86_stl_phys(cs, sm_state + 0x7efc, SMM_REVISION_ID); in do_smm_enter()
109 x86_stl_phys(cs, sm_state + 0x7f00, env->smbase); in do_smm_enter()
111 x86_stl_phys(cs, sm_state + 0x7ffc, env->cr[0]); in do_smm_enter()
112 x86_stl_phys(cs, sm_state + 0x7ff8, env->cr[3]); in do_smm_enter()
113 x86_stl_phys(cs, sm_state + 0x7ff4, cpu_compute_eflags(env)); in do_smm_enter()
114 x86_stl_phys(cs, sm_state + 0x7ff0, env->eip); in do_smm_enter()
115 x86_stl_phys(cs, sm_state + 0x7fec, env->regs[R_EDI]); in do_smm_enter()
116 x86_stl_phys(cs, sm_state + 0x7fe8, env->regs[R_ESI]); in do_smm_enter()
117 x86_stl_phys(cs, sm_state + 0x7fe4, env->regs[R_EBP]); in do_smm_enter()
118 x86_stl_phys(cs, sm_state + 0x7fe0, env->regs[R_ESP]); in do_smm_enter()
119 x86_stl_phys(cs, sm_state + 0x7fdc, env->regs[R_EBX]); in do_smm_enter()
120 x86_stl_phys(cs, sm_state + 0x7fd8, env->regs[R_EDX]); in do_smm_enter()
121 x86_stl_phys(cs, sm_state + 0x7fd4, env->regs[R_ECX]); in do_smm_enter()
122 x86_stl_phys(cs, sm_state + 0x7fd0, env->regs[R_EAX]); in do_smm_enter()
123 x86_stl_phys(cs, sm_state + 0x7fcc, env->dr[6]); in do_smm_enter()
124 x86_stl_phys(cs, sm_state + 0x7fc8, env->dr[7]); in do_smm_enter()
126 x86_stl_phys(cs, sm_state + 0x7fc4, env->tr.selector); in do_smm_enter()
127 x86_stl_phys(cs, sm_state + 0x7f64, env->tr.base); in do_smm_enter()
128 x86_stl_phys(cs, sm_state + 0x7f60, env->tr.limit); in do_smm_enter()
129 x86_stl_phys(cs, sm_state + 0x7f5c, (env->tr.flags >> 8) & 0xf0ff); in do_smm_enter()
131 x86_stl_phys(cs, sm_state + 0x7fc0, env->ldt.selector); in do_smm_enter()
132 x86_stl_phys(cs, sm_state + 0x7f80, env->ldt.base); in do_smm_enter()
133 x86_stl_phys(cs, sm_state + 0x7f7c, env->ldt.limit); in do_smm_enter()
134 x86_stl_phys(cs, sm_state + 0x7f78, (env->ldt.flags >> 8) & 0xf0ff); in do_smm_enter()
136 x86_stl_phys(cs, sm_state + 0x7f74, env->gdt.base); in do_smm_enter()
137 x86_stl_phys(cs, sm_state + 0x7f70, env->gdt.limit); in do_smm_enter()
139 x86_stl_phys(cs, sm_state + 0x7f58, env->idt.base); in do_smm_enter()
140 x86_stl_phys(cs, sm_state + 0x7f54, env->idt.limit); in do_smm_enter()
142 for (i = 0; i < 6; i++) { in do_smm_enter()
143 dt = &env->segs[i]; in do_smm_enter()
145 offset = 0x7f84 + i * 12; in do_smm_enter()
147 offset = 0x7f2c + (i - 3) * 12; in do_smm_enter()
149 x86_stl_phys(cs, sm_state + 0x7fa8 + i * 4, dt->selector); in do_smm_enter()
150 x86_stl_phys(cs, sm_state + offset + 8, dt->base); in do_smm_enter()
151 x86_stl_phys(cs, sm_state + offset + 4, dt->limit); in do_smm_enter()
152 x86_stl_phys(cs, sm_state + offset, (dt->flags >> 8) & 0xf0ff); in do_smm_enter()
154 x86_stl_phys(cs, sm_state + 0x7f14, env->cr[4]); in do_smm_enter()
156 x86_stl_phys(cs, sm_state + 0x7efc, SMM_REVISION_ID); in do_smm_enter()
157 x86_stl_phys(cs, sm_state + 0x7ef8, env->smbase); in do_smm_enter()
162 cpu_load_efer(env, 0); in do_smm_enter()
164 cpu_load_eflags(env, 0, ~(CC_O | CC_S | CC_Z | CC_A | CC_P | CC_C | in do_smm_enter()
166 env->eip = 0x00008000; in do_smm_enter()
168 env->cr[0] & ~(CR0_PE_MASK | CR0_EM_MASK | CR0_TS_MASK | in do_smm_enter()
170 cpu_x86_update_cr4(env, 0); in do_smm_enter()
171 env->dr[7] = 0x00000400; in do_smm_enter()
173 cpu_x86_load_seg_cache(env, R_CS, (env->smbase >> 4) & 0xffff, env->smbase, in do_smm_enter()
174 0xffffffff, in do_smm_enter()
177 cpu_x86_load_seg_cache(env, R_DS, 0, 0, 0xffffffff, in do_smm_enter()
180 cpu_x86_load_seg_cache(env, R_ES, 0, 0, 0xffffffff, in do_smm_enter()
183 cpu_x86_load_seg_cache(env, R_SS, 0, 0, 0xffffffff, in do_smm_enter()
186 cpu_x86_load_seg_cache(env, R_FS, 0, 0, 0xffffffff, in do_smm_enter()
189 cpu_x86_load_seg_cache(env, R_GS, 0, 0, 0xffffffff, in do_smm_enter()
197 CPUState *cs = env_cpu(env); in helper_rsm() local
202 sm_state = env->smbase + 0x8000; in helper_rsm()
204 cpu_load_efer(env, x86_ldq_phys(cs, sm_state + 0x7ed0)); in helper_rsm()
206 env->gdt.base = x86_ldq_phys(cs, sm_state + 0x7e68); in helper_rsm()
207 env->gdt.limit = x86_ldl_phys(cs, sm_state + 0x7e64); in helper_rsm()
209 env->ldt.selector = x86_lduw_phys(cs, sm_state + 0x7e70); in helper_rsm()
210 env->ldt.base = x86_ldq_phys(cs, sm_state + 0x7e78); in helper_rsm()
211 env->ldt.limit = x86_ldl_phys(cs, sm_state + 0x7e74); in helper_rsm()
212 env->ldt.flags = (x86_lduw_phys(cs, sm_state + 0x7e72) & 0xf0ff) << 8; in helper_rsm()
214 env->idt.base = x86_ldq_phys(cs, sm_state + 0x7e88); in helper_rsm()
215 env->idt.limit = x86_ldl_phys(cs, sm_state + 0x7e84); in helper_rsm()
217 env->tr.selector = x86_lduw_phys(cs, sm_state + 0x7e90); in helper_rsm()
218 env->tr.base = x86_ldq_phys(cs, sm_state + 0x7e98); in helper_rsm()
219 env->tr.limit = x86_ldl_phys(cs, sm_state + 0x7e94); in helper_rsm()
220 env->tr.flags = (x86_lduw_phys(cs, sm_state + 0x7e92) & 0xf0ff) << 8; in helper_rsm()
222 env->regs[R_EAX] = x86_ldq_phys(cs, sm_state + 0x7ff8); in helper_rsm()
223 env->regs[R_ECX] = x86_ldq_phys(cs, sm_state + 0x7ff0); in helper_rsm()
224 env->regs[R_EDX] = x86_ldq_phys(cs, sm_state + 0x7fe8); in helper_rsm()
225 env->regs[R_EBX] = x86_ldq_phys(cs, sm_state + 0x7fe0); in helper_rsm()
226 env->regs[R_ESP] = x86_ldq_phys(cs, sm_state + 0x7fd8); in helper_rsm()
227 env->regs[R_EBP] = x86_ldq_phys(cs, sm_state + 0x7fd0); in helper_rsm()
228 env->regs[R_ESI] = x86_ldq_phys(cs, sm_state + 0x7fc8); in helper_rsm()
229 env->regs[R_EDI] = x86_ldq_phys(cs, sm_state + 0x7fc0); in helper_rsm()
231 env->regs[i] = x86_ldq_phys(cs, sm_state + 0x7ff8 - i * 8); in helper_rsm()
233 env->eip = x86_ldq_phys(cs, sm_state + 0x7f78); in helper_rsm()
234 cpu_load_eflags(env, x86_ldl_phys(cs, sm_state + 0x7f70), in helper_rsm()
236 env->dr[6] = x86_ldl_phys(cs, sm_state + 0x7f68); in helper_rsm()
237 env->dr[7] = x86_ldl_phys(cs, sm_state + 0x7f60); in helper_rsm()
239 cpu_x86_update_cr4(env, x86_ldl_phys(cs, sm_state + 0x7f48)); in helper_rsm()
240 cpu_x86_update_cr3(env, x86_ldq_phys(cs, sm_state + 0x7f50)); in helper_rsm()
241 cpu_x86_update_cr0(env, x86_ldl_phys(cs, sm_state + 0x7f58)); in helper_rsm()
243 for (i = 0; i < 6; i++) { in helper_rsm()
244 offset = 0x7e00 + i * 16; in helper_rsm()
246 x86_lduw_phys(cs, sm_state + offset), in helper_rsm()
247 x86_ldq_phys(cs, sm_state + offset + 8), in helper_rsm()
248 x86_ldl_phys(cs, sm_state + offset + 4), in helper_rsm()
249 (x86_lduw_phys(cs, sm_state + offset + 2) & in helper_rsm()
250 0xf0ff) << 8); in helper_rsm()
253 val = x86_ldl_phys(cs, sm_state + 0x7efc); /* revision ID */ in helper_rsm()
254 if (val & 0x20000) { in helper_rsm()
255 env->smbase = x86_ldl_phys(cs, sm_state + 0x7f00); in helper_rsm()
258 cpu_x86_update_cr0(env, x86_ldl_phys(cs, sm_state + 0x7ffc)); in helper_rsm()
259 cpu_x86_update_cr3(env, x86_ldl_phys(cs, sm_state + 0x7ff8)); in helper_rsm()
260 cpu_load_eflags(env, x86_ldl_phys(cs, sm_state + 0x7ff4), in helper_rsm()
262 env->eip = x86_ldl_phys(cs, sm_state + 0x7ff0); in helper_rsm()
263 env->regs[R_EDI] = x86_ldl_phys(cs, sm_state + 0x7fec); in helper_rsm()
264 env->regs[R_ESI] = x86_ldl_phys(cs, sm_state + 0x7fe8); in helper_rsm()
265 env->regs[R_EBP] = x86_ldl_phys(cs, sm_state + 0x7fe4); in helper_rsm()
266 env->regs[R_ESP] = x86_ldl_phys(cs, sm_state + 0x7fe0); in helper_rsm()
267 env->regs[R_EBX] = x86_ldl_phys(cs, sm_state + 0x7fdc); in helper_rsm()
268 env->regs[R_EDX] = x86_ldl_phys(cs, sm_state + 0x7fd8); in helper_rsm()
269 env->regs[R_ECX] = x86_ldl_phys(cs, sm_state + 0x7fd4); in helper_rsm()
270 env->regs[R_EAX] = x86_ldl_phys(cs, sm_state + 0x7fd0); in helper_rsm()
271 env->dr[6] = x86_ldl_phys(cs, sm_state + 0x7fcc); in helper_rsm()
272 env->dr[7] = x86_ldl_phys(cs, sm_state + 0x7fc8); in helper_rsm()
274 env->tr.selector = x86_ldl_phys(cs, sm_state + 0x7fc4) & 0xffff; in helper_rsm()
275 env->tr.base = x86_ldl_phys(cs, sm_state + 0x7f64); in helper_rsm()
276 env->tr.limit = x86_ldl_phys(cs, sm_state + 0x7f60); in helper_rsm()
277 env->tr.flags = (x86_ldl_phys(cs, sm_state + 0x7f5c) & 0xf0ff) << 8; in helper_rsm()
279 env->ldt.selector = x86_ldl_phys(cs, sm_state + 0x7fc0) & 0xffff; in helper_rsm()
280 env->ldt.base = x86_ldl_phys(cs, sm_state + 0x7f80); in helper_rsm()
281 env->ldt.limit = x86_ldl_phys(cs, sm_state + 0x7f7c); in helper_rsm()
282 env->ldt.flags = (x86_ldl_phys(cs, sm_state + 0x7f78) & 0xf0ff) << 8; in helper_rsm()
284 env->gdt.base = x86_ldl_phys(cs, sm_state + 0x7f74); in helper_rsm()
285 env->gdt.limit = x86_ldl_phys(cs, sm_state + 0x7f70); in helper_rsm()
287 env->idt.base = x86_ldl_phys(cs, sm_state + 0x7f58); in helper_rsm()
288 env->idt.limit = x86_ldl_phys(cs, sm_state + 0x7f54); in helper_rsm()
290 for (i = 0; i < 6; i++) { in helper_rsm()
292 offset = 0x7f84 + i * 12; in helper_rsm()
294 offset = 0x7f2c + (i - 3) * 12; in helper_rsm()
297 x86_ldl_phys(cs, in helper_rsm()
298 sm_state + 0x7fa8 + i * 4) & 0xffff, in helper_rsm()
299 x86_ldl_phys(cs, sm_state + offset + 8), in helper_rsm()
300 x86_ldl_phys(cs, sm_state + offset + 4), in helper_rsm()
301 (x86_ldl_phys(cs, in helper_rsm()
302 sm_state + offset) & 0xf0ff) << 8); in helper_rsm()
304 cpu_x86_update_cr4(env, x86_ldl_phys(cs, sm_state + 0x7f14)); in helper_rsm()
306 val = x86_ldl_phys(cs, sm_state + 0x7efc); /* revision ID */ in helper_rsm()
307 if (val & 0x20000) { in helper_rsm()
308 env->smbase = x86_ldl_phys(cs, sm_state + 0x7ef8); in helper_rsm()
311 if ((env->hflags2 & HF2_SMM_INSIDE_NMI_MASK) == 0) { in helper_rsm()
312 env->hflags2 &= ~HF2_NMI_MASK; in helper_rsm()
314 env->hflags2 &= ~HF2_SMM_INSIDE_NMI_MASK; in helper_rsm()
315 env->hflags &= ~HF_SMM_MASK; in helper_rsm()