VirtualBox

source: vbox/trunk/include/VBox/vmm/apic.h@ 60309

Last change on this file since 60309 was 60307, checked in by vboxsync, 9 years ago

VMM: APIC rewrite. Initial commit, work in progress.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 34.3 KB
Line 
1/** @file
2 * APIC - Advanced Programmable Interrupt Controller.
3 */
4
5/*
6 * Copyright (C) 2006-2016 Oracle Corporation
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 (GPL) as published by the Free Software
12 * Foundation, in version 2 as it comes in the "COPYING" file of the
13 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
14 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * The contents of this file may alternatively be used under the terms
17 * of the Common Development and Distribution License Version 1.0
18 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
19 * VirtualBox OSE distribution, in which case the provisions of the
20 * CDDL are applicable instead of those of the GPL.
21 *
22 * You may elect to license modified versions of this file under the
23 * terms and conditions of either the GPL or the CDDL or both.
24 */
25
26#ifndef ___VBox_vmm_apic_h
27#define ___VBox_vmm_apic_h
28
29#include <VBox/vmm/pdmins.h>
30#include <VBox/vmm/pdmdev.h>
31
32/** @defgroup grp_apic The local APIC VMM API
33 * @ingroup grp_vmm
34 * @{
35 */
36
37/** The APIC hardware version we are emulating. */
38#define XAPIC_HARDWARE_VERSION XAPIC_HARDWARE_VERSION_P4
39
40/** The APIC base physical address. */
41#define MSR_APICBASE_PHYSADDR(a) ((a) >> 12)
42/** The APIC base physical address shift. */
43#define MSR_APICBASE_PHYSADDR_SHIFT 12
44/** The APIC base MSR mode shift. */
45#define MSR_APICBASE_MODE_SHIFT 10
46/** The APIC global enable bit. */
47#define MSR_APICBASE_XAPIC_ENABLE_BIT RT_BIT_64(11)
48/** The x2APIC global enable bit. */
49#define MSR_APICBASE_X2APIC_ENABLE_BIT RT_BIT_64(10)
50/** The APIC bootstrap processor bit. */
51#define MSR_APICBASE_BOOTSTRAP_CPU_BIT RT_BIT_64(8)
52/** The default APIC base address. */
53#define XAPIC_APICBASE_PHYSADDR UINT64_C(0xfee00000)
54/** The APIC base MSR - Is the APIC enabled? */
55#define MSR_APICBASE_IS_ENABLED(a_Msr) RT_BOOL((a_Msr) & MSR_APICBASE_XAPIC_ENABLE_BIT)
56
57/** Offset of APIC ID Register. */
58#define XAPIC_OFF_ID 0x020
59/** Offset of APIC Version Register. */
60#define XAPIC_OFF_VERSION 0x030
61/** Offset of Task Priority Register. */
62#define XAPIC_OFF_TPR 0x080
63/** Offset of Arbitrartion Priority register. */
64#define XAPIC_OFF_APR 0x090
65/** Offset of Processor Priority register. */
66#define XAPIC_OFF_PPR 0x0A0
67/** Offset of End Of Interrupt register. */
68#define XAPIC_OFF_EOI 0x0B0
69/** Offset of Remote Read Register. */
70#define XAPIC_OFF_RRD 0x0C0
71/** Offset of Logical Destination Register. */
72#define XAPIC_OFF_LDR 0x0D0
73/** Offset of Destination Format Register. */
74#define XAPIC_OFF_DFR 0x0E0
75/** Offset of Spurious Interrupt Vector Register. */
76#define XAPIC_OFF_SVR 0x0F0
77/** Offset of In-service Register (bits 31:0). */
78#define XAPIC_OFF_ISR0 0x100
79/** Offset of In-service Register (bits 63:32). */
80#define XAPIC_OFF_ISR1 0x110
81/** Offset of In-service Register (bits 95:64). */
82#define XAPIC_OFF_ISR2 0x120
83/** Offset of In-service Register (bits 127:96). */
84#define XAPIC_OFF_ISR3 0x130
85/** Offset of In-service Register (bits 159:128). */
86#define XAPIC_OFF_ISR4 0x140
87/** Offset of In-service Register (bits 191:160). */
88#define XAPIC_OFF_ISR5 0x150
89/** Offset of In-service Register (bits 223:192). */
90#define XAPIC_OFF_ISR6 0x160
91/** Offset of In-service Register (bits 255:224). */
92#define XAPIC_OFF_ISR7 0x170
93/** Offset of Trigger Mode Register (bits 31:0). */
94#define XAPIC_OFF_TMR0 0x180
95/** Offset of Trigger Mode Register (bits 63:32). */
96#define XAPIC_OFF_TMR1 0x190
97/** Offset of Trigger Mode Register (bits 95:64). */
98#define XAPIC_OFF_TMR2 0x1A0
99/** Offset of Trigger Mode Register (bits 127:96). */
100#define XAPIC_OFF_TMR3 0x1B0
101/** Offset of Trigger Mode Register (bits 159:128). */
102#define XAPIC_OFF_TMR4 0x1C0
103/** Offset of Trigger Mode Register (bits 191:160). */
104#define XAPIC_OFF_TMR5 0x1D0
105/** Offset of Trigger Mode Register (bits 223:192). */
106#define XAPIC_OFF_TMR6 0x1E0
107/** Offset of Trigger Mode Register (bits 255:224). */
108#define XAPIC_OFF_TMR7 0x1F0
109/** Offset of Interrupt Request Register (bits 31:0). */
110#define XAPIC_OFF_IRR0 0x200
111/** Offset of Interrupt Request Register (bits 63:32). */
112#define XAPIC_OFF_IRR1 0x210
113/** Offset of Interrupt Request Register (bits 95:64). */
114#define XAPIC_OFF_IRR2 0x220
115/** Offset of Interrupt Request Register (bits 127:96). */
116#define XAPIC_OFF_IRR3 0x230
117/** Offset of Interrupt Request Register (bits 159:128). */
118#define XAPIC_OFF_IRR4 0x240
119/** Offset of Interrupt Request Register (bits 191:160). */
120#define XAPIC_OFF_IRR5 0x250
121/** Offset of Interrupt Request Register (bits 223:192). */
122#define XAPIC_OFF_IRR6 0x260
123/** Offset of Interrupt Request Register (bits 255:224). */
124#define XAPIC_OFF_IRR7 0x270
125/** Offset of Error Status Register. */
126#define XAPIC_OFF_ESR 0x280
127/** Offset of LVT CMCI Register. */
128#define XAPIC_OFF_LVT_CMCI 0x2F0
129/** Offset of Interrupt Command Register - Lo. */
130#define XAPIC_OFF_ICR_LO 0x300
131/** Offset of Interrupt Command Register - Hi. */
132#define XAPIC_OFF_ICR_HI 0x310
133/** Offset of LVT Timer Register. */
134#define XAPIC_OFF_LVT_TIMER 0x320
135/** Offset of LVT Thermal Sensor Register. */
136#define XAPIC_OFF_LVT_THERMAL 0x330
137/** Offset of LVT Performance Counter Register. */
138#define XAPIC_OFF_LVT_PERF 0x340
139/** Offset of LVT LINT0 Register. */
140#define XAPIC_OFF_LVT_LINT0 0x350
141/** Offset of LVT LINT1 Register. */
142#define XAPIC_OFF_LVT_LINT1 0x360
143/** Offset of LVT Error Register . */
144#define XAPIC_OFF_LVT_ERROR 0x370
145/** Offset of Timer Initial Count Register. */
146#define XAPIC_OFF_TIMER_ICR 0x380
147/** Offset of Timer Current Count Register. */
148#define XAPIC_OFF_TIMER_CCR 0x390
149/** Offset of Timer Divide Configuration Register. */
150#define XAPIC_OFF_TIMER_DCR 0x3E0
151/** Offset of Self-IPI Register (x2APIC only). */
152#define X2APIC_OFF_SELF_IPI 0x3F0
153
154/** Offset of LVT range start. */
155#define XAPIC_OFF_LVT_START XAPIC_OFF_LVT_TIMER
156/** Offset of LVT range end (inclusive). */
157#define XAPIC_OFF_LVT_END XAPIC_OFF_LVT_ERROR
158/** Offset of LVT extended range start. */
159#define XAPIC_OFF_LVT_EXT_START XAPIC_OFF_LVT_CMCI
160/** Offset of LVT extended range end (inclusive). */
161#define XAPIC_OFF_LVT_EXT_END XAPIC_OFF_LVT_CMCI
162
163
164/**
165 * The xAPIC sparse 256-bit register.
166 */
167typedef union XAPIC256BITREG
168{
169 /** The sparse-bitmap view. */
170 struct
171 {
172 uint32_t u32Reg;
173 uint32_t uReserved0[3];
174 } u[8];
175 /** The 32-bit view. */
176 uint32_t au32[32];
177} XAPIC256BITREG;
178/** Pointer to an xAPIC sparse bitmap register. */
179typedef XAPIC256BITREG *PXAPIC256BITREG;
180/** Pointer to a const xAPIC sparse bitmap register. */
181typedef XAPIC256BITREG const *PCXAPIC256BITREG;
182AssertCompileSize(XAPIC256BITREG, 128);
183
184/**
185 * The xAPIC memory layout as per Intel/AMD specs.
186 */
187typedef struct XAPICPAGE
188{
189 /* 0x00 - Reserved. */
190 uint32_t uReserved0[8];
191 /* 0x20 - APIC ID. */
192 struct
193 {
194 uint8_t u8Reserved0[3];
195 uint8_t u8ApicId;
196 uint32_t u32Reserved0[3];
197 } id;
198 /* 0x30 - APIC version register. */
199 union
200 {
201 struct
202 {
203#if XAPIC_HARDWARE_VERSION == XAPIC_HARDWARE_VERSION_P4
204 uint8_t u8Version;
205#else
206# error "Implement Pentium and P6 family APIC architectures"
207#endif
208 uint8_t uReserved0;
209 uint8_t u8MaxLvtEntry;
210 uint8_t fEoiBroadcastSupression : 1;
211 uint8_t u7Reserved1 : 7;
212 uint32_t u32Reserved0[3];
213 } u;
214 struct
215 {
216 uint32_t u32Version;
217 uint32_t u32Reserved0[3];
218 } all;
219 } version;
220 /* 0x40 - Reserved. */
221 uint32_t uReserved1[16];
222 /* 0x80 - Task Priority Register (TPR). */
223 struct
224 {
225 uint8_t u8Tpr;
226 uint8_t u8Reserved0[3];
227 uint32_t u32Reserved0[3];
228 } tpr;
229 /* 0x90 - Arbitration Priority Register (APR). */
230 struct
231 {
232 uint8_t u8Apr;
233 uint8_t u8Reserved0[3];
234 uint32_t u32Reserved0[3];
235 } apr;
236 /* 0xA0 - Processor Priority Register (PPR). */
237 struct
238 {
239 uint8_t u8Ppr;
240 uint8_t u8Reserved0[3];
241 uint32_t u32Reserved0[3];
242 } ppr;
243 /* 0xB0 - End Of Interrupt Register (EOI). */
244 struct
245 {
246 uint32_t u32Eoi;
247 uint32_t u32Reserved0[3];
248 } eoi;
249 /* 0xC0 - Remote Read Register (RRD). */
250 struct
251 {
252 uint32_t u32Rrd;
253 uint32_t u32Reserved0[3];
254 } rrd;
255 /* 0xD0 - Logical Destination Register (LDR). */
256 union
257 {
258 struct
259 {
260 uint32_t u24Reserved0 : 24;
261 uint32_t u8LogicalApicId : 8;
262 uint32_t u32Reserved0[3];
263 } u;
264 struct
265 {
266 uint32_t u32Ldr;
267 uint32_t u32Reserved0[3];
268 } all;
269 } ldr;
270 /* 0xE0 - Destination Format Register (DFR). */
271 union
272 {
273 struct
274 {
275 uint32_t u28ReservedMb1 : 28; /* MB1 */
276 uint32_t u4Model : 4;
277 uint32_t u32Reserved0[3];
278 } u;
279 struct
280 {
281 uint32_t u32Dfr;
282 uint32_t u32Reserved0[3];
283 } all;
284 } dfr;
285 /* 0xF0 - Spurious-Interrupt Vector Register (SVR). */
286 union
287 {
288 struct
289 {
290 uint32_t u8SpuriousVector : 8;
291 uint32_t fApicSoftwareEnable : 1;
292 uint32_t u3Reserved0 : 3;
293 uint32_t fSupressEoiBroadcast : 1;
294 uint32_t u19Reserved1 : 19;
295 uint32_t u32Reserved0[3];
296 } u;
297 struct
298 {
299 uint32_t u32Svr;
300 uint32_t u32Reserved0[3];
301 } all;
302 } svr;
303 /* 0x100 - In-service Register (ISR). */
304 XAPIC256BITREG isr;
305 /* 0x180 - Trigger Mode Register (TMR). */
306 XAPIC256BITREG tmr;
307 /* 0x200 - Interrupt Request Register (IRR). */
308 XAPIC256BITREG irr;
309 /* 0x280 - Error Status Register (ESR). */
310 union
311 {
312 struct
313 {
314#if XAPIC_HARDWARE_VERSION == XAPIC_HARDWARE_VERSION_P4
315 uint32_t u4Reserved0 : 4;
316#else
317# error "Implement Pentium and P6 family APIC architectures"
318#endif
319 uint32_t fRedirectableIpi : 1;
320 uint32_t fSendIllegalVector : 1;
321 uint32_t fRcvdIllegalVector : 1;
322 uint32_t fIllegalRegAddr : 1;
323 uint32_t u24Reserved1 : 24;
324 uint32_t u32Reserved0[3];
325 } u;
326 struct
327 {
328 uint32_t u32Errors;
329 uint32_t u32Reserved0[3];
330 } all;
331 } esr;
332 /* 0x290 - Reserved. */
333 uint32_t uReserved2[28];
334 /* 0x300 - Interrupt Command Register (ICR) - Low. */
335 union
336 {
337 struct
338 {
339 uint32_t u8Vector : 8;
340 uint32_t u3DeliveryMode : 3;
341 uint32_t u1DestMode : 1;
342 uint32_t u1DeliveryStatus : 1;
343 uint32_t fReserved0 : 1;
344 uint32_t u1Level : 1;
345 uint32_t u1TriggerMode : 1;
346 uint32_t u2Reserved1 : 2;
347 uint32_t u2DestShorthand : 2;
348 uint32_t u12Reserved2 : 12;
349 uint32_t u32Reserved0[3];
350 } u;
351 struct
352 {
353 uint32_t u32IcrLo;
354 uint32_t u32Reserved0[3];
355 } all;
356 } icr_lo;
357 /* 0x310 - Interrupt Comannd Register (ICR) - High. */
358 union
359 {
360 struct
361 {
362 uint32_t u24Reserved0 : 24;
363 uint32_t u8Dest : 8;
364 uint32_t u32Reserved0[3];
365 } u;
366 struct
367 {
368 uint32_t u32IcrHi;
369 uint32_t u32Reserved0[3];
370 } all;
371 } icr_hi;
372 /* 0x320 - Local Vector Table (LVT) Timer Register. */
373 union
374 {
375 struct
376 {
377 uint32_t u8Vector : 8;
378 uint32_t u4Reserved0 : 4;
379 uint32_t u1DeliveryStatus : 1;
380 uint32_t u3Reserved1 : 3;
381 uint32_t u1Mask : 1;
382 uint32_t u2TimerMode : 2;
383 uint32_t u13Reserved2 : 13;
384 uint32_t u32Reserved0[3];
385 } u;
386 struct
387 {
388 uint32_t u32LvtTimer;
389 uint32_t u32Reserved0[3];
390 } all;
391 } lvt_timer;
392 /* 0x330 - Local Vector Table (LVT) Thermal Sensor Register. */
393#if XAPIC_HARDWARE_VERSION == XAPIC_HARDWARE_VERSION_P4
394 union
395 {
396 struct
397 {
398 uint32_t u8Vector : 8;
399 uint32_t u3DeliveryMode : 3;
400 uint32_t u1Reserved0 : 1;
401 uint32_t u1DeliveryStatus : 1;
402 uint32_t u3Reserved1 : 3;
403 uint32_t u1Mask : 1;
404 uint32_t u15Reserved2 : 15;
405 uint32_t u32Reserved0[3];
406 } u;
407 struct
408 {
409 uint32_t u32LvtThermal;
410 uint32_t u32Reserved0[3];
411 } all;
412 } lvt_thermal;
413#else
414# error "Implement Pentium and P6 family APIC architectures"
415#endif
416 /* 0x340 - Local Vector Table (LVT) Performance Monitor Counter (PMC) Register. */
417 union
418 {
419 struct
420 {
421 uint32_t u8Vector : 8;
422 uint32_t u3DeliveryMode : 3;
423 uint32_t u1Reserved0 : 1;
424 uint32_t u1DeliveryStatus : 1;
425 uint32_t u3Reserved1 : 3;
426 uint32_t u1Mask : 1;
427 uint32_t u15Reserved2 : 15;
428 uint32_t u32Reserved0[3];
429 } u;
430 struct
431 {
432 uint32_t u32LvtPerf;
433 uint32_t u32Reserved0[3];
434 } all;
435 } lvt_perf;
436 /* 0x350 - Local Vector Table (LVT) LINT0 Register. */
437 union
438 {
439 struct
440 {
441 uint32_t u8Vector : 8;
442 uint32_t u3DeliveryMode : 3;
443 uint32_t u1Reserved0 : 1;
444 uint32_t u1DeliveryStatus : 1;
445 uint32_t u1IntrPolarity : 1;
446 uint32_t u1RemoteIrr : 1;
447 uint32_t u1TriggerMode : 1;
448 uint32_t u1Mask : 1;
449 uint32_t u15Reserved2 : 15;
450 uint32_t u32Reserved0[3];
451 } u;
452 struct
453 {
454 uint32_t u32LvtLint0;
455 uint32_t u32Reserved0[3];
456 } all;
457 } lvt_lint0;
458 /* 0x360 - Local Vector Table (LVT) LINT1 Register. */
459 union
460 {
461 struct
462 {
463 uint32_t u8Vector : 8;
464 uint32_t u3DeliveryMode : 3;
465 uint32_t u1Reserved0 : 1;
466 uint32_t u1DeliveryStatus : 1;
467 uint32_t u1IntrPolarity : 1;
468 uint32_t u1RemoteIrr : 1;
469 uint32_t u1TriggerMode : 1;
470 uint32_t u1Mask : 1;
471 uint32_t u15Reserved2 : 15;
472 uint32_t u32Reserved0[3];
473 } u;
474 struct
475 {
476 uint32_t u32LvtLint1;
477 uint32_t u32Reserved0[3];
478 } all;
479 } lvt_lint1;
480 /* 0x370 - Local Vector Table (LVT) Error Register. */
481 union
482 {
483 struct
484 {
485 uint32_t u8Vector : 8;
486 uint32_t u4Reserved0 : 4;
487 uint32_t u1DeliveryStatus : 1;
488 uint32_t u3Reserved1 : 3;
489 uint32_t u1Mask : 1;
490 uint32_t u15Reserved2 : 15;
491 uint32_t u32Reserved0[3];
492 } u;
493 struct
494 {
495 uint32_t u32LvtError;
496 uint32_t u32Reserved0[3];
497 } all;
498 } lvt_error;
499 /* 0x380 - Timer Initial Counter Register. */
500 struct
501 {
502 uint32_t u32InitialCount;
503 uint32_t u32Reserved0[3];
504 } timer_icr;
505 /* 0x390 - Timer Current Counter Register. */
506 struct
507 {
508 uint32_t u32CurrentCount;
509 uint32_t u32Reserved0[3];
510 } timer_ccr;
511 /* 0x3A0 - Reserved. */
512 uint32_t u32Reserved3[16];
513 /* 0x3E0 - Timer Divide Configuration Register. */
514 union
515 {
516 struct
517 {
518 uint32_t u2DivideValue0 : 2;
519 uint32_t u1Reserved0 : 1;
520 uint32_t u1DivideValue1 : 1;
521 uint32_t u28Reserved1 : 28;
522 uint32_t u32Reserved0[3];
523 } u;
524 struct
525 {
526 uint32_t u32DivideValue;
527 uint32_t u32Reserved0[3];
528 } all;
529 } timer_dcr;
530 /* 0x3F0 - Reserved. */
531 uint8_t u8Reserved0[3088];
532} XAPICPAGE;
533/** Pointer to a XAPICPAGE struct. */
534typedef volatile XAPICPAGE *PXAPICPAGE;
535/** Pointer to a const XAPICPAGE struct. */
536typedef const volatile XAPICPAGE *PCXAPICPAGE;
537AssertCompileSize(XAPICPAGE, 4096);
538AssertCompileMemberOffset(XAPICPAGE, id, XAPIC_OFF_ID);
539AssertCompileMemberOffset(XAPICPAGE, version, XAPIC_OFF_VERSION);
540AssertCompileMemberOffset(XAPICPAGE, tpr, XAPIC_OFF_TPR);
541AssertCompileMemberOffset(XAPICPAGE, apr, XAPIC_OFF_APR);
542AssertCompileMemberOffset(XAPICPAGE, ppr, XAPIC_OFF_PPR);
543AssertCompileMemberOffset(XAPICPAGE, eoi, XAPIC_OFF_EOI);
544AssertCompileMemberOffset(XAPICPAGE, rrd, XAPIC_OFF_RRD);
545AssertCompileMemberOffset(XAPICPAGE, ldr, XAPIC_OFF_LDR);
546AssertCompileMemberOffset(XAPICPAGE, dfr, XAPIC_OFF_DFR);
547AssertCompileMemberOffset(XAPICPAGE, svr, XAPIC_OFF_SVR);
548AssertCompileMemberOffset(XAPICPAGE, isr, XAPIC_OFF_ISR0);
549AssertCompileMemberOffset(XAPICPAGE, tmr, XAPIC_OFF_TMR0);
550AssertCompileMemberOffset(XAPICPAGE, irr, XAPIC_OFF_IRR0);
551AssertCompileMemberOffset(XAPICPAGE, esr, XAPIC_OFF_ESR);
552AssertCompileMemberOffset(XAPICPAGE, icr_lo, XAPIC_OFF_ICR_LO);
553AssertCompileMemberOffset(XAPICPAGE, icr_hi, XAPIC_OFF_ICR_HI);
554AssertCompileMemberOffset(XAPICPAGE, lvt_timer, XAPIC_OFF_LVT_TIMER);
555AssertCompileMemberOffset(XAPICPAGE, lvt_thermal, XAPIC_OFF_LVT_THERMAL);
556AssertCompileMemberOffset(XAPICPAGE, lvt_perf, XAPIC_OFF_LVT_PERF);
557AssertCompileMemberOffset(XAPICPAGE, lvt_lint0, XAPIC_OFF_LVT_LINT0);
558AssertCompileMemberOffset(XAPICPAGE, lvt_lint1, XAPIC_OFF_LVT_LINT1);
559AssertCompileMemberOffset(XAPICPAGE, lvt_error, XAPIC_OFF_LVT_ERROR);
560AssertCompileMemberOffset(XAPICPAGE, timer_icr, XAPIC_OFF_TIMER_ICR);
561AssertCompileMemberOffset(XAPICPAGE, timer_ccr, XAPIC_OFF_TIMER_CCR);
562AssertCompileMemberOffset(XAPICPAGE, timer_dcr, XAPIC_OFF_TIMER_DCR);
563
564/**
565 * The x2APIC memory layout as per Intel/AMD specs.
566 */
567typedef struct X2APICPAGE
568{
569 /* 0x00 - Reserved. */
570 uint32_t uReserved0[8];
571 /* 0x20 - APIC ID. */
572 struct
573 {
574 uint32_t u32ApicId;
575 uint32_t u32Reserved0[3];
576 } id;
577 /* 0x30 - APIC version register. */
578 union
579 {
580 struct
581 {
582 uint8_t u8Version;
583 uint8_t u8Reserved0;
584 uint8_t u8MaxLvtEntry;
585 uint8_t fEoiBroadcastSupression : 1;
586 uint8_t u7Reserved1 : 7;
587 uint32_t u32Reserved0[3];
588 } u;
589 struct
590 {
591 uint32_t u32Version;
592 uint32_t u32Reserved2[3];
593 } all;
594 } version;
595 /* 0x40 - Reserved. */
596 uint32_t uReserved1[16];
597 /* 0x80 - Task Priority Register (TPR). */
598 struct
599 {
600 uint8_t u8Tpr;
601 uint8_t u8Reserved0[3];
602 uint32_t u32Reserved0[3];
603 } tpr;
604 /* 0x90 - Reserved. */
605 uint32_t uReserved2[4];
606 /* 0xA0 - Processor Priority Register (PPR). */
607 struct
608 {
609 uint8_t u8Ppr;
610 uint8_t u8Reserved0[3];
611 uint32_t u32Reserved0[3];
612 } ppr;
613 /* 0xB0 - End Of Interrupt Register (EOI). */
614 struct
615 {
616 uint32_t u32Eoi;
617 uint32_t u32Reserved0[3];
618 } eoi;
619 /* 0xC0 - Remote Read Register (RRD). */
620 struct
621 {
622 uint32_t u32Rrd;
623 uint32_t u32Reserved0[3];
624 } rrd;
625 /* 0xD0 - Logical Destination Register (LDR). */
626 struct
627 {
628 uint32_t u32LogicalApicId;
629 uint32_t u32Reserved1[3];
630 } ldr;
631 /* 0xE0 - Reserved. */
632 uint32_t uReserved3[4];
633 /* 0xF0 - Spurious-Interrupt Vector Register (SVR). */
634 union
635 {
636 struct
637 {
638 uint32_t u8SpuriousVector : 8;
639 uint32_t fApicSoftwareEnable : 1;
640 uint32_t u3Reserved0 : 3;
641 uint32_t fSupressEoiBroadcast : 1;
642 uint32_t u19Reserved1 : 19;
643 uint32_t u32Reserved0[3];
644 } u;
645 struct
646 {
647 uint32_t u32Svr;
648 uint32_t uReserved0[3];
649 } all;
650 } svr;
651 /* 0x100 - In-service Register (ISR). */
652 XAPIC256BITREG isr;
653 /* 0x180 - Trigger Mode Register (TMR). */
654 XAPIC256BITREG tmr;
655 /* 0x200 - Interrupt Request Register (IRR). */
656 XAPIC256BITREG irr;
657 /* 0x280 - Error Status Register (ESR). */
658 union
659 {
660 struct
661 {
662#if XAPIC_HARDWARE_VERSION == XAPIC_HARDWARE_VERSION_P4
663 uint32_t u4Reserved0 : 4;
664#else
665# error "Implement Pentium and P6 family APIC architectures"
666#endif
667 uint32_t fRedirectableIpi : 1;
668 uint32_t fSendIllegalVector : 1;
669 uint32_t fRcvdIllegalVector : 1;
670 uint32_t fIllegalRegAddr : 1;
671 uint32_t u24Reserved1 : 24;
672 uint32_t uReserved0[3];
673 } u;
674 struct
675 {
676 uint32_t u32Errors;
677 uint32_t u32Reserved0[3];
678 } all;
679 } esr;
680 /* 0x290 - Reserved. */
681 uint32_t uReserved4[28];
682 /* 0x300 - Interrupt Command Register (ICR) - Low. */
683 union
684 {
685 struct
686 {
687 uint32_t u8Vector : 8;
688 uint32_t u3DeliveryMode : 3;
689 uint32_t u1DestMode : 1;
690 uint32_t u2Reserved0 : 2;
691 uint32_t u1Level : 1;
692 uint32_t u1TriggerMode : 1;
693 uint32_t u2Reserved1 : 2;
694 uint32_t u2DestShorthand : 2;
695 uint32_t u12Reserved2 : 12;
696 uint32_t u32Reserved0[3];
697 } u;
698 struct
699 {
700 uint32_t u32IcrLo;
701 uint32_t u32Reserved3[3];
702 } all;
703 } icr_lo;
704 /* 0x310 - Interrupt Comannd Register (ICR) - High. */
705 struct
706 {
707 uint32_t u32IcrHi;
708 uint32_t uReserved1[3];
709 } icr_hi;
710 /* 0x320 - Local Vector Table (LVT) Timer Register. */
711 union
712 {
713 struct
714 {
715 uint32_t u8Vector : 8;
716 uint32_t u4Reserved0 : 4;
717 uint32_t u1DeliveryStatus : 1;
718 uint32_t u3Reserved1 : 3;
719 uint32_t u1Mask : 1;
720 uint32_t u2TimerMode : 2;
721 uint32_t u13Reserved2 : 13;
722 uint32_t u32Reserved0[3];
723 } u;
724 struct
725 {
726 uint32_t u32LvtTimer;
727 uint32_t u32Reserved0[3];
728 } all;
729 } lvt_timer;
730 /* 0x330 - Local Vector Table (LVT) Thermal Sensor Register. */
731 union
732 {
733 struct
734 {
735 uint32_t u8Vector : 8;
736 uint32_t u3DeliveryMode : 3;
737 uint32_t u1Reserved0 : 1;
738 uint32_t u1DeliveryStatus : 1;
739 uint32_t u3Reserved1 : 3;
740 uint32_t u1Mask : 1;
741 uint32_t u15Reserved2 : 15;
742 uint32_t u32Reserved0[3];
743 } u;
744 struct
745 {
746 uint32_t u32LvtThermal;
747 uint32_t uReserved0[3];
748 } all;
749 } lvt_thermal;
750 /* 0x340 - Local Vector Table (LVT) Performance Monitor Counter (PMC) Register. */
751 union
752 {
753 struct
754 {
755 uint32_t u8Vector : 8;
756 uint32_t u3DeliveryMode : 3;
757 uint32_t u1Reserved0 : 1;
758 uint32_t u1DeliveryStatus : 1;
759 uint32_t u3Reserved1 : 3;
760 uint32_t u1Mask : 1;
761 uint32_t u15Reserved2 : 15;
762 uint32_t u32Reserved0[3];
763 } u;
764 struct
765 {
766 uint32_t u32LvtPerf;
767 uint32_t u32Reserved0[3];
768 } all;
769 } lvt_perf;
770 /* 0x350 - Local Vector Table (LVT) LINT0 Register. */
771 union
772 {
773 struct
774 {
775 uint32_t u8Vector : 8;
776 uint32_t u3DeliveryMode : 3;
777 uint32_t u1Reserved0 : 1;
778 uint32_t u1DeliveryStatus : 1;
779 uint32_t u1IntrPolarity : 1;
780 uint32_t u1RemoteIrr : 1;
781 uint32_t u1TriggerMode : 1;
782 uint32_t u1Mask : 1;
783 uint32_t u15Reserved2 : 15;
784 uint32_t u32Reserved0[3];
785 } u;
786 struct
787 {
788 uint32_t u32LvtLint0;
789 uint32_t u32Reserved0[3];
790 } all;
791 } lvt_lint0;
792 /* 0x360 - Local Vector Table (LVT) LINT1 Register. */
793 union
794 {
795 struct
796 {
797 uint32_t u8Vector : 8;
798 uint32_t u3DeliveryMode : 3;
799 uint32_t u1Reserved0 : 1;
800 uint32_t u1DeliveryStatus : 1;
801 uint32_t u1IntrPolarity : 1;
802 uint32_t u1RemoteIrr : 1;
803 uint32_t u1TriggerMode : 1;
804 uint32_t u1Mask : 1;
805 uint32_t u15Reserved2 : 15;
806 uint32_t u32Reserved0[3];
807 } u;
808 struct
809 {
810 uint32_t u32LvtLint1;
811 uint32_t u32Reserved0[3];
812 } all;
813 } lvt_lint1;
814 /* 0x370 - Local Vector Table (LVT) Error Register. */
815 union
816 {
817 struct
818 {
819 uint32_t u8Vector : 8;
820 uint32_t u4Reserved0 : 4;
821 uint32_t u1DeliveryStatus : 1;
822 uint32_t u3Reserved1 : 3;
823 uint32_t u1Mask : 1;
824 uint32_t u15Reserved2 : 15;
825 uint32_t u32Reserved0[3];
826 } u;
827 struct
828 {
829 uint32_t u32LvtError;
830 uint32_t u32Reserved0[3];
831 } all;
832 } lvt_error;
833 /* 0x380 - Timer Initial Counter Register. */
834 struct
835 {
836 uint32_t u32InitialCount;
837 uint32_t u32Reserved0[3];
838 } timer_icr;
839 /* 0x390 - Timer Current Counter Register. */
840 struct
841 {
842 uint32_t u32CurrentCount;
843 uint32_t u32Reserved0[3];
844 } timer_ccr;
845 /* 0x3A0 - Reserved. */
846 uint32_t uReserved5[16];
847 /* 0x3E0 - Timer Divide Configuration Register. */
848 union
849 {
850 struct
851 {
852 uint32_t u2DivideValue0 : 2;
853 uint32_t u1Reserved0 : 1;
854 uint32_t u1DivideValue1 : 1;
855 uint32_t u28Reserved1 : 28;
856 uint32_t u32Reserved0[3];
857 } u;
858 struct
859 {
860 uint32_t u32DivideValue;
861 uint32_t u32Reserved0[3];
862 } all;
863 } timer_dcr;
864 /* 0x3F0 - Self IPI Register. */
865 struct
866 {
867 uint32_t u8Vector : 8;
868 uint32_t u24Reserved0 : 24;
869 uint32_t u32Reserved0[3];
870 } self_ipi;
871 /* 0x400 - Reserved. */
872 uint8_t u8Reserved0[3072];
873} X2APICPAGE;
874/** Pointer to a X2APICPAGE struct. */
875typedef volatile X2APICPAGE *PX2APICPAGE;
876/** Pointer to a const X2APICPAGE struct. */
877typedef const volatile X2APICPAGE *PCX2APICPAGE;
878//AssertCompileSize(X2APICPAGE, 4096);
879AssertCompileMemberOffset(X2APICPAGE, id, XAPIC_OFF_ID);
880AssertCompileMemberOffset(X2APICPAGE, version, XAPIC_OFF_VERSION);
881AssertCompileMemberOffset(X2APICPAGE, tpr, XAPIC_OFF_TPR);
882AssertCompileMemberOffset(X2APICPAGE, ppr, XAPIC_OFF_PPR);
883AssertCompileMemberOffset(X2APICPAGE, eoi, XAPIC_OFF_EOI);
884AssertCompileMemberOffset(X2APICPAGE, rrd, XAPIC_OFF_RRD);
885AssertCompileMemberOffset(X2APICPAGE, ldr, XAPIC_OFF_LDR);
886AssertCompileMemberOffset(X2APICPAGE, svr, XAPIC_OFF_SVR);
887AssertCompileMemberOffset(X2APICPAGE, isr, XAPIC_OFF_ISR0);
888AssertCompileMemberOffset(X2APICPAGE, tmr, XAPIC_OFF_TMR0);
889AssertCompileMemberOffset(X2APICPAGE, irr, XAPIC_OFF_IRR0);
890AssertCompileMemberOffset(X2APICPAGE, esr, XAPIC_OFF_ESR);
891AssertCompileMemberOffset(X2APICPAGE, icr_lo, XAPIC_OFF_ICR_LO);
892AssertCompileMemberOffset(X2APICPAGE, icr_hi, XAPIC_OFF_ICR_HI);
893AssertCompileMemberOffset(X2APICPAGE, lvt_timer, XAPIC_OFF_LVT_TIMER);
894AssertCompileMemberOffset(X2APICPAGE, lvt_thermal, XAPIC_OFF_LVT_THERMAL);
895AssertCompileMemberOffset(X2APICPAGE, lvt_perf, XAPIC_OFF_LVT_PERF);
896AssertCompileMemberOffset(X2APICPAGE, lvt_lint0, XAPIC_OFF_LVT_LINT0);
897AssertCompileMemberOffset(X2APICPAGE, lvt_lint1, XAPIC_OFF_LVT_LINT1);
898AssertCompileMemberOffset(X2APICPAGE, lvt_error, XAPIC_OFF_LVT_ERROR);
899AssertCompileMemberOffset(X2APICPAGE, timer_icr, XAPIC_OFF_TIMER_ICR);
900AssertCompileMemberOffset(X2APICPAGE, timer_ccr, XAPIC_OFF_TIMER_CCR);
901AssertCompileMemberOffset(X2APICPAGE, timer_dcr, XAPIC_OFF_TIMER_DCR);
902AssertCompileMemberOffset(X2APICPAGE, self_ipi, X2APIC_OFF_SELF_IPI);
903
904/** The offset (in bits) of the posted-interrupt bitmap's outstanding
905 * notification bit. */
906#define XAPIC_PIB_NOTIFICATION_BIT UINT32_C(256)
907
908/**
909 * APIC Pending Interrupt Bitmap (PIB).
910 * The layout is critical as it mimics VT-x's Posted Interrupt Bitmap!
911 */
912typedef struct APICPIB
913{
914 uint32_t volatile aVectorBitmap[8];
915 uint32_t volatile fOutstandingNotification;
916 uint8_t au8Reserved[28];
917} APICPIB;
918AssertCompileMemberOffset(APICPIB, fOutstandingNotification, XAPIC_PIB_NOTIFICATION_BIT / 8);
919AssertCompileSize(APICPIB, 64);
920/** Pointer to a pending interrupt bitmap. */
921typedef APICPIB *PAPICPIB;
922/** Pointer to a const pending interrupt bitmap. */
923typedef const APICPIB *PCAPICPIB;
924
925RT_C_DECLS_BEGIN
926
927#ifdef IN_RING3
928/** @defgroup grp_apic_r3 The APIC Host Context Ring-3 API
929 * @{
930 */
931VMMR3_INT_DECL(int) APICR3InitCompleted(PVM pVM, VMINITCOMPLETED enmWhat);
932VMMR3_INT_DECL(void) APICR3InitIpi(PVMCPU pVCpu);
933VMMR3_INT_DECL(void) APICR3Reset(PVMCPU pVCpu);
934/** @} */
935#endif /* IN_RING3 */
936
937#ifdef IN_RING0
938/** @defgroup grp_apic_r0 The APIC Host Context Ring-0 API
939 * @{
940 */
941VMMR0_INT_DECL(int) APICR0InitVM(PVM pVM);
942VMMR0_INT_DECL(int) APICR0TermVM(PVM pVM);
943/** @} */
944#endif /* IN_RING0 */
945
946VMMDECL(bool) APICQueueInterruptToService(PVMCPU pVCpu, uint8_t u8PendingIntr);
947VMMDECL(void) APICDequeueInterruptFromService(PVMCPU pVCpu, uint8_t u8PendingIntr);
948VMMDECL(void) APICUpdatePendingInterrupts(PVMCPU pVCpu);
949VMMDECL(bool) APICGetHighestPendingInterrupt(PVMCPU pVCpu, uint8_t *pu8PendingIntr);
950
951RT_C_DECLS_END
952
953extern const PDMDEVREG g_DeviceAPIC;
954/** @} */
955
956#endif
957
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