VirtualBox

source: vbox/trunk/src/VBox/VMM/IOMInternal.h@ 4953

Last change on this file since 4953 was 4787, checked in by vboxsync, 17 years ago

Eliminated HCPTRTYPE and replaced with R3R0PTRTYPE where necessary.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 18.0 KB
Line 
1/* $Id: IOMInternal.h 4787 2007-09-14 09:08:56Z vboxsync $ */
2/** @file
3 * IOM - Internal header file.
4 */
5
6/*
7 * Copyright (C) 2006-2007 innotek GmbH
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License as published by the Free Software Foundation,
13 * in version 2 as it comes in the "COPYING" file of the VirtualBox OSE
14 * distribution. VirtualBox OSE is distributed in the hope that it will
15 * be useful, but WITHOUT ANY WARRANTY of any kind.
16 */
17
18#ifndef ___IOMInternal_h
19#define ___IOMInternal_h
20
21#include <VBox/cdefs.h>
22#include <VBox/types.h>
23#include <VBox/iom.h>
24#include <VBox/stam.h>
25#include <iprt/avl.h>
26
27#if !defined(IN_IOM_R3) && !defined(IN_IOM_R0) && !defined(IN_IOM_GC)
28# error "Not in IOM! This is an internal header!"
29#endif
30
31
32/** @defgroup grp_iom_int Internals
33 * @ingroup grp_iom
34 * @internal
35 * @{
36 */
37
38/**
39 * MMIO range descriptor, R3 version.
40 */
41typedef struct IOMMMIORANGER3
42{
43 /** Avl node core with GCPhys as Key and GCPhys + cbSize - 1 as KeyLast. */
44 AVLROGCPHYSNODECORE Core;
45 /** Start physical address. */
46 RTGCPHYS GCPhys;
47 /** Size of the range. */
48 RTUINT cbSize;
49 /** Pointer to user argument. */
50 RTR3PTR pvUser;
51 /** Pointer to device instance. */
52 R3PTRTYPE(PPDMDEVINS) pDevIns;
53 /** Pointer to write callback function. */
54 R3PTRTYPE(PFNIOMMMIOWRITE) pfnWriteCallback;
55 /** Pointer to read callback function. */
56 R3PTRTYPE(PFNIOMMMIOREAD) pfnReadCallback;
57 /** Pointer to fill (memset) callback function. */
58 R3PTRTYPE(PFNIOMMMIOFILL) pfnFillCallback;
59 /** Description / Name. For easing debugging. */
60 R3PTRTYPE(const char *) pszDesc;
61} IOMMMIORANGER3;
62/** Pointer to a MMIO range descriptor, R3 version. */
63typedef struct IOMMMIORANGER3 *PIOMMMIORANGER3;
64
65/**
66 * MMIO range descriptor, R0 version.
67 */
68typedef struct IOMMMIORANGER0
69{
70 /** Avl node core with GCPhys as Key and GCPhys + cbSize - 1 as KeyLast. */
71 AVLROGCPHYSNODECORE Core;
72 /** Start physical address. */
73 RTGCPHYS GCPhys;
74 /** Size of the range. */
75 RTUINT cbSize;
76 /** Pointer to user argument. */
77 RTR0PTR pvUser;
78 /** Pointer to device instance. */
79 R0PTRTYPE(PPDMDEVINS) pDevIns;
80 /** Pointer to write callback function. */
81 R0PTRTYPE(PFNIOMMMIOWRITE) pfnWriteCallback;
82 /** Pointer to read callback function. */
83 R0PTRTYPE(PFNIOMMMIOREAD) pfnReadCallback;
84 /** Pointer to fill (memset) callback function. */
85 R0PTRTYPE(PFNIOMMMIOFILL) pfnFillCallback;
86 /** Description / Name. For easing debugging. */
87 R3PTRTYPE(const char *) pszDesc;
88} IOMMMIORANGER0;
89/** Pointer to a MMIO range descriptor, R0 version. */
90typedef struct IOMMMIORANGER0 *PIOMMMIORANGER0;
91
92/**
93 * MMIO range descriptor, GC version.
94 */
95typedef struct IOMMMIORANGEGC
96{
97 /** Avl node core with GCPhys as Key and GCPhys + cbSize - 1 as KeyLast. */
98 AVLROGCPHYSNODECORE Core;
99 /** Start physical address. */
100 RTGCPHYS GCPhys;
101 /** Size of the range. */
102 RTUINT cbSize;
103 /** Pointer to user argument. */
104 RTGCPTR pvUser;
105 /** Pointer to device instance. */
106 GCPTRTYPE(PPDMDEVINS) pDevIns;
107 /** Pointer to write callback function. */
108 GCPTRTYPE(PFNIOMMMIOWRITE) pfnWriteCallback;
109 /** Pointer to read callback function. */
110 GCPTRTYPE(PFNIOMMMIOREAD) pfnReadCallback;
111 /** Pointer to fill (memset) callback function. */
112 GCPTRTYPE(PFNIOMMMIOFILL) pfnFillCallback;
113 /** Description / Name. For easing debugging. */
114 R3PTRTYPE(const char *) pszDesc;
115} IOMMMIORANGEGC;
116/** Pointer to a MMIO range descriptor, GC version. */
117typedef struct IOMMMIORANGEGC *PIOMMMIORANGEGC;
118
119
120/**
121 * MMIO address statistics. (one address)
122 *
123 * This is a simple way of making on demand statistics, however it's a
124 * bit free with the hypervisor heap memory..
125 */
126typedef struct IOMMMIOSTATS
127{
128 /** Avl node core with the address as Key. */
129 AVLOGCPHYSNODECORE Core;
130 /** Number of reads to this address from R3. */
131 STAMCOUNTER ReadR3;
132 /** Number of writes to this address from R3. */
133 STAMCOUNTER WriteR3;
134 /** Number of reads to this address from R0. */
135 STAMCOUNTER ReadR0;
136 /** Number of writes to this address from R0. */
137 STAMCOUNTER WriteR0;
138 /** Number of reads to this address from GC. */
139 STAMCOUNTER ReadGC;
140 /** Number of writes to this address from GC. */
141 STAMCOUNTER WriteGC;
142 /** Profiling read handler overhead in R3. */
143 STAMPROFILEADV ProfReadR3;
144 /** Profiling write handler overhead in R3. */
145 STAMPROFILEADV ProfWriteR3;
146 /** Profiling read handler overhead in R0. */
147 STAMPROFILEADV ProfReadR0;
148 /** Profiling write handler overhead in R0. */
149 STAMPROFILEADV ProfWriteR0;
150 /** Profiling read handler overhead in GC. */
151 STAMPROFILEADV ProfReadGC;
152 /** Profiling write handler overhead in GC. */
153 STAMPROFILEADV ProfWriteGC;
154 /** Number of reads to this address from R0 which was serviced in R3. */
155 STAMCOUNTER ReadR0ToR3;
156 /** Number of writes to this address from R0 which was serviced in R3. */
157 STAMCOUNTER WriteR0ToR3;
158 /** Number of reads to this address from GC which was serviced in R3. */
159 STAMCOUNTER ReadGCToR3;
160 /** Number of writes to this address from GC which was serviced in R3. */
161 STAMCOUNTER WriteGCToR3;
162} IOMMMIOSTATS;
163/** Pointer to I/O port statistics. */
164typedef IOMMMIOSTATS *PIOMMMIOSTATS;
165
166
167/**
168 * I/O port range descriptor, R3 version.
169 */
170typedef struct IOMIOPORTRANGER3
171{
172 /** Avl node core with Port as Key and Port + cPorts - 1 as KeyLast. */
173 AVLROIOPORTNODECORE Core;
174 /** Start I/O port address. */
175 RTIOPORT Port;
176 /** Size of the range. */
177 uint16_t cPorts;
178 /** Pointer to user argument. */
179 RTR3PTR pvUser;
180 /** Pointer to the associated device instance. */
181 R3PTRTYPE(PPDMDEVINS) pDevIns;
182 /** Pointer to OUT callback function. */
183 R3PTRTYPE(PFNIOMIOPORTOUT) pfnOutCallback;
184 /** Pointer to IN callback function. */
185 R3PTRTYPE(PFNIOMIOPORTIN) pfnInCallback;
186 /** Pointer to string OUT callback function. */
187 R3PTRTYPE(PFNIOMIOPORTOUTSTRING) pfnOutStrCallback;
188 /** Pointer to string IN callback function. */
189 R3PTRTYPE(PFNIOMIOPORTINSTRING) pfnInStrCallback;
190 /** Description / Name. For easing debugging. */
191 R3PTRTYPE(const char *) pszDesc;
192} IOMIOPORTRANGER3;
193/** Pointer to I/O port range descriptor, R3 version. */
194typedef IOMIOPORTRANGER3 *PIOMIOPORTRANGER3;
195
196/**
197 * I/O port range descriptor, R0 version.
198 */
199typedef struct IOMIOPORTRANGER0
200{
201 /** Avl node core with Port as Key and Port + cPorts - 1 as KeyLast. */
202 AVLROIOPORTNODECORE Core;
203 /** Start I/O port address. */
204 RTIOPORT Port;
205 /** Size of the range. */
206 uint16_t cPorts;
207 /** Pointer to user argument. */
208 RTR0PTR pvUser;
209 /** Pointer to the associated device instance. */
210 R0PTRTYPE(PPDMDEVINS) pDevIns;
211 /** Pointer to OUT callback function. */
212 R0PTRTYPE(PFNIOMIOPORTOUT) pfnOutCallback;
213 /** Pointer to IN callback function. */
214 R0PTRTYPE(PFNIOMIOPORTIN) pfnInCallback;
215 /** Pointer to string OUT callback function. */
216 R0PTRTYPE(PFNIOMIOPORTOUTSTRING) pfnOutStrCallback;
217 /** Pointer to string IN callback function. */
218 R0PTRTYPE(PFNIOMIOPORTINSTRING) pfnInStrCallback;
219 /** Description / Name. For easing debugging. */
220 R3PTRTYPE(const char *) pszDesc;
221} IOMIOPORTRANGER0;
222/** Pointer to I/O port range descriptor, R0 version. */
223typedef IOMIOPORTRANGER0 *PIOMIOPORTRANGER0;
224
225/**
226 * I/O port range descriptor.
227 */
228typedef struct IOMIOPORTRANGEGC
229{
230 /** Avl node core with Port as Key and Port + cPorts - 1 as KeyLast. */
231 AVLROIOPORTNODECORE Core;
232 /** Start I/O port address. */
233 RTIOPORT Port;
234 /** Size of the range. */
235 uint16_t cPorts;
236 /** Pointer to user argument. */
237 RTGCPTR pvUser;
238 /** Pointer to the associated device instance. */
239 GCPTRTYPE(PPDMDEVINS) pDevIns;
240 /** Pointer to OUT callback function. */
241 GCPTRTYPE(PFNIOMIOPORTOUT) pfnOutCallback;
242 /** Pointer to IN callback function. */
243 GCPTRTYPE(PFNIOMIOPORTIN) pfnInCallback;
244 /** Pointer to string OUT callback function. */
245 GCPTRTYPE(PFNIOMIOPORTOUTSTRING) pfnOutStrCallback;
246 /** Pointer to string IN callback function. */
247 GCPTRTYPE(PFNIOMIOPORTINSTRING) pfnInStrCallback;
248 /** Description / Name. For easing debugging. */
249 R3PTRTYPE(const char *) pszDesc;
250} IOMIOPORTRANGEGC;
251/** Pointer to I/O port range descriptor, GC version. */
252typedef IOMIOPORTRANGEGC *PIOMIOPORTRANGEGC;
253
254
255/**
256 * I/O port statistics. (one I/O port)
257 *
258 * This is a simple way of making on demand statistics, however it's a
259 * bit free with the hypervisor heap memory..
260 */
261typedef struct IOMIOPORTSTATS
262{
263 /** Avl node core with the port as Key. */
264 AVLOIOPORTNODECORE Core;
265 /** Number of INs to this port from R3. */
266 STAMCOUNTER InR3;
267 /** Number of OUTs to this port from R3. */
268 STAMCOUNTER OutR3;
269 /** Number of INs to this port from R0. */
270 STAMCOUNTER InR0;
271 /** Number of OUTs to this port from R0. */
272 STAMCOUNTER OutR0;
273 /** Number of INs to this port from GC. */
274 STAMCOUNTER InGC;
275 /** Number of OUTs to this port from GC. */
276 STAMCOUNTER OutGC;
277 /** Profiling IN handler overhead in R3. */
278 STAMPROFILEADV ProfInR3;
279 /** Profiling OUT handler overhead in R3. */
280 STAMPROFILEADV ProfOutR3;
281 /** Profiling IN handler overhead in R0. */
282 STAMPROFILEADV ProfInR0;
283 /** Profiling OUT handler overhead in R0. */
284 STAMPROFILEADV ProfOutR0;
285 /** Profiling IN handler overhead in GC. */
286 STAMPROFILEADV ProfInGC;
287 /** Profiling OUT handler overhead in GC. */
288 STAMPROFILEADV ProfOutGC;
289 /** Number of INs to this port from R0 which was serviced in R3. */
290 STAMCOUNTER InR0ToR3;
291 /** Number of OUTs to this port from R0 which was serviced in R3. */
292 STAMCOUNTER OutR0ToR3;
293 /** Number of INs to this port from GC which was serviced in R3. */
294 STAMCOUNTER InGCToR3;
295 /** Number of OUTs to this port from GC which was serviced in R3. */
296 STAMCOUNTER OutGCToR3;
297} IOMIOPORTSTATS;
298/** Pointer to I/O port statistics. */
299typedef IOMIOPORTSTATS *PIOMIOPORTSTATS;
300
301
302/**
303 * The IOM trees.
304 * These are offset based the nodes and root must be in the same
305 * memory block in HC. The locations of IOM structure and the hypervisor heap
306 * are quite different in HC and GC.
307 */
308typedef struct IOMTREES
309{
310 /** Tree containing I/O port range descriptors registered for HC (IOMIOPORTRANGEHC). */
311 AVLROIOPORTTREE IOPortTreeR3;
312 /** Tree containing I/O port range descriptors registered for R0 (IOMIOPORTRANGER0). */
313 AVLROIOPORTTREE IOPortTreeR0;
314 /** Tree containing I/O port range descriptors registered for GC (IOMIOPORTRANGEGC). */
315 AVLROIOPORTTREE IOPortTreeGC;
316
317 /** Tree containing MMIO range descriptors registered for HC (IOMMMIORANGEHC). */
318 AVLROGCPHYSTREE MMIOTreeR3;
319 /** Tree containing MMIO range descriptors registered for R0 (IOMMMIORANGER0). */
320 AVLROGCPHYSTREE MMIOTreeR0;
321 /** Tree containing MMIO range descriptors registered for GC (IOMMMIORANGEGC). */
322 AVLROGCPHYSTREE MMIOTreeGC;
323
324 /** Tree containing I/O port statistics (IOMIOPORTSTATS). */
325 AVLOIOPORTTREE IOPortStatTree;
326 /** Tree containing MMIO statistics (IOMMMIOSTATS). */
327 AVLOGCPHYSTREE MMIOStatTree;
328} IOMTREES;
329/** Pointer to the IOM trees. */
330typedef IOMTREES *PIOMTREES;
331
332
333/**
334 * Converts an IOM pointer into a VM pointer.
335 * @returns Pointer to the VM structure the PGM is part of.
336 * @param pIOM Pointer to IOM instance data.
337 */
338#define IOM2VM(pIOM) ( (PVM)((char*)pIOM - pIOM->offVM) )
339
340/**
341 * IOM Data (part of VM)
342 */
343typedef struct IOM
344{
345 /** Offset to the VM structure. */
346 RTINT offVM;
347
348 /** Pointer to the trees - GC ptr. */
349 GCPTRTYPE(PIOMTREES) pTreesGC;
350 /** Pointer to the trees - HC ptr. */
351 R3R0PTRTYPE(PIOMTREES) pTreesHC;
352
353
354 /** @name Caching of I/O Port ranges and statistics.
355 * (Saves quite some time in rep outs/ins instruction emulation.)
356 * @{ */
357 R3PTRTYPE(PIOMIOPORTRANGER3) pRangeLastReadR3;
358 R3PTRTYPE(PIOMIOPORTRANGER3) pRangeLastWriteR3;
359 R3PTRTYPE(PIOMIOPORTSTATS) pStatsLastReadR3;
360 R3PTRTYPE(PIOMIOPORTSTATS) pStatsLastWriteR3;
361
362 R3R0PTRTYPE(PIOMIOPORTRANGER0) pRangeLastReadR0;
363 R3R0PTRTYPE(PIOMIOPORTRANGER0) pRangeLastWriteR0;
364 R3R0PTRTYPE(PIOMIOPORTSTATS) pStatsLastReadR0;
365 R3R0PTRTYPE(PIOMIOPORTSTATS) pStatsLastWriteR0;
366
367 GCPTRTYPE(PIOMIOPORTRANGEGC) pRangeLastReadGC;
368 GCPTRTYPE(PIOMIOPORTRANGEGC) pRangeLastWriteGC;
369 GCPTRTYPE(PIOMIOPORTSTATS) pStatsLastReadGC;
370 GCPTRTYPE(PIOMIOPORTSTATS) pStatsLastWriteGC;
371 /** @} */
372
373 /** @name I/O Port statistics.
374 * @{ */
375 STAMPROFILE StatGCIOPortHandler;
376
377 STAMCOUNTER StatGCInstIn;
378 STAMCOUNTER StatGCInstOut;
379 STAMCOUNTER StatGCInstIns;
380 STAMCOUNTER StatGCInstOuts;
381 /** @} */
382
383 /** @name MMIO statistics.
384 * @{ */
385 STAMPROFILE StatGCMMIOHandler;
386 STAMCOUNTER StatGCMMIOFailures;
387
388 STAMPROFILE StatGCInstMov;
389 STAMPROFILE StatGCInstCmp;
390 STAMPROFILE StatGCInstAnd;
391 STAMPROFILE StatGCInstTest;
392 STAMPROFILE StatGCInstXchg;
393 STAMPROFILE StatGCInstStos;
394 STAMPROFILE StatGCInstLods;
395 STAMPROFILE StatGCInstMovs;
396 STAMPROFILE StatGCInstMovsToMMIO;
397 STAMPROFILE StatGCInstMovsFromMMIO;
398 STAMPROFILE StatGCInstMovsMMIO;
399 STAMCOUNTER StatGCInstOther;
400
401 STAMCOUNTER StatGCMMIO1Byte;
402 STAMCOUNTER StatGCMMIO2Bytes;
403 STAMCOUNTER StatGCMMIO4Bytes;
404
405 RTUINT cMovsMaxBytes;
406 RTUINT cStosMaxBytes;
407 /** @} */
408
409} IOM;
410/** Pointer to IOM instance data. */
411typedef IOM *PIOM;
412
413
414__BEGIN_DECLS
415
416#ifdef IN_IOM_R3
417PIOMIOPORTSTATS iomr3IOPortStatsCreate(PVM pVM, RTIOPORT Port, const char *pszDesc);
418PIOMMMIOSTATS iomR3MMIOStatsCreate(PVM pVM, RTGCPHYS GCPhys, const char *pszDesc);
419#endif /* IN_IOM_R3 */
420
421/**
422 * \#PF Handler callback for MMIO ranges.
423 *
424 * @returns VBox status code (appropriate for GC return).
425 *
426 * @param pVM VM Handle.
427 * @param uErrorCode CPU Error code.
428 * @param pRegFrame Trap register frame.
429 * @param pvFault The fault address (cr2).
430 * @param GCPhysFault The GC physical address corresponding to pvFault.
431 * @param pvUser Pointer to the MMIO range entry.
432 */
433IOMDECL(int) IOMMMIOHandler(PVM pVM, RTGCUINT uErrorCode, PCPUMCTXCORE pRegFrame, void *pvFault, RTGCPHYS GCPhysFault, void *pvUser);
434
435/**
436 * Gets the I/O port range for the specified I/O port in the current context.
437 *
438 * @returns Pointer to I/O port range.
439 * @returns NULL if no port registered.
440 *
441 * @param pIOM IOM instance data.
442 * @param Port Port to lookup.
443 */
444inline CTXALLSUFF(PIOMIOPORTRANGE) iomIOPortGetRange(PIOM pIOM, RTIOPORT Port)
445{
446 CTXALLSUFF(PIOMIOPORTRANGE) pRange = (CTXALLSUFF(PIOMIOPORTRANGE))RTAvlroIOPortRangeGet(&pIOM->CTXSUFF(pTrees)->CTXALLSUFF(IOPortTree), Port);
447 return pRange;
448}
449
450/**
451 * Gets the I/O port range for the specified I/O port in the HC.
452 *
453 * @returns Pointer to I/O port range.
454 * @returns NULL if no port registered.
455 *
456 * @param pIOM IOM instance data.
457 * @param Port Port to lookup.
458 */
459inline PIOMIOPORTRANGER3 iomIOPortGetRangeHC(PIOM pIOM, RTIOPORT Port)
460{
461 PIOMIOPORTRANGER3 pRange = (PIOMIOPORTRANGER3)RTAvlroIOPortRangeGet(&pIOM->CTXSUFF(pTrees)->IOPortTreeR3, Port);
462 return pRange;
463}
464
465
466/**
467 * Gets the MMIO range for the specified physical address in the current context.
468 *
469 * @returns Pointer to MMIO range.
470 * @returns NULL if address not in a MMIO range.
471 *
472 * @param pIOM IOM instance data.
473 * @param GCPhys Physical address to lookup.
474 */
475inline CTXALLSUFF(PIOMMMIORANGE) iomMMIOGetRange(PIOM pIOM, RTGCPHYS GCPhys)
476{
477 CTXALLSUFF(PIOMMMIORANGE) pRange = (CTXALLSUFF(PIOMMMIORANGE))RTAvlroGCPhysRangeGet(&pIOM->CTXSUFF(pTrees)->CTXALLSUFF(MMIOTree), GCPhys);
478 return pRange;
479}
480
481
482/**
483 * Gets the MMIO range for the specified physical address in the current context.
484 *
485 * @returns Pointer to MMIO range.
486 * @returns NULL if address not in a MMIO range.
487 *
488 * @param pIOM IOM instance data.
489 * @param GCPhys Physical address to lookup.
490 */
491inline PIOMMMIORANGER3 iomMMIOGetRangeHC(PIOM pIOM, RTGCPHYS GCPhys)
492{
493 PIOMMMIORANGER3 pRange = (PIOMMMIORANGER3)RTAvlroGCPhysRangeGet(&pIOM->CTXSUFF(pTrees)->MMIOTreeR3, GCPhys);
494 return pRange;
495}
496
497#ifdef VBOX_WITH_STATISTICS
498/**
499 * Gets the MMIO statistics record.
500 * @returns Pointer to MMIO stats.
501 * @returns NULL if not found.
502 *
503 * @param pIOM IOM instance data.
504 * @param GCPhys Physical address to lookup.
505 */
506inline PIOMMMIOSTATS iomMMIOGetStats(PIOM pIOM, RTGCPHYS GCPhys)
507{
508 PIOMMMIOSTATS pStats = (PIOMMMIOSTATS)RTAvloGCPhysGet(&pIOM->CTXSUFF(pTrees)->MMIOStatTree, GCPhys);
509 return pStats;
510}
511#endif
512
513__END_DECLS
514
515#ifdef IN_RING3
516
517#endif
518
519/** @} */
520
521#endif /* ___IOMInternal_h */
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