VirtualBox

source: vbox/trunk/include/VBox/cpum.h@ 3810

Last change on this file since 3810 was 3632, checked in by vboxsync, 17 years ago

VBox_hdr_h -> _VBox_hdr_h

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 24.5 KB
Line 
1/** @file
2 * CPUM - CPU Monitor(/ Manager).
3 */
4
5/*
6 * Copyright (C) 2006-2007 innotek GmbH
7 *
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.virtualbox.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License as published by the Free Software Foundation,
12 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
13 * distribution. VirtualBox OSE is distributed in the hope that it will
14 * be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * If you received this file as part of a commercial VirtualBox
17 * distribution, then only the terms of your commercial VirtualBox
18 * license agreement apply instead of the previous paragraph.
19 */
20
21#ifndef ___VBox_cpum_h
22#define ___VBox_cpum_h
23
24#include <VBox/cdefs.h>
25#include <VBox/types.h>
26#include <VBox/x86.h>
27
28
29__BEGIN_DECLS
30
31/** @defgroup grp_cpum The CPU Monitor(/Manager) API
32 * @{
33 */
34
35/**
36 * Selector hidden registers.
37 */
38typedef struct CPUMSELREGHIDDEN
39{
40 /** Base register. */
41 uint32_t u32Base;
42 /** Limit (expanded). */
43 uint32_t u32Limit;
44 /** Flags.
45 * This is the high 32-bit word of the descriptor entry.
46 * Only the flags, dpl and type are used. */
47 X86DESCATTR Attr;
48} CPUMSELREGHID;
49/** Pointer to selector hidden registers. */
50typedef CPUMSELREGHID *PCPUMSELREGHID;
51/** Pointer to const selector hidden registers. */
52typedef const CPUMSELREGHID *PCCPUMSELREGHID;
53
54
55/**
56 * The sysenter register set.
57 */
58typedef struct CPUMSYSENTER
59{
60 /** Ring 0 cs.
61 * This value + 8 is the Ring 0 ss.
62 * This value + 16 is the Ring 3 cs.
63 * This value + 24 is the Ring 3 ss.
64 */
65 uint64_t cs;
66 /** Ring 0 eip. */
67 uint64_t eip;
68 /** Ring 0 esp. */
69 uint64_t esp;
70} CPUMSYSENTER;
71
72
73/**
74 * CPU context core.
75 */
76#pragma pack(1)
77typedef struct CPUMCTXCORE
78{
79 uint32_t edi;
80 uint32_t esi;
81 uint32_t ebp;
82 uint32_t eax;
83 uint32_t ebx;
84 uint32_t edx;
85 uint32_t ecx;
86
87 uint32_t esp;
88 RTSEL ss;
89 RTSEL ssPadding;
90
91 RTSEL gs;
92 RTSEL gsPadding;
93 RTSEL fs;
94 RTSEL fsPadding;
95 RTSEL es;
96 RTSEL esPadding;
97 RTSEL ds;
98 RTSEL dsPadding;
99 RTSEL cs;
100 RTSEL csPadding;
101
102 X86EFLAGS eflags;
103 uint32_t eip;
104
105 /** Hidden selector registers.
106 * @{ */
107 CPUMSELREGHID esHid;
108 CPUMSELREGHID csHid;
109 CPUMSELREGHID ssHid;
110 CPUMSELREGHID dsHid;
111 CPUMSELREGHID fsHid;
112 CPUMSELREGHID gsHid;
113 /** @} */
114
115} CPUMCTXCORE;
116/** Pointer to CPU context core. */
117typedef CPUMCTXCORE *PCPUMCTXCORE;
118/** Pointer to const CPU context core. */
119typedef const CPUMCTXCORE *PCCPUMCTXCORE;
120#pragma pack()
121
122/**
123 * CPU context.
124 */
125#pragma pack(1)
126typedef struct CPUMCTX
127{
128 /** FPU state. (16-byte alignment)
129 * @todo This doesn't have to be in X86FXSTATE on CPUs without fxsr - we need a type for the
130 * actual format or convert it (waste of time). */
131 X86FXSTATE fpu;
132
133 /** CPUMCTXCORE Part.
134 * @{ */
135 uint32_t edi;
136 uint32_t esi;
137 uint32_t ebp;
138 uint32_t eax;
139 uint32_t ebx;
140 uint32_t edx;
141 uint32_t ecx;
142
143 uint32_t esp;
144 RTSEL ss;
145 RTSEL ssPadding;
146
147 RTSEL gs;
148 RTSEL gsPadding;
149 RTSEL fs;
150 RTSEL fsPadding;
151 RTSEL es;
152 RTSEL esPadding;
153 RTSEL ds;
154 RTSEL dsPadding;
155 RTSEL cs;
156 RTSEL csPadding;
157
158 X86EFLAGS eflags;
159 uint32_t eip;
160
161 /** Hidden selector registers.
162 * @{ */
163 CPUMSELREGHID esHid;
164 CPUMSELREGHID csHid;
165 CPUMSELREGHID ssHid;
166 CPUMSELREGHID dsHid;
167 CPUMSELREGHID fsHid;
168 CPUMSELREGHID gsHid;
169 /** @} */
170
171 /** @} */
172
173 /** Control registers.
174 * @{ */
175 uint32_t cr0;
176 uint32_t cr2;
177 uint32_t cr3;
178 uint32_t cr4;
179 /** @} */
180
181 /** Debug registers.
182 * @{ */
183 uint32_t dr0;
184 uint32_t dr1;
185 uint32_t dr2;
186 uint32_t dr3;
187 uint32_t dr4; /**< @todo remove dr4 and dr5. */
188 uint32_t dr5;
189 uint32_t dr6;
190 uint32_t dr7;
191 /** @} */
192
193 /** Global Descriptor Table register. */
194 VBOXGDTR gdtr;
195 uint16_t gdtrPadding;
196 uint32_t gdtrPadding64;/** @todo fix this hack */
197 /** Interrupt Descriptor Table register. */
198 VBOXIDTR idtr;
199 uint16_t idtrPadding;
200 uint32_t idtrPadding64;/** @todo fix this hack */
201 /** The task register.
202 * Only the guest context uses all the members. */
203 RTSEL ldtr;
204 RTSEL ldtrPadding;
205 /** The task register.
206 * Only the guest context uses all the members. */
207 RTSEL tr;
208 RTSEL trPadding;
209
210 /** The sysenter msr registers.
211 * This member is not used by the hypervisor context. */
212 CPUMSYSENTER SysEnter;
213
214 /** Hidden selector registers.
215 * @{ */
216 CPUMSELREGHID ldtrHid;
217 CPUMSELREGHID trHid;
218 /** @} */
219
220 /* padding to get 32byte aligned size */
221 uint32_t padding[6];
222} CPUMCTX;
223#pragma pack()
224/** Pointer to CPUMCTX. */
225typedef CPUMCTX *PCPUMCTX;
226
227/**
228 * Gets the CPUMCTXCORE part of a CPUMCTX.
229 */
230#define CPUMCTX2CORE(pCtx) ((PCPUMCTXCORE)(void *)&(pCtx)->edi)
231
232/**
233 * The register set returned by a CPUID operation.
234 */
235typedef struct CPUMCPUID
236{
237 uint32_t eax;
238 uint32_t ebx;
239 uint32_t ecx;
240 uint32_t edx;
241} CPUMCPUID;
242/** Pointer to a CPUID leaf. */
243typedef CPUMCPUID *PCPUMCPUID;
244/** Pointer to a const CPUID leaf. */
245typedef const CPUMCPUID *PCCPUMCPUID;
246
247/**
248 * CPUID feature to set or clear.
249 */
250typedef enum CPUMCPUIDFEATURE
251{
252 CPUMCPUIDFEATURE_INVALID = 0,
253 /** The APIC feature bit. (Std+Ext) */
254 CPUMCPUIDFEATURE_APIC,
255 /** The sysenter/sysexit feature bit. (Std+Ext) */
256 CPUMCPUIDFEATURE_SEP
257} CPUMCPUIDFEATURE;
258
259
260/** @name Guest Register Getters.
261 * @{ */
262CPUMDECL(void) CPUMGetGuestGDTR(PVM pVM, PVBOXGDTR pGDTR);
263CPUMDECL(uint32_t) CPUMGetGuestIDTR(PVM pVM, uint16_t *pcbLimit);
264CPUMDECL(RTSEL) CPUMGetGuestTR(PVM pVM);
265CPUMDECL(RTSEL) CPUMGetGuestLDTR(PVM pVM);
266CPUMDECL(uint32_t) CPUMGetGuestCR0(PVM pVM);
267CPUMDECL(uint32_t) CPUMGetGuestCR2(PVM pVM);
268CPUMDECL(uint32_t) CPUMGetGuestCR3(PVM pVM);
269CPUMDECL(uint32_t) CPUMGetGuestCR4(PVM pVM);
270CPUMDECL(int) CPUMGetGuestCRx(PVM pVM, uint32_t iReg, uint32_t *pValue);
271CPUMDECL(uint32_t) CPUMGetGuestEFlags(PVM pVM);
272CPUMDECL(uint32_t) CPUMGetGuestEIP(PVM pVM);
273CPUMDECL(uint32_t) CPUMGetGuestEAX(PVM pVM);
274CPUMDECL(uint32_t) CPUMGetGuestEBX(PVM pVM);
275CPUMDECL(uint32_t) CPUMGetGuestECX(PVM pVM);
276CPUMDECL(uint32_t) CPUMGetGuestEDX(PVM pVM);
277CPUMDECL(uint32_t) CPUMGetGuestESI(PVM pVM);
278CPUMDECL(uint32_t) CPUMGetGuestEDI(PVM pVM);
279CPUMDECL(uint32_t) CPUMGetGuestESP(PVM pVM);
280CPUMDECL(uint32_t) CPUMGetGuestEBP(PVM pVM);
281CPUMDECL(RTSEL) CPUMGetGuestCS(PVM pVM);
282CPUMDECL(RTSEL) CPUMGetGuestDS(PVM pVM);
283CPUMDECL(RTSEL) CPUMGetGuestES(PVM pVM);
284CPUMDECL(RTSEL) CPUMGetGuestFS(PVM pVM);
285CPUMDECL(RTSEL) CPUMGetGuestGS(PVM pVM);
286CPUMDECL(RTSEL) CPUMGetGuestSS(PVM pVM);
287CPUMDECL(RTUINTREG) CPUMGetGuestDR0(PVM pVM);
288CPUMDECL(RTUINTREG) CPUMGetGuestDR1(PVM pVM);
289CPUMDECL(RTUINTREG) CPUMGetGuestDR2(PVM pVM);
290CPUMDECL(RTUINTREG) CPUMGetGuestDR3(PVM pVM);
291CPUMDECL(RTUINTREG) CPUMGetGuestDR6(PVM pVM);
292CPUMDECL(RTUINTREG) CPUMGetGuestDR7(PVM pVM);
293CPUMDECL(int) CPUMGetGuestDRx(PVM pVM, uint32_t iReg, uint32_t *pValue);
294CPUMDECL(void) CPUMGetGuestCpuId(PVM pVM, uint32_t iLeaf, uint32_t *pEax, uint32_t *pEbx, uint32_t *pEcx, uint32_t *pEdx);
295CPUMDECL(GCPTRTYPE(PCCPUMCPUID)) CPUMGetGuestCpuIdStdGCPtr(PVM pVM);
296CPUMDECL(GCPTRTYPE(PCCPUMCPUID)) CPUMGetGuestCpuIdExtGCPtr(PVM pVM);
297CPUMDECL(GCPTRTYPE(PCCPUMCPUID)) CPUMGetGuestCpuIdDefGCPtr(PVM pVM);
298CPUMDECL(uint32_t) CPUMGetGuestCpuIdStdMax(PVM pVM);
299CPUMDECL(uint32_t) CPUMGetGuestCpuIdExtMax(PVM pVM);
300CPUMDECL(CPUMSELREGHID *) CPUMGetGuestTRHid(PVM pVM);
301/** @} */
302
303/** @name Guest Register Setters.
304 * @{ */
305CPUMDECL(int) CPUMSetGuestGDTR(PVM pVM, uint32_t addr, uint16_t limit);
306CPUMDECL(int) CPUMSetGuestIDTR(PVM pVM, uint32_t addr, uint16_t limit);
307CPUMDECL(int) CPUMSetGuestTR(PVM pVM, uint16_t tr);
308CPUMDECL(int) CPUMSetGuestLDTR(PVM pVM, uint16_t ldtr);
309CPUMDECL(int) CPUMSetGuestCR0(PVM pVM, uint32_t cr0);
310CPUMDECL(int) CPUMSetGuestCR2(PVM pVM, uint32_t cr2);
311CPUMDECL(int) CPUMSetGuestCR3(PVM pVM, uint32_t cr3);
312CPUMDECL(int) CPUMSetGuestCR4(PVM pVM, uint32_t cr4);
313CPUMDECL(int) CPUMSetGuestCRx(PVM pVM, uint32_t iReg, uint32_t Value);
314CPUMDECL(int) CPUMSetGuestDR0(PVM pVM, RTGCUINTREG uDr0);
315CPUMDECL(int) CPUMSetGuestDR1(PVM pVM, RTGCUINTREG uDr1);
316CPUMDECL(int) CPUMSetGuestDR2(PVM pVM, RTGCUINTREG uDr2);
317CPUMDECL(int) CPUMSetGuestDR3(PVM pVM, RTGCUINTREG uDr3);
318CPUMDECL(int) CPUMSetGuestDR6(PVM pVM, RTGCUINTREG uDr6);
319CPUMDECL(int) CPUMSetGuestDR7(PVM pVM, RTGCUINTREG uDr7);
320CPUMDECL(int) CPUMSetGuestDRx(PVM pVM, uint32_t iReg, uint32_t Value);
321CPUMDECL(int) CPUMSetGuestEFlags(PVM pVM, uint32_t eflags);
322CPUMDECL(int) CPUMSetGuestEIP(PVM pVM, uint32_t eip);
323CPUMDECL(int) CPUMSetGuestEAX(PVM pVM, uint32_t eax);
324CPUMDECL(int) CPUMSetGuestEBX(PVM pVM, uint32_t ebx);
325CPUMDECL(int) CPUMSetGuestECX(PVM pVM, uint32_t ecx);
326CPUMDECL(int) CPUMSetGuestEDX(PVM pVM, uint32_t edx);
327CPUMDECL(int) CPUMSetGuestESI(PVM pVM, uint32_t esi);
328CPUMDECL(int) CPUMSetGuestEDI(PVM pVM, uint32_t edi);
329CPUMDECL(int) CPUMSetGuestESP(PVM pVM, uint32_t esp);
330CPUMDECL(int) CPUMSetGuestEBP(PVM pVM, uint32_t ebp);
331CPUMDECL(int) CPUMSetGuestCS(PVM pVM, uint16_t cs);
332CPUMDECL(int) CPUMSetGuestDS(PVM pVM, uint16_t ds);
333CPUMDECL(int) CPUMSetGuestES(PVM pVM, uint16_t es);
334CPUMDECL(int) CPUMSetGuestFS(PVM pVM, uint16_t fs);
335CPUMDECL(int) CPUMSetGuestGS(PVM pVM, uint16_t gs);
336CPUMDECL(int) CPUMSetGuestSS(PVM pVM, uint16_t ss);
337CPUMDECL(void) CPUMSetGuestCpuIdFeature(PVM pVM, CPUMCPUIDFEATURE enmFeature);
338CPUMDECL(void) CPUMClearGuestCpuIdFeature(PVM pVM, CPUMCPUIDFEATURE enmFeature);
339CPUMDECL(void) CPUMSetGuestCtx(PVM pVM, const PCPUMCTX pCtx);
340/** @} */
341
342/** @name Misc Guest Predicate Functions.
343 * @{ */
344
345/**
346 * Tests if the guest is running in real mode or not.
347 *
348 * @returns true if in real mode, otherwise false.
349 * @param pVM The VM handle.
350 */
351DECLINLINE(bool) CPUMIsGuestInRealMode(PVM pVM)
352{
353 return !(CPUMGetGuestCR0(pVM) & X86_CR0_PE);
354}
355
356/**
357 * Tests if the guest is running in protected or not.
358 *
359 * @returns true if in protected mode, otherwise false.
360 * @param pVM The VM handle.
361 */
362DECLINLINE(bool) CPUMIsGuestInProtectedMode(PVM pVM)
363{
364 return !!(CPUMGetGuestCR0(pVM) & X86_CR0_PE);
365}
366
367/**
368 * Tests if the guest is running in paged protected or not.
369 *
370 * @returns true if in paged protected mode, otherwise false.
371 * @param pVM The VM handle.
372 */
373DECLINLINE(bool) CPUMIsGuestInPagedProtectedMode(PVM pVM)
374{
375 return (CPUMGetGuestCR0(pVM) & (X86_CR0_PE | X86_CR0_PG)) == (X86_CR0_PE | X86_CR0_PG);
376}
377
378/**
379 * Tests if the guest is running in paged protected or not.
380 *
381 * @returns true if in paged protected mode, otherwise false.
382 * @param pVM The VM handle.
383 */
384CPUMDECL(bool) CPUMIsGuestIn16BitCode(PVM pVM);
385
386/**
387 * Tests if the guest is running in paged protected or not.
388 *
389 * @returns true if in paged protected mode, otherwise false.
390 * @param pVM The VM handle.
391 */
392CPUMDECL(bool) CPUMIsGuestIn32BitCode(PVM pVM);
393
394/**
395 * Tests if the guest is running in paged protected or not.
396 *
397 * @returns true if in paged protected mode, otherwise false.
398 * @param pVM The VM handle.
399 */
400CPUMDECL(bool) CPUMIsGuestIn64BitCode(PVM pVM);
401
402/** @} */
403
404
405
406/** @name Hypervisor Register Getters.
407 * @{ */
408CPUMDECL(RTSEL) CPUMGetHyperCS(PVM pVM);
409CPUMDECL(RTSEL) CPUMGetHyperDS(PVM pVM);
410CPUMDECL(RTSEL) CPUMGetHyperES(PVM pVM);
411CPUMDECL(RTSEL) CPUMGetHyperFS(PVM pVM);
412CPUMDECL(RTSEL) CPUMGetHyperGS(PVM pVM);
413CPUMDECL(RTSEL) CPUMGetHyperSS(PVM pVM);
414#if 0 /* these are not correct. */
415CPUMDECL(uint32_t) CPUMGetHyperCR0(PVM pVM);
416CPUMDECL(uint32_t) CPUMGetHyperCR2(PVM pVM);
417CPUMDECL(uint32_t) CPUMGetHyperCR3(PVM pVM);
418CPUMDECL(uint32_t) CPUMGetHyperCR4(PVM pVM);
419#endif
420/** This register is only saved on fatal traps. */
421CPUMDECL(uint32_t) CPUMGetHyperEAX(PVM pVM);
422CPUMDECL(uint32_t) CPUMGetHyperEBX(PVM pVM);
423/** This register is only saved on fatal traps. */
424CPUMDECL(uint32_t) CPUMGetHyperECX(PVM pVM);
425/** This register is only saved on fatal traps. */
426CPUMDECL(uint32_t) CPUMGetHyperEDX(PVM pVM);
427CPUMDECL(uint32_t) CPUMGetHyperESI(PVM pVM);
428CPUMDECL(uint32_t) CPUMGetHyperEDI(PVM pVM);
429CPUMDECL(uint32_t) CPUMGetHyperEBP(PVM pVM);
430CPUMDECL(uint32_t) CPUMGetHyperESP(PVM pVM);
431CPUMDECL(uint32_t) CPUMGetHyperEFlags(PVM pVM);
432CPUMDECL(uint32_t) CPUMGetHyperEIP(PVM pVM);
433CPUMDECL(uint32_t) CPUMGetHyperIDTR(PVM pVM, uint16_t *pcbLimit);
434CPUMDECL(uint32_t) CPUMGetHyperGDTR(PVM pVM, uint16_t *pcbLimit);
435CPUMDECL(RTSEL) CPUMGetHyperLDTR(PVM pVM);
436CPUMDECL(RTGCUINTREG) CPUMGetHyperDR0(PVM pVM);
437CPUMDECL(RTGCUINTREG) CPUMGetHyperDR1(PVM pVM);
438CPUMDECL(RTGCUINTREG) CPUMGetHyperDR2(PVM pVM);
439CPUMDECL(RTGCUINTREG) CPUMGetHyperDR3(PVM pVM);
440CPUMDECL(RTGCUINTREG) CPUMGetHyperDR6(PVM pVM);
441CPUMDECL(RTGCUINTREG) CPUMGetHyperDR7(PVM pVM);
442CPUMDECL(void) CPUMGetHyperCtx(PVM pVM, PCPUMCTX pCtx);
443/** @} */
444
445/** @name Hypervisor Register Setters.
446 * @{ */
447CPUMDECL(void) CPUMSetHyperGDTR(PVM pVM, uint32_t addr, uint16_t limit);
448CPUMDECL(void) CPUMSetHyperLDTR(PVM pVM, RTSEL SelLDTR);
449CPUMDECL(void) CPUMSetHyperIDTR(PVM pVM, uint32_t addr, uint16_t limit);
450CPUMDECL(void) CPUMSetHyperCR3(PVM pVM, uint32_t cr3);
451CPUMDECL(void) CPUMSetHyperTR(PVM pVM, RTSEL SelTR);
452CPUMDECL(void) CPUMSetHyperCS(PVM pVM, RTSEL SelCS);
453CPUMDECL(void) CPUMSetHyperDS(PVM pVM, RTSEL SelDS);
454CPUMDECL(void) CPUMSetHyperES(PVM pVM, RTSEL SelDS);
455CPUMDECL(void) CPUMSetHyperFS(PVM pVM, RTSEL SelDS);
456CPUMDECL(void) CPUMSetHyperGS(PVM pVM, RTSEL SelDS);
457CPUMDECL(void) CPUMSetHyperSS(PVM pVM, RTSEL SelSS);
458CPUMDECL(void) CPUMSetHyperESP(PVM pVM, uint32_t u32ESP);
459CPUMDECL(int) CPUMSetHyperEFlags(PVM pVM, uint32_t Efl);
460CPUMDECL(void) CPUMSetHyperEIP(PVM pVM, uint32_t u32EIP);
461CPUMDECL(void) CPUMSetHyperDR0(PVM pVM, RTGCUINTREG uDr0);
462CPUMDECL(void) CPUMSetHyperDR1(PVM pVM, RTGCUINTREG uDr1);
463CPUMDECL(void) CPUMSetHyperDR2(PVM pVM, RTGCUINTREG uDr2);
464CPUMDECL(void) CPUMSetHyperDR3(PVM pVM, RTGCUINTREG uDr3);
465CPUMDECL(void) CPUMSetHyperDR6(PVM pVM, RTGCUINTREG uDr6);
466CPUMDECL(void) CPUMSetHyperDR7(PVM pVM, RTGCUINTREG uDr7);
467CPUMDECL(void) CPUMSetHyperCtx(PVM pVM, const PCPUMCTX pCtx);
468CPUMDECL(int) CPUMRecalcHyperDRx(PVM pVM);
469/** @} */
470
471CPUMDECL(void) CPUMPushHyper(PVM pVM, uint32_t u32);
472
473/**
474 * Sets or resets an alternative hypervisor context core.
475 *
476 * This is called when we get a hypervisor trap set switch the context
477 * core with the trap frame on the stack. It is called again to reset
478 * back to the default context core when resuming hypervisor execution.
479 *
480 * @param pVM The VM handle.
481 * @param pCtxCore Pointer to the alternative context core or NULL
482 * to go back to the default context core.
483 */
484CPUMDECL(void) CPUMHyperSetCtxCore(PVM pVM, PCPUMCTXCORE pCtxCore);
485
486
487/**
488 * Queries the pointer to the internal CPUMCTX structure
489 *
490 * @returns VBox status code.
491 * @param pVM Handle to the virtual machine.
492 * @param ppCtx Receives the CPUMCTX pointer when successful.
493 */
494CPUMDECL(int) CPUMQueryGuestCtxPtr(PVM pVM, PCPUMCTX *ppCtx);
495
496/**
497 * Queries the pointer to the internal CPUMCTX structure for the hypervisor.
498 *
499 * @returns VBox status code.
500 * @param pVM Handle to the virtual machine.
501 * @param ppCtx Receives the hyper CPUMCTX pointer when successful.
502 */
503CPUMDECL(int) CPUMQueryHyperCtxPtr(PVM pVM, PCPUMCTX *ppCtx);
504
505
506/**
507 * Gets the pointer to the internal CPUMCTXCORE structure.
508 * This is only for reading in order to save a few calls.
509 *
510 * @param pVM Handle to the virtual machine.
511 */
512CPUMDECL(PCCPUMCTXCORE) CPUMGetGuestCtxCore(PVM pVM);
513
514/**
515 * Gets the pointer to the internal CPUMCTXCORE structure for the hypervisor.
516 * This is only for reading in order to save a few calls.
517 *
518 * @param pVM Handle to the virtual machine.
519 */
520CPUMDECL(PCCPUMCTXCORE) CPUMGetHyperCtxCore(PVM pVM);
521
522/**
523 * Sets the guest context core registers.
524 *
525 * @param pVM Handle to the virtual machine.
526 * @param pCtxCore The new context core values.
527 */
528CPUMDECL(void) CPUMSetGuestCtxCore(PVM pVM, PCCPUMCTXCORE pCtxCore);
529
530
531/**
532 * Transforms the guest CPU state to raw-ring mode.
533 *
534 * This function will change the any of the cs and ss register with DPL=0 to DPL=1.
535 *
536 * @returns VBox status. (recompiler failure)
537 * @param pVM VM handle.
538 * @param pCtxCore The context core (for trap usage).
539 * @see @ref pg_raw
540 */
541CPUMDECL(int) CPUMRawEnter(PVM pVM, PCPUMCTXCORE pCtxCore);
542
543/**
544 * Transforms the guest CPU state from raw-ring mode to correct values.
545 *
546 * This function will change any selector registers with DPL=1 to DPL=0.
547 *
548 * @returns Adjusted rc.
549 * @param pVM VM handle.
550 * @param rc Raw mode return code
551 * @param pCtxCore The context core (for trap usage).
552 * @see @ref pg_raw
553 */
554CPUMDECL(int) CPUMRawLeave(PVM pVM, PCPUMCTXCORE pCtxCore, int rc);
555
556/**
557 * Gets the EFLAGS while we're in raw-mode.
558 *
559 * @returns The eflags.
560 * @param pVM The VM handle.
561 * @param pCtxCore The context core.
562 */
563CPUMDECL(uint32_t) CPUMRawGetEFlags(PVM pVM, PCPUMCTXCORE pCtxCore);
564
565/**
566 * Updates the EFLAGS while we're in raw-mode.
567 *
568 * @param pVM The VM handle.
569 * @param pCtxCore The context core.
570 * @param eflags The new EFLAGS value.
571 */
572CPUMDECL(void) CPUMRawSetEFlags(PVM pVM, PCPUMCTXCORE pCtxCore, uint32_t eflags);
573
574/**
575 * Lazily sync in the FPU/XMM state
576 *
577 * This function will change any selector registers with DPL=1 to DPL=0.
578 *
579 * @returns VBox status code.
580 * @param pVM VM handle.
581 */
582CPUMDECL(int) CPUMHandleLazyFPU(PVM pVM);
583
584
585/**
586 * Restore host FPU/XMM state
587 *
588 * @returns VBox status code.
589 * @param pVM VM handle.
590 */
591CPUMDECL(int) CPUMRestoreHostFPUState(PVM pVM);
592
593/** @name Changed flags
594 * These flags are used to keep track of which important register that
595 * have been changed since last they were reset. The only one allowed
596 * to clear them is REM!
597 * @{
598 */
599#define CPUM_CHANGED_FPU_REM BIT(0)
600#define CPUM_CHANGED_CR0 BIT(1)
601#define CPUM_CHANGED_CR4 BIT(2)
602#define CPUM_CHANGED_GLOBAL_TLB_FLUSH BIT(3)
603#define CPUM_CHANGED_CR3 BIT(4)
604#define CPUM_CHANGED_GDTR BIT(5)
605#define CPUM_CHANGED_IDTR BIT(6)
606#define CPUM_CHANGED_LDTR BIT(7)
607#define CPUM_CHANGED_TR BIT(8)
608#define CPUM_CHANGED_SYSENTER_MSR BIT(9)
609#define CPUM_CHANGED_HIDDEN_SEL_REGS BIT(10)
610/** @} */
611
612/**
613 * Gets and resets the changed flags (CPUM_CHANGED_*).
614 *
615 * @returns The changed flags.
616 * @param pVM VM handle.
617 */
618CPUMDECL(unsigned) CPUMGetAndClearChangedFlagsREM(PVM pVM);
619
620/**
621 * Sets the specified changed flags (CPUM_CHANGED_*).
622 *
623 * @param pVM The VM handle.
624 */
625CPUMDECL(void) CPUMSetChangedFlags(PVM pVM, uint32_t fChangedFlags);
626
627/**
628 * Checks if the CPU supports the FXSAVE and FXRSTOR instruction.
629 * @returns true if supported.
630 * @returns false if not supported.
631 * @param pVM The VM handle.
632 */
633CPUMDECL(bool) CPUMSupportsFXSR(PVM pVM);
634
635/**
636 * Checks if the host OS uses the SYSENTER / SYSEXIT instructions.
637 * @returns true if used.
638 * @returns false if not used.
639 * @param pVM The VM handle.
640 */
641CPUMDECL(bool) CPUMIsHostUsingSysEnter(PVM pVM);
642
643/**
644 * Checks if the host OS uses the SYSCALL / SYSRET instructions.
645 * @returns true if used.
646 * @returns false if not used.
647 * @param pVM The VM handle.
648 */
649CPUMDECL(bool) CPUMIsHostUsingSysCall(PVM pVM);
650
651/**
652 * Checks if we activated the FPU/XMM state of the guest OS
653 * @returns true if we did.
654 * @returns false if not.
655 * @param pVM The VM handle.
656 */
657CPUMDECL(bool) CPUMIsGuestFPUStateActive(PVM pVM);
658
659/**
660 * Deactivate the FPU/XMM state of the guest OS
661 * @param pVM The VM handle.
662 */
663CPUMDECL(void) CPUMDeactivateGuestFPUState(PVM pVM);
664
665
666/**
667 * Checks if the hidden selector registers are valid
668 * @returns true if they are.
669 * @returns false if not.
670 * @param pVM The VM handle.
671 */
672CPUMDECL(bool) CPUMAreHiddenSelRegsValid(PVM pVM);
673
674/**
675 * Checks if the hidden selector registers are valid
676 * @param pVM The VM handle.
677 * @param fValid Valid or not
678 */
679CPUMDECL(void) CPUMSetHiddenSelRegsValid(PVM pVM, bool fValid);
680
681/**
682 * Get the current privilege level of the guest.
683 *
684 * @returns cpl
685 * @param pVM VM Handle.
686 * @param pRegFrame Trap register frame.
687 */
688CPUMDECL(uint32_t) CPUMGetGuestCPL(PVM pVM, PCPUMCTXCORE pCtxCore);
689
690
691#ifdef IN_RING3
692/** @defgroup grp_cpum_r3 The CPU Monitor(/Manager) API
693 * @ingroup grp_cpum
694 * @{
695 */
696
697/**
698 * Initializes the CPUM.
699 *
700 * @returns VBox status code.
701 * @param pVM The VM to operate on.
702 */
703CPUMR3DECL(int) CPUMR3Init(PVM pVM);
704
705/**
706 * Applies relocations to data and code managed by this
707 * component. This function will be called at init and
708 * whenever the VMM need to relocate it self inside the GC.
709 *
710 * The CPUM will update the addresses used by the switcher.
711 *
712 * @param pVM The VM.
713 */
714CPUMR3DECL(void) CPUMR3Relocate(PVM pVM);
715
716/**
717 * Terminates the CPUM.
718 *
719 * Termination means cleaning up and freeing all resources,
720 * the VM it self is at this point powered off or suspended.
721 *
722 * @returns VBox status code.
723 * @param pVM The VM to operate on.
724 */
725CPUMR3DECL(int) CPUMR3Term(PVM pVM);
726
727/**
728 * Resets the CPU.
729 *
730 * @param pVM The VM handle.
731 */
732CPUMR3DECL(void) CPUMR3Reset(PVM pVM);
733
734/**
735 * Queries the pointer to the internal CPUMCTX structure
736 *
737 * @returns VBox status code.
738 * @param pVM Handle to the virtual machine.
739 * @param ppCtx Receives the CPUMCTX GC pointer when successful.
740 */
741CPUMR3DECL(int) CPUMR3QueryGuestCtxGCPtr(PVM pVM, GCPTRTYPE(PCPUMCTX) *ppCtx);
742
743
744#ifdef DEBUG
745/**
746 * Debug helper - Saves guest context on raw mode entry (for fatal dump)
747 *
748 * @internal
749 */
750CPUMR3DECL(void) CPUMR3SaveEntryCtx(PVM pVM);
751#endif
752
753/**
754 * API for controlling a few of the CPU features found in CR4.
755 *
756 * Currently only X86_CR4_TSD is accepted as input.
757 *
758 * @returns VBox status code.
759 *
760 * @param pVM The VM handle.
761 * @param fOr The CR4 OR mask.
762 * @param fAnd The CR4 AND mask.
763 */
764CPUMR3DECL(int) CPUMR3SetCR4Feature(PVM pVM, RTHCUINTREG fOr, RTHCUINTREG fAnd);
765
766/** @} */
767#endif
768
769#ifdef IN_GC
770/** @defgroup grp_cpum_gc The CPU Monitor(/Manager) API
771 * @ingroup grp_cpum
772 * @{
773 */
774
775/**
776 * Calls a guest trap/interrupt handler directly
777 * Assumes a trap stack frame has already been setup on the guest's stack!
778 *
779 * @param pRegFrame Original trap/interrupt context
780 * @param selCS Code selector of handler
781 * @param pHandler GC virtual address of handler
782 * @param eflags Callee's EFLAGS
783 * @param selSS Stack selector for handler
784 * @param pEsp Stack address for handler
785 *
786 * This function does not return!
787 *
788 */
789CPUMGCDECL(void) CPUMGCCallGuestTrapHandler(PCPUMCTXCORE pRegFrame, uint32_t selCS, RTGCPTR pHandler, uint32_t eflags, uint32_t selSS, RTGCPTR pEsp);
790
791/**
792 * Performs an iret to V86 code
793 * Assumes a trap stack frame has already been setup on the guest's stack!
794 *
795 * @param pRegFrame Original trap/interrupt context
796 *
797 * This function does not return!
798 */
799CPUMGCDECL(void) CPUMGCCallV86Code(PCPUMCTXCORE pRegFrame);
800
801/** @} */
802#endif
803
804#ifdef IN_RING0
805/** @defgroup grp_cpum_r0 The CPU Monitor(/Manager) API
806 * @ingroup grp_cpum
807 * @{
808 */
809
810/**
811 * Does Ring-0 CPUM initialization.
812 *
813 * This is mainly to check that the Host CPU mode is compatible
814 * with VBox.
815 *
816 * @returns VBox status code.
817 * @param pVM The VM to operate on.
818 */
819CPUMR0DECL(int) CPUMR0Init(PVM pVM);
820
821/** @} */
822#endif
823
824/** @} */
825__END_DECLS
826
827
828#endif
829
830
831
832
833
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette