VirtualBox

source: vbox/trunk/include/VBox/vmm/pdmdev.h@ 35810

Last change on this file since 35810 was 35810, checked in by vboxsync, 14 years ago

VMM: Replace most VERR_VERSION_MISMATCH by more specific error statuses. Translating the errors returned by device, driver and USB device constructors into specific ones for the benefit of old extension pack and misc use of the status.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 179.3 KB
Line 
1/** @file
2 * PDM - Pluggable Device Manager, Devices.
3 */
4
5/*
6 * Copyright (C) 2006-2011 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_pdmdev_h
27#define ___VBox_vmm_pdmdev_h
28
29#include <VBox/vmm/pdmqueue.h>
30#include <VBox/vmm/pdmcritsect.h>
31#include <VBox/vmm/pdmthread.h>
32#include <VBox/vmm/pdmifs.h>
33#include <VBox/vmm/pdmins.h>
34#include <VBox/vmm/pdmcommon.h>
35#include <VBox/vmm/iom.h>
36#include <VBox/vmm/tm.h>
37#include <VBox/vmm/ssm.h>
38#include <VBox/vmm/cfgm.h>
39#include <VBox/vmm/dbgf.h>
40#include <VBox/err.h>
41#include <VBox/pci.h>
42#include <iprt/stdarg.h>
43
44
45RT_C_DECLS_BEGIN
46
47/** @defgroup grp_pdm_device The PDM Devices API
48 * @ingroup grp_pdm
49 * @{
50 */
51
52/**
53 * Construct a device instance for a VM.
54 *
55 * @returns VBox status.
56 * @param pDevIns The device instance data. If the registration structure
57 * is needed, it can be accessed thru pDevIns->pReg.
58 * @param iInstance Instance number. Use this to figure out which registers
59 * and such to use. The instance number is also found in
60 * pDevIns->iInstance, but since it's likely to be
61 * frequently used PDM passes it as parameter.
62 * @param pCfg Configuration node handle for the driver. This is
63 * expected to be in high demand in the constructor and is
64 * therefore passed as an argument. When using it at other
65 * times, it can be found in pDrvIns->pCfg.
66 */
67typedef DECLCALLBACK(int) FNPDMDEVCONSTRUCT(PPDMDEVINS pDevIns, int iInstance, PCFGMNODE pCfg);
68/** Pointer to a FNPDMDEVCONSTRUCT() function. */
69typedef FNPDMDEVCONSTRUCT *PFNPDMDEVCONSTRUCT;
70
71/**
72 * Destruct a device instance.
73 *
74 * Most VM resources are freed by the VM. This callback is provided so that any non-VM
75 * resources can be freed correctly.
76 *
77 * @returns VBox status.
78 * @param pDevIns The device instance data.
79 */
80typedef DECLCALLBACK(int) FNPDMDEVDESTRUCT(PPDMDEVINS pDevIns);
81/** Pointer to a FNPDMDEVDESTRUCT() function. */
82typedef FNPDMDEVDESTRUCT *PFNPDMDEVDESTRUCT;
83
84/**
85 * Device relocation callback.
86 *
87 * This is called when the instance data has been relocated in raw-mode context
88 * (RC). It is also called when the RC hypervisor selects changes. The device
89 * must fixup all necessary pointers and re-query all interfaces to other RC
90 * devices and drivers.
91 *
92 * Before the RC code is executed the first time, this function will be called
93 * with a 0 delta so RC pointer calculations can be one in one place.
94 *
95 * @param pDevIns Pointer to the device instance.
96 * @param offDelta The relocation delta relative to the old location.
97 *
98 * @remark A relocation CANNOT fail.
99 */
100typedef DECLCALLBACK(void) FNPDMDEVRELOCATE(PPDMDEVINS pDevIns, RTGCINTPTR offDelta);
101/** Pointer to a FNPDMDEVRELOCATE() function. */
102typedef FNPDMDEVRELOCATE *PFNPDMDEVRELOCATE;
103
104/**
105 * Device I/O Control interface.
106 *
107 * This is used by external components, such as the COM interface, to
108 * communicate with devices using a class wide interface or a device
109 * specific interface.
110 *
111 * @returns VBox status code.
112 * @param pDevIns Pointer to the device instance.
113 * @param uFunction Function to perform.
114 * @param pvIn Pointer to input data.
115 * @param cbIn Size of input data.
116 * @param pvOut Pointer to output data.
117 * @param cbOut Size of output data.
118 * @param pcbOut Where to store the actual size of the output data.
119 */
120typedef DECLCALLBACK(int) FNPDMDEVIOCTL(PPDMDEVINS pDevIns, RTUINT uFunction,
121 void *pvIn, RTUINT cbIn,
122 void *pvOut, RTUINT cbOut, PRTUINT pcbOut);
123/** Pointer to a FNPDMDEVIOCTL() function. */
124typedef FNPDMDEVIOCTL *PFNPDMDEVIOCTL;
125
126/**
127 * Power On notification.
128 *
129 * @returns VBox status.
130 * @param pDevIns The device instance data.
131 */
132typedef DECLCALLBACK(void) FNPDMDEVPOWERON(PPDMDEVINS pDevIns);
133/** Pointer to a FNPDMDEVPOWERON() function. */
134typedef FNPDMDEVPOWERON *PFNPDMDEVPOWERON;
135
136/**
137 * Reset notification.
138 *
139 * @returns VBox status.
140 * @param pDevIns The device instance data.
141 */
142typedef DECLCALLBACK(void) FNPDMDEVRESET(PPDMDEVINS pDevIns);
143/** Pointer to a FNPDMDEVRESET() function. */
144typedef FNPDMDEVRESET *PFNPDMDEVRESET;
145
146/**
147 * Suspend notification.
148 *
149 * @returns VBox status.
150 * @param pDevIns The device instance data.
151 * @thread EMT(0)
152 */
153typedef DECLCALLBACK(void) FNPDMDEVSUSPEND(PPDMDEVINS pDevIns);
154/** Pointer to a FNPDMDEVSUSPEND() function. */
155typedef FNPDMDEVSUSPEND *PFNPDMDEVSUSPEND;
156
157/**
158 * Resume notification.
159 *
160 * @returns VBox status.
161 * @param pDevIns The device instance data.
162 */
163typedef DECLCALLBACK(void) FNPDMDEVRESUME(PPDMDEVINS pDevIns);
164/** Pointer to a FNPDMDEVRESUME() function. */
165typedef FNPDMDEVRESUME *PFNPDMDEVRESUME;
166
167/**
168 * Power Off notification.
169 *
170 * This is only called when the VMR3PowerOff call is made on a running VM. This
171 * means that there is no notification if the VM was suspended before being
172 * powered of. There will also be no callback when hot plugging devices.
173 *
174 * @param pDevIns The device instance data.
175 * @thread EMT(0)
176 */
177typedef DECLCALLBACK(void) FNPDMDEVPOWEROFF(PPDMDEVINS pDevIns);
178/** Pointer to a FNPDMDEVPOWEROFF() function. */
179typedef FNPDMDEVPOWEROFF *PFNPDMDEVPOWEROFF;
180
181/**
182 * Attach command.
183 *
184 * This is called to let the device attach to a driver for a specified LUN
185 * at runtime. This is not called during VM construction, the device
186 * constructor have to attach to all the available drivers.
187 *
188 * This is like plugging in the keyboard or mouse after turning on the PC.
189 *
190 * @returns VBox status code.
191 * @param pDevIns The device instance.
192 * @param iLUN The logical unit which is being detached.
193 * @param fFlags Flags, combination of the PDM_TACH_FLAGS_* \#defines.
194 */
195typedef DECLCALLBACK(int) FNPDMDEVATTACH(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags);
196/** Pointer to a FNPDMDEVATTACH() function. */
197typedef FNPDMDEVATTACH *PFNPDMDEVATTACH;
198
199/**
200 * Detach notification.
201 *
202 * This is called when a driver is detaching itself from a LUN of the device.
203 * The device should adjust it's state to reflect this.
204 *
205 * This is like unplugging the network cable to use it for the laptop or
206 * something while the PC is still running.
207 *
208 * @param pDevIns The device instance.
209 * @param iLUN The logical unit which is being detached.
210 * @param fFlags Flags, combination of the PDMDEVATT_FLAGS_* \#defines.
211 */
212typedef DECLCALLBACK(void) FNPDMDEVDETACH(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags);
213/** Pointer to a FNPDMDEVDETACH() function. */
214typedef FNPDMDEVDETACH *PFNPDMDEVDETACH;
215
216/**
217 * Query the base interface of a logical unit.
218 *
219 * @returns VBOX status code.
220 * @param pDevIns The device instance.
221 * @param iLUN The logicial unit to query.
222 * @param ppBase Where to store the pointer to the base interface of the LUN.
223 */
224typedef DECLCALLBACK(int) FNPDMDEVQUERYINTERFACE(PPDMDEVINS pDevIns, unsigned iLUN, PPDMIBASE *ppBase);
225/** Pointer to a FNPDMDEVQUERYINTERFACE() function. */
226typedef FNPDMDEVQUERYINTERFACE *PFNPDMDEVQUERYINTERFACE;
227
228/**
229 * Init complete notification.
230 * This can be done to do communication with other devices and other
231 * initialization which requires everything to be in place.
232 *
233 * @returns VBOX status code.
234 * @param pDevIns The device instance.
235 */
236typedef DECLCALLBACK(int) FNPDMDEVINITCOMPLETE(PPDMDEVINS pDevIns);
237/** Pointer to a FNPDMDEVINITCOMPLETE() function. */
238typedef FNPDMDEVINITCOMPLETE *PFNPDMDEVINITCOMPLETE;
239
240
241
242/**
243 * PDM Device Registration Structure.
244 *
245 * This structure is used when registering a device from VBoxInitDevices() in HC
246 * Ring-3. PDM will continue use till the VM is terminated.
247 */
248typedef struct PDMDEVREG
249{
250 /** Structure version. PDM_DEVREG_VERSION defines the current version. */
251 uint32_t u32Version;
252 /** Device name. */
253 char szName[32];
254 /** Name of the raw-mode context module (no path).
255 * Only evalutated if PDM_DEVREG_FLAGS_RC is set. */
256 char szRCMod[32];
257 /** Name of the ring-0 module (no path).
258 * Only evalutated if PDM_DEVREG_FLAGS_R0 is set. */
259 char szR0Mod[32];
260 /** The description of the device. The UTF-8 string pointed to shall, like this structure,
261 * remain unchanged from registration till VM destruction. */
262 const char *pszDescription;
263
264 /** Flags, combination of the PDM_DEVREG_FLAGS_* \#defines. */
265 uint32_t fFlags;
266 /** Device class(es), combination of the PDM_DEVREG_CLASS_* \#defines. */
267 uint32_t fClass;
268 /** Maximum number of instances (per VM). */
269 uint32_t cMaxInstances;
270 /** Size of the instance data. */
271 uint32_t cbInstance;
272
273 /** Construct instance - required. */
274 PFNPDMDEVCONSTRUCT pfnConstruct;
275 /** Destruct instance - optional. */
276 PFNPDMDEVDESTRUCT pfnDestruct;
277 /** Relocation command - optional. */
278 PFNPDMDEVRELOCATE pfnRelocate;
279 /** I/O Control interface - optional. */
280 PFNPDMDEVIOCTL pfnIOCtl;
281 /** Power on notification - optional. */
282 PFNPDMDEVPOWERON pfnPowerOn;
283 /** Reset notification - optional. */
284 PFNPDMDEVRESET pfnReset;
285 /** Suspend notification - optional. */
286 PFNPDMDEVSUSPEND pfnSuspend;
287 /** Resume notification - optional. */
288 PFNPDMDEVRESUME pfnResume;
289 /** Attach command - optional. */
290 PFNPDMDEVATTACH pfnAttach;
291 /** Detach notification - optional. */
292 PFNPDMDEVDETACH pfnDetach;
293 /** Query a LUN base interface - optional. */
294 PFNPDMDEVQUERYINTERFACE pfnQueryInterface;
295 /** Init complete notification - optional. */
296 PFNPDMDEVINITCOMPLETE pfnInitComplete;
297 /** Power off notification - optional. */
298 PFNPDMDEVPOWEROFF pfnPowerOff;
299 /** @todo */
300 PFNRT pfnSoftReset;
301 /** Initialization safty marker. */
302 uint32_t u32VersionEnd;
303} PDMDEVREG;
304/** Pointer to a PDM Device Structure. */
305typedef PDMDEVREG *PPDMDEVREG;
306/** Const pointer to a PDM Device Structure. */
307typedef PDMDEVREG const *PCPDMDEVREG;
308
309/** Current DEVREG version number. */
310#define PDM_DEVREG_VERSION PDM_VERSION_MAKE(0xffff, 1, 0)
311
312/** PDM Device Flags.
313 * @{ */
314/** This flag is used to indicate that the device has a RC component. */
315#define PDM_DEVREG_FLAGS_RC 0x00000001
316/** This flag is used to indicate that the device has a R0 component. */
317#define PDM_DEVREG_FLAGS_R0 0x00000002
318
319/** @def PDM_DEVREG_FLAGS_HOST_BITS_DEFAULT
320 * The bit count for the current host. */
321#if HC_ARCH_BITS == 32
322# define PDM_DEVREG_FLAGS_HOST_BITS_DEFAULT 0x00000010
323#elif HC_ARCH_BITS == 64
324# define PDM_DEVREG_FLAGS_HOST_BITS_DEFAULT 0x00000020
325#else
326# error Unsupported HC_ARCH_BITS value.
327#endif
328/** The host bit count mask. */
329#define PDM_DEVREG_FLAGS_HOST_BITS_MASK 0x00000030
330
331/** The device support only 32-bit guests. */
332#define PDM_DEVREG_FLAGS_GUEST_BITS_32 0x00000100
333/** The device support only 64-bit guests. */
334#define PDM_DEVREG_FLAGS_GUEST_BITS_64 0x00000200
335/** The device support both 32-bit & 64-bit guests. */
336#define PDM_DEVREG_FLAGS_GUEST_BITS_32_64 0x00000300
337/** @def PDM_DEVREG_FLAGS_GUEST_BITS_DEFAULT
338 * The guest bit count for the current compilation. */
339#if GC_ARCH_BITS == 32
340# define PDM_DEVREG_FLAGS_GUEST_BITS_DEFAULT PDM_DEVREG_FLAGS_GUEST_BITS_32
341#elif GC_ARCH_BITS == 64
342# define PDM_DEVREG_FLAGS_GUEST_BITS_DEFAULT PDM_DEVREG_FLAGS_GUEST_BITS_32_64
343#else
344# error Unsupported GC_ARCH_BITS value.
345#endif
346/** The guest bit count mask. */
347#define PDM_DEVREG_FLAGS_GUEST_BITS_MASK 0x00000300
348
349/** A convenience. */
350#define PDM_DEVREG_FLAGS_DEFAULT_BITS (PDM_DEVREG_FLAGS_GUEST_BITS_DEFAULT | PDM_DEVREG_FLAGS_HOST_BITS_DEFAULT)
351
352/** Indicates that the devices support PAE36 on a 32-bit guest. */
353#define PDM_DEVREG_FLAGS_PAE36 0x00001000
354
355/** Indicates that the device needs to be notified before the drivers when suspending. */
356#define PDM_DEVREG_FLAGS_FIRST_SUSPEND_NOTIFICATION 0x00002000
357
358/** Indicates that the device needs to be notified before the drivers when powering off. */
359#define PDM_DEVREG_FLAGS_FIRST_POWEROFF_NOTIFICATION 0x00004000
360/** @} */
361
362
363/** PDM Device Classes.
364 * The order is important, lower bit earlier instantiation.
365 * @{ */
366/** Architecture device. */
367#define PDM_DEVREG_CLASS_ARCH RT_BIT(0)
368/** Architecture BIOS device. */
369#define PDM_DEVREG_CLASS_ARCH_BIOS RT_BIT(1)
370/** PCI bus brigde. */
371#define PDM_DEVREG_CLASS_BUS_PCI RT_BIT(2)
372/** ISA bus brigde. */
373#define PDM_DEVREG_CLASS_BUS_ISA RT_BIT(3)
374/** Input device (mouse, keyboard, joystick, HID, ...). */
375#define PDM_DEVREG_CLASS_INPUT RT_BIT(4)
376/** Interrupt controller (PIC). */
377#define PDM_DEVREG_CLASS_PIC RT_BIT(5)
378/** Interval controoler (PIT). */
379#define PDM_DEVREG_CLASS_PIT RT_BIT(6)
380/** RTC/CMOS. */
381#define PDM_DEVREG_CLASS_RTC RT_BIT(7)
382/** DMA controller. */
383#define PDM_DEVREG_CLASS_DMA RT_BIT(8)
384/** VMM Device. */
385#define PDM_DEVREG_CLASS_VMM_DEV RT_BIT(9)
386/** Graphics device, like VGA. */
387#define PDM_DEVREG_CLASS_GRAPHICS RT_BIT(10)
388/** Storage controller device. */
389#define PDM_DEVREG_CLASS_STORAGE RT_BIT(11)
390/** Network interface controller. */
391#define PDM_DEVREG_CLASS_NETWORK RT_BIT(12)
392/** Audio. */
393#define PDM_DEVREG_CLASS_AUDIO RT_BIT(13)
394/** USB HIC. */
395#define PDM_DEVREG_CLASS_BUS_USB RT_BIT(14)
396/** ACPI. */
397#define PDM_DEVREG_CLASS_ACPI RT_BIT(15)
398/** Serial controller device. */
399#define PDM_DEVREG_CLASS_SERIAL RT_BIT(16)
400/** Parallel controller device */
401#define PDM_DEVREG_CLASS_PARALLEL RT_BIT(17)
402/** Host PCI pass-through device */
403#define PDM_DEVREG_CLASS_HOST_DEV RT_BIT(18)
404/** Misc devices (always last). */
405#define PDM_DEVREG_CLASS_MISC RT_BIT(31)
406/** @} */
407
408
409/** @name IRQ Level for use with the *SetIrq APIs.
410 * @{
411 */
412/** Assert the IRQ (can assume value 1). */
413#define PDM_IRQ_LEVEL_HIGH RT_BIT(0)
414/** Deassert the IRQ (can assume value 0). */
415#define PDM_IRQ_LEVEL_LOW 0
416/** flip-flop - deassert and then assert the IRQ again immediately. */
417#define PDM_IRQ_LEVEL_FLIP_FLOP (RT_BIT(1) | PDM_IRQ_LEVEL_HIGH)
418/** @} */
419
420/**
421 * Registration record for MSI.
422 */
423typedef struct PDMMSIREG
424{
425 /** Number of MSI interrupt vectors, 0 if MSI not supported */
426 uint16_t cMsiVectors;
427 /** Offset of MSI capability */
428 uint8_t iMsiCapOffset;
429 /** Offset of next capability to MSI */
430 uint8_t iMsiNextOffset;
431 /** If we support 64-bit MSI addressing */
432 bool fMsi64bit;
433
434 /** Number of MSI-X interrupt vectors, 0 if MSI-X not supported */
435 uint16_t cMsixVectors;
436 /** Offset of MSI-X capability */
437 uint8_t iMsixCapOffset;
438 /** Offset of next capability to MSI-X */
439 uint8_t iMsixNextOffset;
440 /** Value of PCI BAR (base addresss register) assigned by device for MSI-X page access */
441 uint8_t iMsixBar;
442} PDMMSIREG;
443typedef PDMMSIREG *PPDMMSIREG;
444
445/**
446 * PCI Bus registration structure.
447 * All the callbacks, except the PCIBIOS hack, are working on PCI devices.
448 */
449typedef struct PDMPCIBUSREG
450{
451 /** Structure version number. PDM_PCIBUSREG_VERSION defines the current version. */
452 uint32_t u32Version;
453
454 /**
455 * Registers the device with the default PCI bus.
456 *
457 * @returns VBox status code.
458 * @param pDevIns Device instance of the PCI Bus.
459 * @param pPciDev The PCI device structure.
460 * Any PCI enabled device must keep this in it's instance data!
461 * Fill in the PCI data config before registration, please.
462 * @param pszName Pointer to device name (permanent, readonly). For debugging, not unique.
463 * @param iDev The device number ((dev << 3) | function) the device should have on the bus.
464 * If negative, the pci bus device will assign one.
465 */
466 DECLR3CALLBACKMEMBER(int, pfnRegisterR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, const char *pszName, int iDev));
467
468 /**
469 * Initialize MSI support in a PCI device.
470 *
471 * @returns VBox status code.
472 * @param pDevIns Device instance of the PCI Bus.
473 * @param pPciDev The PCI device structure.
474 * @param pMsiReg MSI registration structure
475 */
476 DECLR3CALLBACKMEMBER(int, pfnRegisterMsiR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PPDMMSIREG pMsiReg));
477
478 /**
479 * Registers a I/O region (memory mapped or I/O ports) for a PCI device.
480 *
481 * @returns VBox status code.
482 * @param pDevIns Device instance of the PCI Bus.
483 * @param pPciDev The PCI device structure.
484 * @param iRegion The region number.
485 * @param cbRegion Size of the region.
486 * @param iType PCI_ADDRESS_SPACE_MEM, PCI_ADDRESS_SPACE_IO or PCI_ADDRESS_SPACE_MEM_PREFETCH.
487 * @param pfnCallback Callback for doing the mapping.
488 */
489 DECLR3CALLBACKMEMBER(int, pfnIORegionRegisterR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, int iRegion, uint32_t cbRegion, PCIADDRESSSPACE enmType, PFNPCIIOREGIONMAP pfnCallback));
490
491 /**
492 * Register PCI configuration space read/write callbacks.
493 *
494 * @param pDevIns Device instance of the PCI Bus.
495 * @param pPciDev The PCI device structure.
496 * @param pfnRead Pointer to the user defined PCI config read function.
497 * @param ppfnReadOld Pointer to function pointer which will receive the old (default)
498 * PCI config read function. This way, user can decide when (and if)
499 * to call default PCI config read function. Can be NULL.
500 * @param pfnWrite Pointer to the user defined PCI config write function.
501 * @param pfnWriteOld Pointer to function pointer which will receive the old (default)
502 * PCI config write function. This way, user can decide when (and if)
503 * to call default PCI config write function. Can be NULL.
504 * @thread EMT
505 */
506 DECLR3CALLBACKMEMBER(void, pfnSetConfigCallbacksR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PFNPCICONFIGREAD pfnRead, PPFNPCICONFIGREAD ppfnReadOld,
507 PFNPCICONFIGWRITE pfnWrite, PPFNPCICONFIGWRITE ppfnWriteOld));
508
509 /**
510 * Set the IRQ for a PCI device.
511 *
512 * @param pDevIns Device instance of the PCI Bus.
513 * @param pPciDev The PCI device structure.
514 * @param iIrq IRQ number to set.
515 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
516 */
517 DECLR3CALLBACKMEMBER(void, pfnSetIrqR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, int iIrq, int iLevel));
518
519 /**
520 * Saves a state of the PCI device.
521 *
522 * @returns VBox status code.
523 * @param pDevIns Device instance of the PCI Bus.
524 * @param pPciDev Pointer to PCI device.
525 * @param pSSMHandle The handle to save the state to.
526 */
527 DECLR3CALLBACKMEMBER(int, pfnSaveExecR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PSSMHANDLE pSSMHandle));
528
529 /**
530 * Loads a saved PCI device state.
531 *
532 * @returns VBox status code.
533 * @param pDevIns Device instance of the PCI Bus.
534 * @param pPciDev Pointer to PCI device.
535 * @param pSSMHandle The handle to the saved state.
536 */
537 DECLR3CALLBACKMEMBER(int, pfnLoadExecR3,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PSSMHANDLE pSSMHandle));
538
539 /**
540 * Called to perform the job of the bios.
541 * This is only called for the first PCI Bus - it is expected to
542 * service all the PCI buses.
543 *
544 * @returns VBox status.
545 * @param pDevIns Device instance of the first bus.
546 */
547 DECLR3CALLBACKMEMBER(int, pfnFakePCIBIOSR3,(PPDMDEVINS pDevIns));
548
549 /** The name of the SetIrq RC entry point. */
550 const char *pszSetIrqRC;
551
552 /** The name of the SetIrq R0 entry point. */
553 const char *pszSetIrqR0;
554
555} PDMPCIBUSREG;
556/** Pointer to a PCI bus registration structure. */
557typedef PDMPCIBUSREG *PPDMPCIBUSREG;
558
559/** Current PDMPCIBUSREG version number. */
560#define PDM_PCIBUSREG_VERSION PDM_VERSION_MAKE(0xfffe, 2, 0)
561
562/**
563 * PCI Bus RC helpers.
564 */
565typedef struct PDMPCIHLPRC
566{
567 /** Structure version. PDM_PCIHLPRC_VERSION defines the current version. */
568 uint32_t u32Version;
569
570 /**
571 * Set an ISA IRQ.
572 *
573 * @param pDevIns PCI device instance.
574 * @param iIrq IRQ number to set.
575 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
576 * @thread EMT only.
577 */
578 DECLRCCALLBACKMEMBER(void, pfnIsaSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
579
580 /**
581 * Set an I/O-APIC IRQ.
582 *
583 * @param pDevIns PCI device instance.
584 * @param iIrq IRQ number to set.
585 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
586 * @thread EMT only.
587 */
588 DECLRCCALLBACKMEMBER(void, pfnIoApicSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
589
590 /**
591 * Send an MSI.
592 *
593 * @param pDevIns PCI device instance.
594 * @param GCAddr Physical address MSI request was written.
595 * @param uValue Value written.
596 * @thread EMT only.
597 */
598 DECLRCCALLBACKMEMBER(void, pfnIoApicSendMsi,(PPDMDEVINS pDevIns, RTGCPHYS GCAddr, uint32_t uValue));
599
600
601 /**
602 * Acquires the PDM lock.
603 *
604 * @returns VINF_SUCCESS on success.
605 * @returns rc if we failed to acquire the lock.
606 * @param pDevIns The PCI device instance.
607 * @param rc What to return if we fail to acquire the lock.
608 */
609 DECLRCCALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
610
611 /**
612 * Releases the PDM lock.
613 *
614 * @param pDevIns The PCI device instance.
615 */
616 DECLRCCALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
617
618 /** Just a safety precaution. */
619 uint32_t u32TheEnd;
620} PDMPCIHLPRC;
621/** Pointer to PCI helpers. */
622typedef RCPTRTYPE(PDMPCIHLPRC *) PPDMPCIHLPRC;
623/** Pointer to const PCI helpers. */
624typedef RCPTRTYPE(const PDMPCIHLPRC *) PCPDMPCIHLPRC;
625
626/** Current PDMPCIHLPRC version number. */
627#define PDM_PCIHLPRC_VERSION PDM_VERSION_MAKE(0xfffd, 2, 0)
628
629
630/**
631 * PCI Bus R0 helpers.
632 */
633typedef struct PDMPCIHLPR0
634{
635 /** Structure version. PDM_PCIHLPR0_VERSION defines the current version. */
636 uint32_t u32Version;
637
638 /**
639 * Set an ISA IRQ.
640 *
641 * @param pDevIns PCI device instance.
642 * @param iIrq IRQ number to set.
643 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
644 * @thread EMT only.
645 */
646 DECLR0CALLBACKMEMBER(void, pfnIsaSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
647
648 /**
649 * Set an I/O-APIC IRQ.
650 *
651 * @param pDevIns PCI device instance.
652 * @param iIrq IRQ number to set.
653 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
654 * @thread EMT only.
655 */
656 DECLR0CALLBACKMEMBER(void, pfnIoApicSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
657
658 /**
659 * Send an MSI.
660 *
661 * @param pDevIns PCI device instance.
662 * @param GCAddr Physical address MSI request was written.
663 * @param uValue Value written.
664 * @thread EMT only.
665 */
666 DECLR0CALLBACKMEMBER(void, pfnIoApicSendMsi,(PPDMDEVINS pDevIns, RTGCPHYS GCAddr, uint32_t uValue));
667
668
669 /**
670 * Acquires the PDM lock.
671 *
672 * @returns VINF_SUCCESS on success.
673 * @returns rc if we failed to acquire the lock.
674 * @param pDevIns The PCI device instance.
675 * @param rc What to return if we fail to acquire the lock.
676 */
677 DECLR0CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
678
679 /**
680 * Releases the PDM lock.
681 *
682 * @param pDevIns The PCI device instance.
683 */
684 DECLR0CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
685
686 /** Just a safety precaution. */
687 uint32_t u32TheEnd;
688} PDMPCIHLPR0;
689/** Pointer to PCI helpers. */
690typedef R0PTRTYPE(PDMPCIHLPR0 *) PPDMPCIHLPR0;
691/** Pointer to const PCI helpers. */
692typedef R0PTRTYPE(const PDMPCIHLPR0 *) PCPDMPCIHLPR0;
693
694/** Current PDMPCIHLPR0 version number. */
695#define PDM_PCIHLPR0_VERSION PDM_VERSION_MAKE(0xfffc, 2, 0)
696
697/**
698 * PCI device helpers.
699 */
700typedef struct PDMPCIHLPR3
701{
702 /** Structure version. PDM_PCIHLPR3_VERSION defines the current version. */
703 uint32_t u32Version;
704
705 /**
706 * Set an ISA IRQ.
707 *
708 * @param pDevIns The PCI device instance.
709 * @param iIrq IRQ number to set.
710 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
711 * @thread EMT only.
712 */
713 DECLR3CALLBACKMEMBER(void, pfnIsaSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
714
715 /**
716 * Set an I/O-APIC IRQ.
717 *
718 * @param pDevIns The PCI device instance.
719 * @param iIrq IRQ number to set.
720 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
721 * @thread EMT only.
722 */
723 DECLR3CALLBACKMEMBER(void, pfnIoApicSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
724
725 /**
726 * Send an MSI.
727 *
728 * @param pDevIns PCI device instance.
729 * @param GCAddr Physical address MSI request was written.
730 * @param uValue Value written.
731 * @thread EMT only.
732 */
733 DECLR3CALLBACKMEMBER(void, pfnIoApicSendMsi,(PPDMDEVINS pDevIns, RTGCPHYS GCAddr, uint32_t uValue));
734
735 /**
736 * Checks if the given address is an MMIO2 base address or not.
737 *
738 * @returns true/false accordingly.
739 * @param pDevIns The PCI device instance.
740 * @param pOwner The owner of the memory, optional.
741 * @param GCPhys The address to check.
742 */
743 DECLR3CALLBACKMEMBER(bool, pfnIsMMIO2Base,(PPDMDEVINS pDevIns, PPDMDEVINS pOwner, RTGCPHYS GCPhys));
744
745 /**
746 * Gets the address of the RC PCI Bus helpers.
747 *
748 * This should be called at both construction and relocation time
749 * to obtain the correct address of the RC helpers.
750 *
751 * @returns RC pointer to the PCI Bus helpers.
752 * @param pDevIns Device instance of the PCI Bus.
753 * @thread EMT only.
754 */
755 DECLR3CALLBACKMEMBER(PCPDMPCIHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
756
757 /**
758 * Gets the address of the R0 PCI Bus helpers.
759 *
760 * This should be called at both construction and relocation time
761 * to obtain the correct address of the R0 helpers.
762 *
763 * @returns R0 pointer to the PCI Bus helpers.
764 * @param pDevIns Device instance of the PCI Bus.
765 * @thread EMT only.
766 */
767 DECLR3CALLBACKMEMBER(PCPDMPCIHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
768
769 /**
770 * Acquires the PDM lock.
771 *
772 * @returns VINF_SUCCESS on success.
773 * @returns Fatal error on failure.
774 * @param pDevIns The PCI device instance.
775 * @param rc Dummy for making the interface identical to the RC and R0 versions.
776 */
777 DECLR3CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
778
779 /**
780 * Releases the PDM lock.
781 *
782 * @param pDevIns The PCI device instance.
783 */
784 DECLR3CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
785
786 /** Just a safety precaution. */
787 uint32_t u32TheEnd;
788} PDMPCIHLPR3;
789/** Pointer to PCI helpers. */
790typedef R3PTRTYPE(PDMPCIHLPR3 *) PPDMPCIHLPR3;
791/** Pointer to const PCI helpers. */
792typedef R3PTRTYPE(const PDMPCIHLPR3 *) PCPDMPCIHLPR3;
793
794/** Current PDMPCIHLPR3 version number. */
795#define PDM_PCIHLPR3_VERSION PDM_VERSION_MAKE(0xfffb, 2, 0)
796
797
798/**
799 * Programmable Interrupt Controller registration structure.
800 */
801typedef struct PDMPICREG
802{
803 /** Structure version number. PDM_PICREG_VERSION defines the current version. */
804 uint32_t u32Version;
805
806 /**
807 * Set the an IRQ.
808 *
809 * @param pDevIns Device instance of the PIC.
810 * @param iIrq IRQ number to set.
811 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
812 */
813 DECLR3CALLBACKMEMBER(void, pfnSetIrqR3,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
814
815 /**
816 * Get a pending interrupt.
817 *
818 * @returns Pending interrupt number.
819 * @param pDevIns Device instance of the PIC.
820 */
821 DECLR3CALLBACKMEMBER(int, pfnGetInterruptR3,(PPDMDEVINS pDevIns));
822
823 /** The name of the RC SetIrq entry point. */
824 const char *pszSetIrqRC;
825 /** The name of the RC GetInterrupt entry point. */
826 const char *pszGetInterruptRC;
827
828 /** The name of the R0 SetIrq entry point. */
829 const char *pszSetIrqR0;
830 /** The name of the R0 GetInterrupt entry point. */
831 const char *pszGetInterruptR0;
832} PDMPICREG;
833/** Pointer to a PIC registration structure. */
834typedef PDMPICREG *PPDMPICREG;
835
836/** Current PDMPICREG version number. */
837#define PDM_PICREG_VERSION PDM_VERSION_MAKE(0xfffa, 1, 0)
838
839/**
840 * PIC RC helpers.
841 */
842typedef struct PDMPICHLPRC
843{
844 /** Structure version. PDM_PICHLPRC_VERSION defines the current version. */
845 uint32_t u32Version;
846
847 /**
848 * Set the interrupt force action flag.
849 *
850 * @param pDevIns Device instance of the PIC.
851 */
852 DECLRCCALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns));
853
854 /**
855 * Clear the interrupt force action flag.
856 *
857 * @param pDevIns Device instance of the PIC.
858 */
859 DECLRCCALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns));
860
861 /**
862 * Acquires the PDM lock.
863 *
864 * @returns VINF_SUCCESS on success.
865 * @returns rc if we failed to acquire the lock.
866 * @param pDevIns The PIC device instance.
867 * @param rc What to return if we fail to acquire the lock.
868 */
869 DECLRCCALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
870
871 /**
872 * Releases the PDM lock.
873 *
874 * @param pDevIns The PIC device instance.
875 */
876 DECLRCCALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
877
878 /** Just a safety precaution. */
879 uint32_t u32TheEnd;
880} PDMPICHLPRC;
881
882/** Pointer to PIC RC helpers. */
883typedef RCPTRTYPE(PDMPICHLPRC *) PPDMPICHLPRC;
884/** Pointer to const PIC RC helpers. */
885typedef RCPTRTYPE(const PDMPICHLPRC *) PCPDMPICHLPRC;
886
887/** Current PDMPICHLPRC version number. */
888#define PDM_PICHLPRC_VERSION PDM_VERSION_MAKE(0xfff9, 1, 0)
889
890
891/**
892 * PIC R0 helpers.
893 */
894typedef struct PDMPICHLPR0
895{
896 /** Structure version. PDM_PICHLPR0_VERSION defines the current version. */
897 uint32_t u32Version;
898
899 /**
900 * Set the interrupt force action flag.
901 *
902 * @param pDevIns Device instance of the PIC.
903 */
904 DECLR0CALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns));
905
906 /**
907 * Clear the interrupt force action flag.
908 *
909 * @param pDevIns Device instance of the PIC.
910 */
911 DECLR0CALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns));
912
913 /**
914 * Acquires the PDM lock.
915 *
916 * @returns VINF_SUCCESS on success.
917 * @returns rc if we failed to acquire the lock.
918 * @param pDevIns The PIC device instance.
919 * @param rc What to return if we fail to acquire the lock.
920 */
921 DECLR0CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
922
923 /**
924 * Releases the PDM lock.
925 *
926 * @param pDevIns The PCI device instance.
927 */
928 DECLR0CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
929
930 /** Just a safety precaution. */
931 uint32_t u32TheEnd;
932} PDMPICHLPR0;
933
934/** Pointer to PIC R0 helpers. */
935typedef R0PTRTYPE(PDMPICHLPR0 *) PPDMPICHLPR0;
936/** Pointer to const PIC R0 helpers. */
937typedef R0PTRTYPE(const PDMPICHLPR0 *) PCPDMPICHLPR0;
938
939/** Current PDMPICHLPR0 version number. */
940#define PDM_PICHLPR0_VERSION PDM_VERSION_MAKE(0xfff8, 1, 0)
941
942/**
943 * PIC R3 helpers.
944 */
945typedef struct PDMPICHLPR3
946{
947 /** Structure version. PDM_PICHLP_VERSION defines the current version. */
948 uint32_t u32Version;
949
950 /**
951 * Set the interrupt force action flag.
952 *
953 * @param pDevIns Device instance of the PIC.
954 */
955 DECLR3CALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns));
956
957 /**
958 * Clear the interrupt force action flag.
959 *
960 * @param pDevIns Device instance of the PIC.
961 */
962 DECLR3CALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns));
963
964 /**
965 * Acquires the PDM lock.
966 *
967 * @returns VINF_SUCCESS on success.
968 * @returns Fatal error on failure.
969 * @param pDevIns The PIC device instance.
970 * @param rc Dummy for making the interface identical to the RC and R0 versions.
971 */
972 DECLR3CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
973
974 /**
975 * Releases the PDM lock.
976 *
977 * @param pDevIns The PIC device instance.
978 */
979 DECLR3CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
980
981 /**
982 * Gets the address of the RC PIC helpers.
983 *
984 * This should be called at both construction and relocation time
985 * to obtain the correct address of the RC helpers.
986 *
987 * @returns RC pointer to the PIC helpers.
988 * @param pDevIns Device instance of the PIC.
989 */
990 DECLR3CALLBACKMEMBER(PCPDMPICHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
991
992 /**
993 * Gets the address of the R0 PIC helpers.
994 *
995 * This should be called at both construction and relocation time
996 * to obtain the correct address of the R0 helpers.
997 *
998 * @returns R0 pointer to the PIC helpers.
999 * @param pDevIns Device instance of the PIC.
1000 */
1001 DECLR3CALLBACKMEMBER(PCPDMPICHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
1002
1003 /** Just a safety precaution. */
1004 uint32_t u32TheEnd;
1005} PDMPICHLPR3;
1006
1007/** Pointer to PIC R3 helpers. */
1008typedef R3PTRTYPE(PDMPICHLPR3 *) PPDMPICHLPR3;
1009/** Pointer to const PIC R3 helpers. */
1010typedef R3PTRTYPE(const PDMPICHLPR3 *) PCPDMPICHLPR3;
1011
1012/** Current PDMPICHLPR3 version number. */
1013#define PDM_PICHLPR3_VERSION PDM_VERSION_MAKE(0xfff7, 1, 0)
1014
1015
1016
1017/**
1018 * Advanced Programmable Interrupt Controller registration structure.
1019 */
1020typedef struct PDMAPICREG
1021{
1022 /** Structure version number. PDM_APICREG_VERSION defines the current version. */
1023 uint32_t u32Version;
1024
1025 /**
1026 * Get a pending interrupt.
1027 *
1028 * @returns Pending interrupt number.
1029 * @param pDevIns Device instance of the APIC.
1030 */
1031 DECLR3CALLBACKMEMBER(int, pfnGetInterruptR3,(PPDMDEVINS pDevIns));
1032
1033 /**
1034 * Check if the APIC has a pending interrupt/if a TPR change would active one
1035 *
1036 * @returns Pending interrupt yes/no
1037 * @param pDevIns Device instance of the APIC.
1038 */
1039 DECLR3CALLBACKMEMBER(bool, pfnHasPendingIrqR3,(PPDMDEVINS pDevIns));
1040
1041 /**
1042 * Set the APIC base.
1043 *
1044 * @param pDevIns Device instance of the APIC.
1045 * @param u64Base The new base.
1046 */
1047 DECLR3CALLBACKMEMBER(void, pfnSetBaseR3,(PPDMDEVINS pDevIns, uint64_t u64Base));
1048
1049 /**
1050 * Get the APIC base.
1051 *
1052 * @returns Current base.
1053 * @param pDevIns Device instance of the APIC.
1054 */
1055 DECLR3CALLBACKMEMBER(uint64_t, pfnGetBaseR3,(PPDMDEVINS pDevIns));
1056
1057 /**
1058 * Set the TPR (task priority register).
1059 *
1060 * @param pDevIns Device instance of the APIC.
1061 * @param idCpu VCPU id
1062 * @param u8TPR The new TPR.
1063 */
1064 DECLR3CALLBACKMEMBER(void, pfnSetTPRR3,(PPDMDEVINS pDevIns, VMCPUID idCpu, uint8_t u8TPR));
1065
1066 /**
1067 * Get the TPR (task priority register).
1068 *
1069 * @returns The current TPR.
1070 * @param pDevIns Device instance of the APIC.
1071 * @param idCpu VCPU id
1072 */
1073 DECLR3CALLBACKMEMBER(uint8_t, pfnGetTPRR3,(PPDMDEVINS pDevIns, VMCPUID idCpu));
1074
1075 /**
1076 * Write MSR in APIC range.
1077 *
1078 * @returns VBox status code.
1079 * @param pDevIns Device instance of the APIC.
1080 * @param idCpu Target CPU.
1081 * @param u32Reg MSR to write.
1082 * @param u64Value Value to write.
1083 */
1084 DECLR3CALLBACKMEMBER(int, pfnWriteMSRR3, (PPDMDEVINS pDevIns, VMCPUID idCpu, uint32_t u32Reg, uint64_t u64Value));
1085
1086 /**
1087 * Read MSR in APIC range.
1088 *
1089 * @returns VBox status code.
1090 * @param pDevIns Device instance of the APIC.
1091 * @param idCpu Target CPU.
1092 * @param u32Reg MSR to read.
1093 * @param pu64Value Value read.
1094 */
1095 DECLR3CALLBACKMEMBER(int, pfnReadMSRR3, (PPDMDEVINS pDevIns, VMCPUID idCpu, uint32_t u32Reg, uint64_t *pu64Value));
1096
1097 /**
1098 * Private interface between the IOAPIC and APIC.
1099 *
1100 * This is a low-level, APIC/IOAPIC implementation specific interface
1101 * which is registered with PDM only because it makes life so much
1102 * simpler right now (GC bits). This is a bad bad hack! The correct
1103 * way of doing this would involve some way of querying GC interfaces
1104 * and relocating them. Perhaps doing some kind of device init in GC...
1105 *
1106 * @returns status code.
1107 * @param pDevIns Device instance of the APIC.
1108 * @param u8Dest See APIC implementation.
1109 * @param u8DestMode See APIC implementation.
1110 * @param u8DeliveryMode See APIC implementation.
1111 * @param iVector See APIC implementation.
1112 * @param u8Polarity See APIC implementation.
1113 * @param u8TriggerMode See APIC implementation.
1114 */
1115 DECLR3CALLBACKMEMBER(int, pfnBusDeliverR3,(PPDMDEVINS pDevIns, uint8_t u8Dest, uint8_t u8DestMode, uint8_t u8DeliveryMode,
1116 uint8_t iVector, uint8_t u8Polarity, uint8_t u8TriggerMode));
1117
1118 /**
1119 * Deliver a signal to CPU's local interrupt pins (LINT0/LINT1). Used for
1120 * virtual wire mode when interrupts from the PIC are passed through LAPIC.
1121 *
1122 * @returns status code.
1123 * @param pDevIns Device instance of the APIC.
1124 * @param u8Pin Local pin number (0 or 1 for current CPUs).
1125 */
1126 DECLR3CALLBACKMEMBER(int, pfnLocalInterruptR3,(PPDMDEVINS pDevIns, uint8_t u8Pin, uint8_t u8Level));
1127
1128 /** The name of the RC GetInterrupt entry point. */
1129 const char *pszGetInterruptRC;
1130 /** The name of the RC HasPendingIrq entry point. */
1131 const char *pszHasPendingIrqRC;
1132 /** The name of the RC SetBase entry point. */
1133 const char *pszSetBaseRC;
1134 /** The name of the RC GetBase entry point. */
1135 const char *pszGetBaseRC;
1136 /** The name of the RC SetTPR entry point. */
1137 const char *pszSetTPRRC;
1138 /** The name of the RC GetTPR entry point. */
1139 const char *pszGetTPRRC;
1140 /** The name of the RC WriteMSR entry point. */
1141 const char *pszWriteMSRRC;
1142 /** The name of the RC ReadMSR entry point. */
1143 const char *pszReadMSRRC;
1144 /** The name of the RC BusDeliver entry point. */
1145 const char *pszBusDeliverRC;
1146 /** The name of the RC LocalInterrupt entry point. */
1147 const char *pszLocalInterruptRC;
1148
1149 /** The name of the R0 GetInterrupt entry point. */
1150 const char *pszGetInterruptR0;
1151 /** The name of the R0 HasPendingIrq entry point. */
1152 const char *pszHasPendingIrqR0;
1153 /** The name of the R0 SetBase entry point. */
1154 const char *pszSetBaseR0;
1155 /** The name of the R0 GetBase entry point. */
1156 const char *pszGetBaseR0;
1157 /** The name of the R0 SetTPR entry point. */
1158 const char *pszSetTPRR0;
1159 /** The name of the R0 GetTPR entry point. */
1160 const char *pszGetTPRR0;
1161 /** The name of the R0 WriteMSR entry point. */
1162 const char *pszWriteMSRR0;
1163 /** The name of the R0 ReadMSR entry point. */
1164 const char *pszReadMSRR0;
1165 /** The name of the R0 BusDeliver entry point. */
1166 const char *pszBusDeliverR0;
1167 /** The name of the R0 LocalInterrupt entry point. */
1168 const char *pszLocalInterruptR0;
1169
1170} PDMAPICREG;
1171/** Pointer to an APIC registration structure. */
1172typedef PDMAPICREG *PPDMAPICREG;
1173
1174/** Current PDMAPICREG version number. */
1175#define PDM_APICREG_VERSION PDM_VERSION_MAKE(0xfff6, 1, 0)
1176
1177
1178/**
1179 * APIC version argument for pfnChangeFeature.
1180 */
1181typedef enum PDMAPICVERSION
1182{
1183 /** Invalid 0 entry. */
1184 PDMAPICVERSION_INVALID = 0,
1185 /** No APIC. */
1186 PDMAPICVERSION_NONE,
1187 /** Standard APIC (X86_CPUID_FEATURE_EDX_APIC). */
1188 PDMAPICVERSION_APIC,
1189 /** Intel X2APIC (X86_CPUID_FEATURE_ECX_X2APIC). */
1190 PDMAPICVERSION_X2APIC,
1191 /** The usual 32-bit paranoia. */
1192 PDMAPICVERSION_32BIT_HACK = 0x7fffffff
1193} PDMAPICVERSION;
1194
1195/**
1196 * APIC irq argument for SetInterruptFF.
1197 */
1198typedef enum PDMAPICIRQ
1199{
1200 /** Invalid 0 entry. */
1201 PDMAPICIRQ_INVALID = 0,
1202 /** Normal hardware interrupt. */
1203 PDMAPICIRQ_HARDWARE,
1204 /** NMI. */
1205 PDMAPICIRQ_NMI,
1206 /** SMI. */
1207 PDMAPICIRQ_SMI,
1208 /** ExtINT (HW interrupt via PIC). */
1209 PDMAPICIRQ_EXTINT,
1210 /** The usual 32-bit paranoia. */
1211 PDMAPICIRQ_32BIT_HACK = 0x7fffffff
1212} PDMAPICIRQ;
1213
1214
1215/**
1216 * APIC RC helpers.
1217 */
1218typedef struct PDMAPICHLPRC
1219{
1220 /** Structure version. PDM_APICHLPRC_VERSION defines the current version. */
1221 uint32_t u32Version;
1222
1223 /**
1224 * Set the interrupt force action flag.
1225 *
1226 * @param pDevIns Device instance of the APIC.
1227 * @param enmType IRQ type.
1228 * @param idCpu Virtual CPU to set flag upon.
1229 */
1230 DECLRCCALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1231
1232 /**
1233 * Clear the interrupt force action flag.
1234 *
1235 * @param pDevIns Device instance of the APIC.
1236 * @param enmType IRQ type.
1237 * @param idCpu Virtual CPU to clear flag upon.
1238 */
1239 DECLRCCALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1240
1241 /**
1242 * Modifies APIC-related bits in the CPUID feature mask.
1243 *
1244 * @param pDevIns Device instance of the APIC.
1245 * @param enmVersion Supported APIC version.
1246 */
1247 DECLRCCALLBACKMEMBER(void, pfnChangeFeature,(PPDMDEVINS pDevIns, PDMAPICVERSION enmVersion));
1248
1249 /**
1250 * Acquires the PDM lock.
1251 *
1252 * @returns VINF_SUCCESS on success.
1253 * @returns rc if we failed to acquire the lock.
1254 * @param pDevIns The APIC device instance.
1255 * @param rc What to return if we fail to acquire the lock.
1256 */
1257 DECLRCCALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
1258
1259 /**
1260 * Releases the PDM lock.
1261 *
1262 * @param pDevIns The APIC device instance.
1263 */
1264 DECLRCCALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
1265
1266 /**
1267 * Get the virtual CPU id corresponding to the current EMT.
1268 *
1269 * @param pDevIns The APIC device instance.
1270 */
1271 DECLRCCALLBACKMEMBER(VMCPUID, pfnGetCpuId,(PPDMDEVINS pDevIns));
1272
1273 /** Just a safety precaution. */
1274 uint32_t u32TheEnd;
1275} PDMAPICHLPRC;
1276/** Pointer to APIC GC helpers. */
1277typedef RCPTRTYPE(PDMAPICHLPRC *) PPDMAPICHLPRC;
1278/** Pointer to const APIC helpers. */
1279typedef RCPTRTYPE(const PDMAPICHLPRC *) PCPDMAPICHLPRC;
1280
1281/** Current PDMAPICHLPRC version number. */
1282#define PDM_APICHLPRC_VERSION PDM_VERSION_MAKE(0xfff5, 1, 0)
1283
1284
1285/**
1286 * APIC R0 helpers.
1287 */
1288typedef struct PDMAPICHLPR0
1289{
1290 /** Structure version. PDM_APICHLPR0_VERSION defines the current version. */
1291 uint32_t u32Version;
1292
1293 /**
1294 * Set the interrupt force action flag.
1295 *
1296 * @param pDevIns Device instance of the APIC.
1297 * @param enmType IRQ type.
1298 * @param idCpu Virtual CPU to set flag upon.
1299 */
1300 DECLR0CALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1301
1302 /**
1303 * Clear the interrupt force action flag.
1304 *
1305 * @param pDevIns Device instance of the APIC.
1306 * @param enmType IRQ type.
1307 * @param idCpu Virtual CPU to clear flag upon.
1308 */
1309 DECLR0CALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1310
1311 /**
1312 * Modifies APIC-related bits in the CPUID feature mask.
1313 *
1314 * @param pDevIns Device instance of the APIC.
1315 * @param enmVersion Supported APIC version.
1316 */
1317 DECLR0CALLBACKMEMBER(void, pfnChangeFeature,(PPDMDEVINS pDevIns, PDMAPICVERSION enmVersion));
1318
1319 /**
1320 * Acquires the PDM lock.
1321 *
1322 * @returns VINF_SUCCESS on success.
1323 * @returns rc if we failed to acquire the lock.
1324 * @param pDevIns The APIC device instance.
1325 * @param rc What to return if we fail to acquire the lock.
1326 */
1327 DECLR0CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
1328
1329 /**
1330 * Releases the PDM lock.
1331 *
1332 * @param pDevIns The APIC device instance.
1333 */
1334 DECLR0CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
1335
1336 /**
1337 * Get the virtual CPU id corresponding to the current EMT.
1338 *
1339 * @param pDevIns The APIC device instance.
1340 */
1341 DECLR0CALLBACKMEMBER(VMCPUID, pfnGetCpuId,(PPDMDEVINS pDevIns));
1342
1343 /** Just a safety precaution. */
1344 uint32_t u32TheEnd;
1345} PDMAPICHLPR0;
1346/** Pointer to APIC GC helpers. */
1347typedef RCPTRTYPE(PDMAPICHLPR0 *) PPDMAPICHLPR0;
1348/** Pointer to const APIC helpers. */
1349typedef R0PTRTYPE(const PDMAPICHLPR0 *) PCPDMAPICHLPR0;
1350
1351/** Current PDMAPICHLPR0 version number. */
1352#define PDM_APICHLPR0_VERSION PDM_VERSION_MAKE(0xfff4, 1, 0)
1353
1354/**
1355 * APIC R3 helpers.
1356 */
1357typedef struct PDMAPICHLPR3
1358{
1359 /** Structure version. PDM_APICHLPR3_VERSION defines the current version. */
1360 uint32_t u32Version;
1361
1362 /**
1363 * Set the interrupt force action flag.
1364 *
1365 * @param pDevIns Device instance of the APIC.
1366 * @param enmType IRQ type.
1367 * @param idCpu Virtual CPU to set flag upon.
1368 */
1369 DECLR3CALLBACKMEMBER(void, pfnSetInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1370
1371 /**
1372 * Clear the interrupt force action flag.
1373 *
1374 * @param pDevIns Device instance of the APIC.
1375 * @param enmType IRQ type.
1376 * @param idCpu Virtual CPU to clear flag upon.
1377 */
1378 DECLR3CALLBACKMEMBER(void, pfnClearInterruptFF,(PPDMDEVINS pDevIns, PDMAPICIRQ enmType, VMCPUID idCpu));
1379
1380 /**
1381 * Modifies APIC-related bits in the CPUID feature mask.
1382 *
1383 * @param pDevIns Device instance of the APIC.
1384 * @param enmVersion Supported APIC version.
1385 */
1386 DECLR3CALLBACKMEMBER(void, pfnChangeFeature,(PPDMDEVINS pDevIns, PDMAPICVERSION enmVersion));
1387
1388 /**
1389 * Get the virtual CPU id corresponding to the current EMT.
1390 *
1391 * @param pDevIns The APIC device instance.
1392 */
1393 DECLR3CALLBACKMEMBER(VMCPUID, pfnGetCpuId,(PPDMDEVINS pDevIns));
1394
1395 /**
1396 * Sends SIPI to given virtual CPU.
1397 *
1398 * @param pDevIns The APIC device instance.
1399 * @param idCpu Virtual CPU to perform SIPI on
1400 * @param iVector SIPI vector
1401 */
1402 DECLR3CALLBACKMEMBER(void, pfnSendSipi,(PPDMDEVINS pDevIns, VMCPUID idCpu, uint32_t uVector));
1403
1404 /**
1405 * Sends init IPI to given virtual CPU, should result in reset and
1406 * halting till SIPI.
1407 *
1408 * @param pDevIns The APIC device instance.
1409 * @param idCpu Virtual CPU to perform SIPI on
1410 */
1411 DECLR3CALLBACKMEMBER(void, pfnSendInitIpi,(PPDMDEVINS pDevIns, VMCPUID idCpu));
1412
1413 /**
1414 * Gets the address of the RC APIC helpers.
1415 *
1416 * This should be called at both construction and relocation time
1417 * to obtain the correct address of the RC helpers.
1418 *
1419 * @returns GC pointer to the APIC helpers.
1420 * @param pDevIns Device instance of the APIC.
1421 */
1422 DECLR3CALLBACKMEMBER(PCPDMAPICHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
1423
1424 /**
1425 * Gets the address of the R0 APIC helpers.
1426 *
1427 * This should be called at both construction and relocation time
1428 * to obtain the correct address of the R0 helpers.
1429 *
1430 * @returns R0 pointer to the APIC helpers.
1431 * @param pDevIns Device instance of the APIC.
1432 */
1433 DECLR3CALLBACKMEMBER(PCPDMAPICHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
1434
1435 /**
1436 * Get the critical section used to synchronize the PICs, PCI and stuff.
1437 *
1438 * @returns Ring-3 pointer to the critical section.
1439 * @param pDevIns The APIC device instance.
1440 */
1441 DECLR3CALLBACKMEMBER(R3PTRTYPE(PPDMCRITSECT), pfnGetR3CritSect,(PPDMDEVINS pDevIns));
1442
1443 /**
1444 * Get the critical section used to synchronize the PICs, PCI and stuff.
1445 *
1446 * @returns Raw-mode context pointer to the critical section.
1447 * @param pDevIns The APIC device instance.
1448 */
1449 DECLR3CALLBACKMEMBER(RCPTRTYPE(PPDMCRITSECT), pfnGetRCCritSect,(PPDMDEVINS pDevIns));
1450
1451 /**
1452 * Get the critical section used to synchronize the PICs, PCI and stuff.
1453 *
1454 * @returns Ring-0 pointer to the critical section.
1455 * @param pDevIns The APIC device instance.
1456 */
1457 DECLR3CALLBACKMEMBER(R0PTRTYPE(PPDMCRITSECT), pfnGetR0CritSect,(PPDMDEVINS pDevIns));
1458
1459 /** Just a safety precaution. */
1460 uint32_t u32TheEnd;
1461} PDMAPICHLPR3;
1462/** Pointer to APIC helpers. */
1463typedef R3PTRTYPE(PDMAPICHLPR3 *) PPDMAPICHLPR3;
1464/** Pointer to const APIC helpers. */
1465typedef R3PTRTYPE(const PDMAPICHLPR3 *) PCPDMAPICHLPR3;
1466
1467/** Current PDMAPICHLP version number. */
1468#define PDM_APICHLPR3_VERSION PDM_VERSION_MAKE(0xfff3, 1, 0)
1469
1470
1471/**
1472 * I/O APIC registration structure.
1473 */
1474typedef struct PDMIOAPICREG
1475{
1476 /** Struct version+magic number (PDM_IOAPICREG_VERSION). */
1477 uint32_t u32Version;
1478
1479 /**
1480 * Set the an IRQ.
1481 *
1482 * @param pDevIns Device instance of the I/O APIC.
1483 * @param iIrq IRQ number to set.
1484 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
1485 */
1486 DECLR3CALLBACKMEMBER(void, pfnSetIrqR3,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
1487
1488 /** The name of the GC SetIrq entry point. */
1489 const char *pszSetIrqRC;
1490
1491 /** The name of the R0 SetIrq entry point. */
1492 const char *pszSetIrqR0;
1493
1494 /**
1495 * Send a MSI.
1496 *
1497 * @param pDevIns Device instance of the I/O APIC.
1498 * @param GCPhys Request address.
1499 * @param uValue Request value.
1500 */
1501 DECLR3CALLBACKMEMBER(void, pfnSendMsiR3,(PPDMDEVINS pDevIns, RTGCPHYS GCAddr, uint32_t uValue));
1502
1503 /** The name of the GC SendMsi entry point. */
1504 const char *pszSendMsiRC;
1505
1506 /** The name of the R0 SendMsi entry point. */
1507 const char *pszSendMsiR0;
1508} PDMIOAPICREG;
1509/** Pointer to an APIC registration structure. */
1510typedef PDMIOAPICREG *PPDMIOAPICREG;
1511
1512/** Current PDMAPICREG version number. */
1513#define PDM_IOAPICREG_VERSION PDM_VERSION_MAKE(0xfff2, 2, 0)
1514
1515
1516/**
1517 * IOAPIC RC helpers.
1518 */
1519typedef struct PDMIOAPICHLPRC
1520{
1521 /** Structure version. PDM_IOAPICHLPRC_VERSION defines the current version. */
1522 uint32_t u32Version;
1523
1524 /**
1525 * Private interface between the IOAPIC and APIC.
1526 *
1527 * See comments about this hack on PDMAPICREG::pfnBusDeliverR3.
1528 *
1529 * @returns status code.
1530 * @param pDevIns Device instance of the IOAPIC.
1531 * @param u8Dest See APIC implementation.
1532 * @param u8DestMode See APIC implementation.
1533 * @param u8DeliveryMode See APIC implementation.
1534 * @param iVector See APIC implementation.
1535 * @param u8Polarity See APIC implementation.
1536 * @param u8TriggerMode See APIC implementation.
1537 */
1538 DECLRCCALLBACKMEMBER(int, pfnApicBusDeliver,(PPDMDEVINS pDevIns, uint8_t u8Dest, uint8_t u8DestMode, uint8_t u8DeliveryMode,
1539 uint8_t iVector, uint8_t u8Polarity, uint8_t u8TriggerMode));
1540
1541 /**
1542 * Acquires the PDM lock.
1543 *
1544 * @returns VINF_SUCCESS on success.
1545 * @returns rc if we failed to acquire the lock.
1546 * @param pDevIns The IOAPIC device instance.
1547 * @param rc What to return if we fail to acquire the lock.
1548 */
1549 DECLRCCALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
1550
1551 /**
1552 * Releases the PDM lock.
1553 *
1554 * @param pDevIns The IOAPIC device instance.
1555 */
1556 DECLRCCALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
1557
1558 /** Just a safety precaution. */
1559 uint32_t u32TheEnd;
1560} PDMIOAPICHLPRC;
1561/** Pointer to IOAPIC RC helpers. */
1562typedef RCPTRTYPE(PDMIOAPICHLPRC *) PPDMIOAPICHLPRC;
1563/** Pointer to const IOAPIC helpers. */
1564typedef RCPTRTYPE(const PDMIOAPICHLPRC *) PCPDMIOAPICHLPRC;
1565
1566/** Current PDMIOAPICHLPRC version number. */
1567#define PDM_IOAPICHLPRC_VERSION PDM_VERSION_MAKE(0xfff1, 1, 0)
1568
1569
1570/**
1571 * IOAPIC R0 helpers.
1572 */
1573typedef struct PDMIOAPICHLPR0
1574{
1575 /** Structure version. PDM_IOAPICHLPR0_VERSION defines the current version. */
1576 uint32_t u32Version;
1577
1578 /**
1579 * Private interface between the IOAPIC and APIC.
1580 *
1581 * See comments about this hack on PDMAPICREG::pfnBusDeliverR3.
1582 *
1583 * @returns status code.
1584 * @param pDevIns Device instance of the IOAPIC.
1585 * @param u8Dest See APIC implementation.
1586 * @param u8DestMode See APIC implementation.
1587 * @param u8DeliveryMode See APIC implementation.
1588 * @param iVector See APIC implementation.
1589 * @param u8Polarity See APIC implementation.
1590 * @param u8TriggerMode See APIC implementation.
1591 */
1592 DECLR0CALLBACKMEMBER(int, pfnApicBusDeliver,(PPDMDEVINS pDevIns, uint8_t u8Dest, uint8_t u8DestMode, uint8_t u8DeliveryMode,
1593 uint8_t iVector, uint8_t u8Polarity, uint8_t u8TriggerMode));
1594
1595 /**
1596 * Acquires the PDM lock.
1597 *
1598 * @returns VINF_SUCCESS on success.
1599 * @returns rc if we failed to acquire the lock.
1600 * @param pDevIns The IOAPIC device instance.
1601 * @param rc What to return if we fail to acquire the lock.
1602 */
1603 DECLR0CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
1604
1605 /**
1606 * Releases the PDM lock.
1607 *
1608 * @param pDevIns The IOAPIC device instance.
1609 */
1610 DECLR0CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
1611
1612 /** Just a safety precaution. */
1613 uint32_t u32TheEnd;
1614} PDMIOAPICHLPR0;
1615/** Pointer to IOAPIC R0 helpers. */
1616typedef R0PTRTYPE(PDMIOAPICHLPR0 *) PPDMIOAPICHLPR0;
1617/** Pointer to const IOAPIC helpers. */
1618typedef R0PTRTYPE(const PDMIOAPICHLPR0 *) PCPDMIOAPICHLPR0;
1619
1620/** Current PDMIOAPICHLPR0 version number. */
1621#define PDM_IOAPICHLPR0_VERSION PDM_VERSION_MAKE(0xfff0, 1, 0)
1622
1623/**
1624 * IOAPIC R3 helpers.
1625 */
1626typedef struct PDMIOAPICHLPR3
1627{
1628 /** Structure version. PDM_IOAPICHLPR3_VERSION defines the current version. */
1629 uint32_t u32Version;
1630
1631 /**
1632 * Private interface between the IOAPIC and APIC.
1633 *
1634 * See comments about this hack on PDMAPICREG::pfnBusDeliverR3.
1635 *
1636 * @returns status code
1637 * @param pDevIns Device instance of the IOAPIC.
1638 * @param u8Dest See APIC implementation.
1639 * @param u8DestMode See APIC implementation.
1640 * @param u8DeliveryMode See APIC implementation.
1641 * @param iVector See APIC implementation.
1642 * @param u8Polarity See APIC implementation.
1643 * @param u8TriggerMode See APIC implementation.
1644 */
1645 DECLR3CALLBACKMEMBER(int, pfnApicBusDeliver,(PPDMDEVINS pDevIns, uint8_t u8Dest, uint8_t u8DestMode, uint8_t u8DeliveryMode,
1646 uint8_t iVector, uint8_t u8Polarity, uint8_t u8TriggerMode));
1647
1648 /**
1649 * Acquires the PDM lock.
1650 *
1651 * @returns VINF_SUCCESS on success.
1652 * @returns Fatal error on failure.
1653 * @param pDevIns The IOAPIC device instance.
1654 * @param rc Dummy for making the interface identical to the GC and R0 versions.
1655 */
1656 DECLR3CALLBACKMEMBER(int, pfnLock,(PPDMDEVINS pDevIns, int rc));
1657
1658 /**
1659 * Releases the PDM lock.
1660 *
1661 * @param pDevIns The IOAPIC device instance.
1662 */
1663 DECLR3CALLBACKMEMBER(void, pfnUnlock,(PPDMDEVINS pDevIns));
1664
1665 /**
1666 * Gets the address of the RC IOAPIC helpers.
1667 *
1668 * This should be called at both construction and relocation time
1669 * to obtain the correct address of the RC helpers.
1670 *
1671 * @returns RC pointer to the IOAPIC helpers.
1672 * @param pDevIns Device instance of the IOAPIC.
1673 */
1674 DECLR3CALLBACKMEMBER(PCPDMIOAPICHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
1675
1676 /**
1677 * Gets the address of the R0 IOAPIC helpers.
1678 *
1679 * This should be called at both construction and relocation time
1680 * to obtain the correct address of the R0 helpers.
1681 *
1682 * @returns R0 pointer to the IOAPIC helpers.
1683 * @param pDevIns Device instance of the IOAPIC.
1684 */
1685 DECLR3CALLBACKMEMBER(PCPDMIOAPICHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
1686
1687 /** Just a safety precaution. */
1688 uint32_t u32TheEnd;
1689} PDMIOAPICHLPR3;
1690/** Pointer to IOAPIC R3 helpers. */
1691typedef R3PTRTYPE(PDMIOAPICHLPR3 *) PPDMIOAPICHLPR3;
1692/** Pointer to const IOAPIC helpers. */
1693typedef R3PTRTYPE(const PDMIOAPICHLPR3 *) PCPDMIOAPICHLPR3;
1694
1695/** Current PDMIOAPICHLPR3 version number. */
1696#define PDM_IOAPICHLPR3_VERSION PDM_VERSION_MAKE(0xffef, 1, 0)
1697
1698
1699/**
1700 * HPET registration structure.
1701 */
1702typedef struct PDMHPETREG
1703{
1704 /** Struct version+magic number (PDM_HPETREG_VERSION). */
1705 uint32_t u32Version;
1706
1707} PDMHPETREG;
1708/** Pointer to an HPET registration structure. */
1709typedef PDMHPETREG *PPDMHPETREG;
1710
1711/** Current PDMHPETREG version number. */
1712#define PDM_HPETREG_VERSION PDM_VERSION_MAKE(0xffe2, 1, 0)
1713
1714/**
1715 * HPET RC helpers.
1716 *
1717 * @remarks Keep this around in case HPET will need PDM interaction in again RC
1718 * at some later point.
1719 */
1720typedef struct PDMHPETHLPRC
1721{
1722 /** Structure version. PDM_HPETHLPRC_VERSION defines the current version. */
1723 uint32_t u32Version;
1724
1725 /** Just a safety precaution. */
1726 uint32_t u32TheEnd;
1727} PDMHPETHLPRC;
1728
1729/** Pointer to HPET RC helpers. */
1730typedef RCPTRTYPE(PDMHPETHLPRC *) PPDMHPETHLPRC;
1731/** Pointer to const HPET RC helpers. */
1732typedef RCPTRTYPE(const PDMHPETHLPRC *) PCPDMHPETHLPRC;
1733
1734/** Current PDMHPETHLPRC version number. */
1735#define PDM_HPETHLPRC_VERSION PDM_VERSION_MAKE(0xffee, 2, 0)
1736
1737
1738/**
1739 * HPET R0 helpers.
1740 *
1741 * @remarks Keep this around in case HPET will need PDM interaction in again R0
1742 * at some later point.
1743 */
1744typedef struct PDMHPETHLPR0
1745{
1746 /** Structure version. PDM_HPETHLPR0_VERSION defines the current version. */
1747 uint32_t u32Version;
1748
1749 /** Just a safety precaution. */
1750 uint32_t u32TheEnd;
1751} PDMHPETHLPR0;
1752
1753/** Pointer to HPET R0 helpers. */
1754typedef R0PTRTYPE(PDMHPETHLPR0 *) PPDMHPETHLPR0;
1755/** Pointer to const HPET R0 helpers. */
1756typedef R0PTRTYPE(const PDMHPETHLPR0 *) PCPDMHPETHLPR0;
1757
1758/** Current PDMHPETHLPR0 version number. */
1759#define PDM_HPETHLPR0_VERSION PDM_VERSION_MAKE(0xffed, 2, 0)
1760
1761/**
1762 * HPET R3 helpers.
1763 */
1764typedef struct PDMHPETHLPR3
1765{
1766 /** Structure version. PDM_HPETHLP_VERSION defines the current version. */
1767 uint32_t u32Version;
1768
1769 /**
1770 * Gets the address of the RC HPET helpers.
1771 *
1772 * This should be called at both construction and relocation time
1773 * to obtain the correct address of the RC helpers.
1774 *
1775 * @returns RC pointer to the HPET helpers.
1776 * @param pDevIns Device instance of the HPET.
1777 */
1778 DECLR3CALLBACKMEMBER(PCPDMHPETHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
1779
1780 /**
1781 * Gets the address of the R0 HPET helpers.
1782 *
1783 * This should be called at both construction and relocation time
1784 * to obtain the correct address of the R0 helpers.
1785 *
1786 * @returns R0 pointer to the HPET helpers.
1787 * @param pDevIns Device instance of the HPET.
1788 */
1789 DECLR3CALLBACKMEMBER(PCPDMHPETHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
1790
1791 /**
1792 * Set legacy mode on PIT and RTC.
1793 *
1794 * @returns VINF_SUCCESS on success.
1795 * @returns rc if we failed to set legacy mode.
1796 * @param pDevIns Device instance of the HPET.
1797 * @param fActivated Whether legacy mode is activated or deactivated.
1798 */
1799 DECLR3CALLBACKMEMBER(int, pfnSetLegacyMode,(PPDMDEVINS pDevIns, bool fActivated));
1800
1801
1802 /**
1803 * Set IRQ, bypassing ISA bus override rules.
1804 *
1805 * @returns VINF_SUCCESS on success.
1806 * @returns rc if we failed to set legacy mode.
1807 * @param pDevIns Device instance of the HPET.
1808 * @param fActivate Activate or deactivate legacy mode.
1809 */
1810 DECLR3CALLBACKMEMBER(int, pfnSetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
1811
1812 /** Just a safety precaution. */
1813 uint32_t u32TheEnd;
1814} PDMHPETHLPR3;
1815
1816/** Pointer to HPET R3 helpers. */
1817typedef R3PTRTYPE(PDMHPETHLPR3 *) PPDMHPETHLPR3;
1818/** Pointer to const HPET R3 helpers. */
1819typedef R3PTRTYPE(const PDMHPETHLPR3 *) PCPDMHPETHLPR3;
1820
1821/** Current PDMHPETHLPR3 version number. */
1822#define PDM_HPETHLPR3_VERSION PDM_VERSION_MAKE(0xffec, 2, 0)
1823
1824
1825/**
1826 * Raw PCI device registration structure.
1827 */
1828typedef struct PDMPCIRAWREG
1829{
1830 /** Struct version+magic number (PDM_PCIRAWREG_VERSION). */
1831 uint32_t u32Version;
1832 /** Just a safety precaution. */
1833 uint32_t u32TheEnd;
1834} PDMPCIRAWREG;
1835/** Pointer to a raw PCI registration structure. */
1836typedef PDMPCIRAWREG *PPDMPCIRAWREG;
1837
1838/** Current PDMPCIRAWREG version number. */
1839#define PDM_PCIRAWREG_VERSION PDM_VERSION_MAKE(0xffe1, 1, 0)
1840
1841/**
1842 * Raw PCI device raw-mode context helpers.
1843 */
1844typedef struct PDMPCIRAWHLPRC
1845{
1846 /** Structure version and magic number (PDM_PCIRAWHLPRC_VERSION). */
1847 uint32_t u32Version;
1848 /** Just a safety precaution. */
1849 uint32_t u32TheEnd;
1850} PDMPCIRAWHLPRC;
1851/** Pointer to a raw PCI deviec raw-mode context helper structure. */
1852typedef RCPTRTYPE(PDMPCIRAWHLPRC *) PPDMPCIRAWHLPRC;
1853/** Pointer to a const raw PCI deviec raw-mode context helper structure. */
1854typedef RCPTRTYPE(const PDMPCIRAWHLPRC *) PCPDMPCIRAWHLPRC;
1855
1856/** Current PDMPCIRAWHLPRC version number. */
1857#define PDM_PCIRAWHLPRC_VERSION PDM_VERSION_MAKE(0xffe0, 1, 0)
1858
1859/**
1860 * Raw PCI device ring-0 context helpers.
1861 */
1862typedef struct PDMPCIRAWHLPR0
1863{
1864 /** Structure version and magic number (PDM_PCIRAWHLPR0_VERSION). */
1865 uint32_t u32Version;
1866 /** Just a safety precaution. */
1867 uint32_t u32TheEnd;
1868} PDMPCIRAWHLPR0;
1869/** Pointer to a raw PCI deviec ring-0 context helper structure. */
1870typedef R0PTRTYPE(PDMPCIRAWHLPR0 *) PPDMPCIRAWHLPR0;
1871/** Pointer to a const raw PCI deviec ring-0 context helper structure. */
1872typedef R0PTRTYPE(const PDMPCIRAWHLPR0 *) PCPDMPCIRAWHLPR0;
1873
1874/** Current PDMPCIRAWHLPR0 version number. */
1875#define PDM_PCIRAWHLPR0_VERSION PDM_VERSION_MAKE(0xffdf, 1, 0)
1876
1877
1878/**
1879 * Raw PCI device ring-3 context helpers.
1880 */
1881typedef struct PDMPCIRAWHLPR3
1882{
1883 /** Undefined structure version and magic number. */
1884 uint32_t u32Version;
1885
1886 /**
1887 * Gets the address of the RC raw PCI device helpers.
1888 *
1889 * This should be called at both construction and relocation time to obtain
1890 * the correct address of the RC helpers.
1891 *
1892 * @returns RC pointer to the raw PCI device helpers.
1893 * @param pDevIns Device instance of the raw PCI device.
1894 */
1895 DECLR3CALLBACKMEMBER(PCPDMPCIRAWHLPRC, pfnGetRCHelpers,(PPDMDEVINS pDevIns));
1896
1897 /**
1898 * Gets the address of the R0 raw PCI device helpers.
1899 *
1900 * This should be called at both construction and relocation time to obtain
1901 * the correct address of the R0 helpers.
1902 *
1903 * @returns R0 pointer to the raw PCI device helpers.
1904 * @param pDevIns Device instance of the raw PCI device.
1905 */
1906 DECLR3CALLBACKMEMBER(PCPDMPCIRAWHLPR0, pfnGetR0Helpers,(PPDMDEVINS pDevIns));
1907
1908 /** Just a safety precaution. */
1909 uint32_t u32TheEnd;
1910} PDMPCIRAWHLPR3;
1911/** Pointer to raw PCI R3 helpers. */
1912typedef R3PTRTYPE(PDMPCIRAWHLPR3 *) PPDMPCIRAWHLPR3;
1913/** Pointer to const raw PCI R3 helpers. */
1914typedef R3PTRTYPE(const PDMPCIRAWHLPR3 *) PCPDMPCIRAWHLPR3;
1915
1916/** Current PDMPCIRAWHLPR3 version number. */
1917#define PDM_PCIRAWHLPR3_VERSION PDM_VERSION_MAKE(0xffde, 1, 0)
1918
1919
1920#ifdef IN_RING3
1921
1922/**
1923 * DMA Transfer Handler.
1924 *
1925 * @returns Number of bytes transferred.
1926 * @param pDevIns Device instance of the DMA.
1927 * @param pvUser User pointer.
1928 * @param uChannel Channel number.
1929 * @param off DMA position.
1930 * @param cb Block size.
1931 */
1932typedef DECLCALLBACK(uint32_t) FNDMATRANSFERHANDLER(PPDMDEVINS pDevIns, void *pvUser, unsigned uChannel, uint32_t off, uint32_t cb);
1933/** Pointer to a FNDMATRANSFERHANDLER(). */
1934typedef FNDMATRANSFERHANDLER *PFNDMATRANSFERHANDLER;
1935
1936/**
1937 * DMA Controller registration structure.
1938 */
1939typedef struct PDMDMAREG
1940{
1941 /** Structure version number. PDM_DMACREG_VERSION defines the current version. */
1942 uint32_t u32Version;
1943
1944 /**
1945 * Execute pending transfers.
1946 *
1947 * @returns A more work indiciator. I.e. 'true' if there is more to be done, and 'false' if all is done.
1948 * @param pDevIns Device instance of the DMAC.
1949 */
1950 DECLR3CALLBACKMEMBER(bool, pfnRun,(PPDMDEVINS pDevIns));
1951
1952 /**
1953 * Register transfer function for DMA channel.
1954 *
1955 * @param pDevIns Device instance of the DMAC.
1956 * @param uChannel Channel number.
1957 * @param pfnTransferHandler Device specific transfer function.
1958 * @param pvUSer User pointer to be passed to the callback.
1959 */
1960 DECLR3CALLBACKMEMBER(void, pfnRegister,(PPDMDEVINS pDevIns, unsigned uChannel, PFNDMATRANSFERHANDLER pfnTransferHandler, void *pvUser));
1961
1962 /**
1963 * Read memory
1964 *
1965 * @returns Number of bytes read.
1966 * @param pDevIns Device instance of the DMAC.
1967 * @param pvBuffer Pointer to target buffer.
1968 * @param off DMA position.
1969 * @param cbBlock Block size.
1970 */
1971 DECLR3CALLBACKMEMBER(uint32_t, pfnReadMemory,(PPDMDEVINS pDevIns, unsigned uChannel, void *pvBuffer, uint32_t off, uint32_t cbBlock));
1972
1973 /**
1974 * Write memory
1975 *
1976 * @returns Number of bytes written.
1977 * @param pDevIns Device instance of the DMAC.
1978 * @param pvBuffer Memory to write.
1979 * @param off DMA position.
1980 * @param cbBlock Block size.
1981 */
1982 DECLR3CALLBACKMEMBER(uint32_t, pfnWriteMemory,(PPDMDEVINS pDevIns, unsigned uChannel, const void *pvBuffer, uint32_t off, uint32_t cbBlock));
1983
1984 /**
1985 * Set the DREQ line.
1986 *
1987 * @param pDevIns Device instance of the DMAC.
1988 * @param uChannel Channel number.
1989 * @param uLevel Level of the line.
1990 */
1991 DECLR3CALLBACKMEMBER(void, pfnSetDREQ,(PPDMDEVINS pDevIns, unsigned uChannel, unsigned uLevel));
1992
1993 /**
1994 * Get channel mode
1995 *
1996 * @returns Channel mode.
1997 * @param pDevIns Device instance of the DMAC.
1998 * @param uChannel Channel number.
1999 */
2000 DECLR3CALLBACKMEMBER(uint8_t, pfnGetChannelMode,(PPDMDEVINS pDevIns, unsigned uChannel));
2001
2002} PDMDMACREG;
2003/** Pointer to a DMAC registration structure. */
2004typedef PDMDMACREG *PPDMDMACREG;
2005
2006/** Current PDMDMACREG version number. */
2007#define PDM_DMACREG_VERSION PDM_VERSION_MAKE(0xffeb, 1, 0)
2008
2009
2010/**
2011 * DMA Controller device helpers.
2012 */
2013typedef struct PDMDMACHLP
2014{
2015 /** Structure version. PDM_DMACHLP_VERSION defines the current version. */
2016 uint32_t u32Version;
2017
2018 /* to-be-defined */
2019
2020} PDMDMACHLP;
2021/** Pointer to DMAC helpers. */
2022typedef PDMDMACHLP *PPDMDMACHLP;
2023/** Pointer to const DMAC helpers. */
2024typedef const PDMDMACHLP *PCPDMDMACHLP;
2025
2026/** Current PDMDMACHLP version number. */
2027#define PDM_DMACHLP_VERSION PDM_VERSION_MAKE(0xffea, 1, 0)
2028
2029#endif /* IN_RING3 */
2030
2031
2032
2033/**
2034 * RTC registration structure.
2035 */
2036typedef struct PDMRTCREG
2037{
2038 /** Structure version number. PDM_RTCREG_VERSION defines the current version. */
2039 uint32_t u32Version;
2040 uint32_t u32Alignment; /**< structure size alignment. */
2041
2042 /**
2043 * Write to a CMOS register and update the checksum if necessary.
2044 *
2045 * @returns VBox status code.
2046 * @param pDevIns Device instance of the RTC.
2047 * @param iReg The CMOS register index.
2048 * @param u8Value The CMOS register value.
2049 */
2050 DECLR3CALLBACKMEMBER(int, pfnWrite,(PPDMDEVINS pDevIns, unsigned iReg, uint8_t u8Value));
2051
2052 /**
2053 * Read a CMOS register.
2054 *
2055 * @returns VBox status code.
2056 * @param pDevIns Device instance of the RTC.
2057 * @param iReg The CMOS register index.
2058 * @param pu8Value Where to store the CMOS register value.
2059 */
2060 DECLR3CALLBACKMEMBER(int, pfnRead,(PPDMDEVINS pDevIns, unsigned iReg, uint8_t *pu8Value));
2061
2062} PDMRTCREG;
2063/** Pointer to a RTC registration structure. */
2064typedef PDMRTCREG *PPDMRTCREG;
2065/** Pointer to a const RTC registration structure. */
2066typedef const PDMRTCREG *PCPDMRTCREG;
2067
2068/** Current PDMRTCREG version number. */
2069#define PDM_RTCREG_VERSION PDM_VERSION_MAKE(0xffe9, 1, 0)
2070
2071
2072/**
2073 * RTC device helpers.
2074 */
2075typedef struct PDMRTCHLP
2076{
2077 /** Structure version. PDM_RTCHLP_VERSION defines the current version. */
2078 uint32_t u32Version;
2079
2080 /* to-be-defined */
2081
2082} PDMRTCHLP;
2083/** Pointer to RTC helpers. */
2084typedef PDMRTCHLP *PPDMRTCHLP;
2085/** Pointer to const RTC helpers. */
2086typedef const PDMRTCHLP *PCPDMRTCHLP;
2087
2088/** Current PDMRTCHLP version number. */
2089#define PDM_RTCHLP_VERSION PDM_VERSION_MAKE(0xffe8, 1, 0)
2090
2091
2092
2093#ifdef IN_RING3
2094
2095/**
2096 * PDM Device API.
2097 */
2098typedef struct PDMDEVHLPR3
2099{
2100 /** Structure version. PDM_DEVHLP_VERSION defines the current version. */
2101 uint32_t u32Version;
2102
2103 /**
2104 * Register a number of I/O ports with a device.
2105 *
2106 * These callbacks are of course for the host context (HC).
2107 * Register HC handlers before guest context (GC) handlers! There must be a
2108 * HC handler for every GC handler!
2109 *
2110 * @returns VBox status.
2111 * @param pDevIns The device instance to register the ports with.
2112 * @param Port First port number in the range.
2113 * @param cPorts Number of ports to register.
2114 * @param pvUser User argument.
2115 * @param pfnOut Pointer to function which is gonna handle OUT operations.
2116 * @param pfnIn Pointer to function which is gonna handle IN operations.
2117 * @param pfnOutStr Pointer to function which is gonna handle string OUT operations.
2118 * @param pfnInStr Pointer to function which is gonna handle string IN operations.
2119 * @param pszDesc Pointer to description string. This must not be freed.
2120 */
2121 DECLR3CALLBACKMEMBER(int, pfnIOPortRegister,(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTHCPTR pvUser,
2122 PFNIOMIOPORTOUT pfnOut, PFNIOMIOPORTIN pfnIn,
2123 PFNIOMIOPORTOUTSTRING pfnOutStr, PFNIOMIOPORTINSTRING pfnInStr, const char *pszDesc));
2124
2125 /**
2126 * Register a number of I/O ports with a device for RC.
2127 *
2128 * These callbacks are for the raw-mode context (RC). Register ring-3 context
2129 * (R3) handlers before raw-mode context handlers! There must be a R3 handler
2130 * for every RC handler!
2131 *
2132 * @returns VBox status.
2133 * @param pDevIns The device instance to register the ports with
2134 * and which RC module to resolve the names
2135 * against.
2136 * @param Port First port number in the range.
2137 * @param cPorts Number of ports to register.
2138 * @param pvUser User argument.
2139 * @param pszOut Name of the RC function which is gonna handle OUT operations.
2140 * @param pszIn Name of the RC function which is gonna handle IN operations.
2141 * @param pszOutStr Name of the RC function which is gonna handle string OUT operations.
2142 * @param pszInStr Name of the RC function which is gonna handle string IN operations.
2143 * @param pszDesc Pointer to description string. This must not be freed.
2144 */
2145 DECLR3CALLBACKMEMBER(int, pfnIOPortRegisterRC,(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTRCPTR pvUser,
2146 const char *pszOut, const char *pszIn,
2147 const char *pszOutStr, const char *pszInStr, const char *pszDesc));
2148
2149 /**
2150 * Register a number of I/O ports with a device.
2151 *
2152 * These callbacks are of course for the ring-0 host context (R0).
2153 * Register R3 (HC) handlers before R0 (R0) handlers! There must be a R3 (HC) handler for every R0 handler!
2154 *
2155 * @returns VBox status.
2156 * @param pDevIns The device instance to register the ports with.
2157 * @param Port First port number in the range.
2158 * @param cPorts Number of ports to register.
2159 * @param pvUser User argument. (if pointer, then it must be in locked memory!)
2160 * @param pszOut Name of the R0 function which is gonna handle OUT operations.
2161 * @param pszIn Name of the R0 function which is gonna handle IN operations.
2162 * @param pszOutStr Name of the R0 function which is gonna handle string OUT operations.
2163 * @param pszInStr Name of the R0 function which is gonna handle string IN operations.
2164 * @param pszDesc Pointer to description string. This must not be freed.
2165 */
2166 DECLR3CALLBACKMEMBER(int, pfnIOPortRegisterR0,(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTR0PTR pvUser,
2167 const char *pszOut, const char *pszIn,
2168 const char *pszOutStr, const char *pszInStr, const char *pszDesc));
2169
2170 /**
2171 * Deregister I/O ports.
2172 *
2173 * This naturally affects both guest context (GC), ring-0 (R0) and ring-3 (R3/HC) handlers.
2174 *
2175 * @returns VBox status.
2176 * @param pDevIns The device instance owning the ports.
2177 * @param Port First port number in the range.
2178 * @param cPorts Number of ports to deregister.
2179 */
2180 DECLR3CALLBACKMEMBER(int, pfnIOPortDeregister,(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts));
2181
2182 /**
2183 * Register a Memory Mapped I/O (MMIO) region.
2184 *
2185 * These callbacks are of course for the ring-3 context (R3). Register HC
2186 * handlers before raw-mode context (RC) and ring-0 context (R0) handlers! There
2187 * must be a R3 handler for every RC and R0 handler!
2188 *
2189 * @returns VBox status.
2190 * @param pDevIns The device instance to register the MMIO with.
2191 * @param GCPhysStart First physical address in the range.
2192 * @param cbRange The size of the range (in bytes).
2193 * @param pvUser User argument.
2194 * @param pfnWrite Pointer to function which is gonna handle Write operations.
2195 * @param pfnRead Pointer to function which is gonna handle Read operations.
2196 * @param pfnFill Pointer to function which is gonna handle Fill/memset operations. (optional)
2197 * @param pszDesc Pointer to description string. This must not be freed.
2198 */
2199 DECLR3CALLBACKMEMBER(int, pfnMMIORegister,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTHCPTR pvUser,
2200 PFNIOMMMIOWRITE pfnWrite, PFNIOMMMIOREAD pfnRead, PFNIOMMMIOFILL pfnFill,
2201 const char *pszDesc));
2202
2203 /**
2204 * Register a Memory Mapped I/O (MMIO) region for GC.
2205 *
2206 * These callbacks are for the raw-mode context (RC). Register ring-3 context
2207 * (R3) handlers before guest context handlers! There must be a R3 handler for
2208 * every RC handler!
2209 *
2210 * @returns VBox status.
2211 * @param pDevIns The device instance to register the MMIO with.
2212 * @param GCPhysStart First physical address in the range.
2213 * @param cbRange The size of the range (in bytes).
2214 * @param pvUser User argument.
2215 * @param pszWrite Name of the RC function which is gonna handle Write operations.
2216 * @param pszRead Name of the RC function which is gonna handle Read operations.
2217 * @param pszFill Name of the RC function which is gonna handle Fill/memset operations. (optional)
2218 * @param pszDesc Obsolete. NULL is fine.
2219 * @todo Remove pszDesc in the next major revision of PDMDEVHLPR3.
2220 */
2221 DECLR3CALLBACKMEMBER(int, pfnMMIORegisterRC,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTGCPTR pvUser,
2222 const char *pszWrite, const char *pszRead, const char *pszFill,
2223 const char *pszDesc));
2224
2225 /**
2226 * Register a Memory Mapped I/O (MMIO) region for R0.
2227 *
2228 * These callbacks are for the ring-0 host context (R0). Register ring-3
2229 * constext (R3) handlers before R0 handlers! There must be a R3 handler for
2230 * every R0 handler!
2231 *
2232 * @returns VBox status.
2233 * @param pDevIns The device instance to register the MMIO with.
2234 * @param GCPhysStart First physical address in the range.
2235 * @param cbRange The size of the range (in bytes).
2236 * @param pvUser User argument. (if pointer, then it must be in locked memory!)
2237 * @param pszWrite Name of the RC function which is gonna handle Write operations.
2238 * @param pszRead Name of the RC function which is gonna handle Read operations.
2239 * @param pszFill Name of the RC function which is gonna handle Fill/memset operations. (optional)
2240 * @param pszDesc Obsolete. NULL is fine.
2241 * @todo Remove pszDesc in the next major revision of PDMDEVHLPR3.
2242 */
2243 DECLR3CALLBACKMEMBER(int, pfnMMIORegisterR0,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTR0PTR pvUser,
2244 const char *pszWrite, const char *pszRead, const char *pszFill,
2245 const char *pszDesc));
2246
2247 /**
2248 * Deregister a Memory Mapped I/O (MMIO) region.
2249 *
2250 * This naturally affects both guest context (GC), ring-0 (R0) and ring-3 (R3/HC) handlers.
2251 *
2252 * @returns VBox status.
2253 * @param pDevIns The device instance owning the MMIO region(s).
2254 * @param GCPhysStart First physical address in the range.
2255 * @param cbRange The size of the range (in bytes).
2256 */
2257 DECLR3CALLBACKMEMBER(int, pfnMMIODeregister,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange));
2258
2259 /**
2260 * Allocate and register a MMIO2 region.
2261 *
2262 * As mentioned elsewhere, MMIO2 is just RAM spelled differently. It's
2263 * RAM associated with a device. It is also non-shared memory with a
2264 * permanent ring-3 mapping and page backing (presently).
2265 *
2266 * @returns VBox status.
2267 * @param pDevIns The device instance.
2268 * @param iRegion The region number. Use the PCI region number as
2269 * this must be known to the PCI bus device too. If
2270 * it's not associated with the PCI device, then
2271 * any number up to UINT8_MAX is fine.
2272 * @param cb The size (in bytes) of the region.
2273 * @param fFlags Reserved for future use, must be zero.
2274 * @param ppv Where to store the address of the ring-3 mapping
2275 * of the memory.
2276 * @param pszDesc Pointer to description string. This must not be
2277 * freed.
2278 * @thread EMT.
2279 */
2280 DECLR3CALLBACKMEMBER(int, pfnMMIO2Register,(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS cb, uint32_t fFlags, void **ppv, const char *pszDesc));
2281
2282 /**
2283 * Deregisters and frees a MMIO2 region.
2284 *
2285 * Any physical (and virtual) access handlers registered for the region must
2286 * be deregistered before calling this function.
2287 *
2288 * @returns VBox status code.
2289 * @param pDevIns The device instance.
2290 * @param iRegion The region number used during registration.
2291 * @thread EMT.
2292 */
2293 DECLR3CALLBACKMEMBER(int, pfnMMIO2Deregister,(PPDMDEVINS pDevIns, uint32_t iRegion));
2294
2295 /**
2296 * Maps a MMIO2 region into the physical memory space.
2297 *
2298 * A MMIO2 range may overlap with base memory if a lot of RAM
2299 * is configured for the VM, in which case we'll drop the base
2300 * memory pages. Presently we will make no attempt to preserve
2301 * anything that happens to be present in the base memory that
2302 * is replaced, this is of course incorrectly but it's too much
2303 * effort.
2304 *
2305 * @returns VBox status code.
2306 * @param pDevIns The device instance.
2307 * @param iRegion The region number used during registration.
2308 * @param GCPhys The physical address to map it at.
2309 * @thread EMT.
2310 */
2311 DECLR3CALLBACKMEMBER(int, pfnMMIO2Map,(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS GCPhys));
2312
2313 /**
2314 * Unmaps a MMIO2 region previously mapped using pfnMMIO2Map.
2315 *
2316 * @returns VBox status code.
2317 * @param pDevIns The device instance.
2318 * @param iRegion The region number used during registration.
2319 * @param GCPhys The physical address it's currently mapped at.
2320 * @thread EMT.
2321 */
2322 DECLR3CALLBACKMEMBER(int, pfnMMIO2Unmap,(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS GCPhys));
2323
2324 /**
2325 * Maps a portion of an MMIO2 region into the hypervisor region.
2326 *
2327 * Callers of this API must never deregister the MMIO2 region before the
2328 * VM is powered off.
2329 *
2330 * @return VBox status code.
2331 * @param pDevIns The device owning the MMIO2 memory.
2332 * @param iRegion The region.
2333 * @param off The offset into the region. Will be rounded down
2334 * to closest page boundary.
2335 * @param cb The number of bytes to map. Will be rounded up
2336 * to the closest page boundary.
2337 * @param pszDesc Mapping description.
2338 * @param pRCPtr Where to store the RC address.
2339 */
2340 DECLR3CALLBACKMEMBER(int, pfnMMHyperMapMMIO2,(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS off, RTGCPHYS cb,
2341 const char *pszDesc, PRTRCPTR pRCPtr));
2342
2343 /**
2344 * Maps a portion of an MMIO2 region into kernel space (host).
2345 *
2346 * The kernel mapping will become invalid when the MMIO2 memory is deregistered
2347 * or the VM is terminated.
2348 *
2349 * @return VBox status code.
2350 * @param pDevIns The device owning the MMIO2 memory.
2351 * @param iRegion The region.
2352 * @param off The offset into the region. Must be page
2353 * aligned.
2354 * @param cb The number of bytes to map. Must be page
2355 * aligned.
2356 * @param pszDesc Mapping description.
2357 * @param pR0Ptr Where to store the R0 address.
2358 */
2359 DECLR3CALLBACKMEMBER(int, pfnMMIO2MapKernel,(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS off, RTGCPHYS cb,
2360 const char *pszDesc, PRTR0PTR pR0Ptr));
2361
2362 /**
2363 * Register a ROM (BIOS) region.
2364 *
2365 * It goes without saying that this is read-only memory. The memory region must be
2366 * in unassigned memory. I.e. from the top of the address space or on the PC in
2367 * the 0xa0000-0xfffff range.
2368 *
2369 * @returns VBox status.
2370 * @param pDevIns The device instance owning the ROM region.
2371 * @param GCPhysStart First physical address in the range.
2372 * Must be page aligned!
2373 * @param cbRange The size of the range (in bytes).
2374 * Must be page aligned!
2375 * @param pvBinary Pointer to the binary data backing the ROM image.
2376 * @param cbBinary The size of the binary pointer. This must
2377 * be equal or smaller than @a cbRange.
2378 * @param fFlags Shadow ROM flags, PGMPHYS_ROM_FLAGS_* in pgm.h.
2379 * @param pszDesc Pointer to description string. This must not be freed.
2380 *
2381 * @remark There is no way to remove the rom, automatically on device cleanup or
2382 * manually from the device yet. At present I doubt we need such features...
2383 */
2384 DECLR3CALLBACKMEMBER(int, pfnROMRegister,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange,
2385 const void *pvBinary, uint32_t cbBinary, uint32_t fFlags, const char *pszDesc));
2386
2387 /**
2388 * Changes the protection of shadowed ROM mapping.
2389 *
2390 * This is intented for use by the system BIOS, chipset or device in question to
2391 * change the protection of shadowed ROM code after init and on reset.
2392 *
2393 * @param pDevIns The device instance.
2394 * @param GCPhysStart Where the mapping starts.
2395 * @param cbRange The size of the mapping.
2396 * @param enmProt The new protection type.
2397 */
2398 DECLR3CALLBACKMEMBER(int, pfnROMProtectShadow,(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, PGMROMPROT enmProt));
2399
2400 /**
2401 * Register a save state data unit.
2402 *
2403 * @returns VBox status.
2404 * @param pDevIns The device instance.
2405 * @param pszName Data unit name.
2406 * @param uInstance The instance identifier of the data unit.
2407 * This must together with the name be unique.
2408 * @param uVersion Data layout version number.
2409 * @param cbGuess The approximate amount of data in the unit.
2410 * Only for progress indicators.
2411 * @param pszBefore Name of data unit which we should be put in
2412 * front of. Optional (NULL).
2413 *
2414 * @param pfnLivePrep Prepare live save callback, optional.
2415 * @param pfnLiveExec Execute live save callback, optional.
2416 * @param pfnLiveVote Vote live save callback, optional.
2417 *
2418 * @param pfnSavePrep Prepare save callback, optional.
2419 * @param pfnSaveExec Execute save callback, optional.
2420 * @param pfnSaveDone Done save callback, optional.
2421 *
2422 * @param pfnLoadPrep Prepare load callback, optional.
2423 * @param pfnLoadExec Execute load callback, optional.
2424 * @param pfnLoadDone Done load callback, optional.
2425 */
2426 DECLR3CALLBACKMEMBER(int, pfnSSMRegister,(PPDMDEVINS pDevIns, uint32_t uVersion, size_t cbGuess, const char *pszBefore,
2427 PFNSSMDEVLIVEPREP pfnLivePrep, PFNSSMDEVLIVEEXEC pfnLiveExec, PFNSSMDEVLIVEVOTE pfnLiveVote,
2428 PFNSSMDEVSAVEPREP pfnSavePrep, PFNSSMDEVSAVEEXEC pfnSaveExec, PFNSSMDEVSAVEDONE pfnSaveDone,
2429 PFNSSMDEVLOADPREP pfnLoadPrep, PFNSSMDEVLOADEXEC pfnLoadExec, PFNSSMDEVLOADDONE pfnLoadDone));
2430
2431 /**
2432 * Creates a timer.
2433 *
2434 * @returns VBox status.
2435 * @param pDevIns The device instance.
2436 * @param enmClock The clock to use on this timer.
2437 * @param pfnCallback Callback function.
2438 * @param pvUser User argument for the callback.
2439 * @param fFlags Flags, see TMTIMER_FLAGS_*.
2440 * @param pszDesc Pointer to description string which must stay around
2441 * until the timer is fully destroyed (i.e. a bit after TMTimerDestroy()).
2442 * @param ppTimer Where to store the timer on success.
2443 */
2444 DECLR3CALLBACKMEMBER(int, pfnTMTimerCreate,(PPDMDEVINS pDevIns, TMCLOCK enmClock, PFNTMTIMERDEV pfnCallback, void *pvUser, uint32_t fFlags, const char *pszDesc, PPTMTIMERR3 ppTimer));
2445
2446 /**
2447 * Get the real world UTC time adjusted for VM lag, user offset and warpdrive.
2448 *
2449 * @returns pTime.
2450 * @param pDevIns The device instance.
2451 * @param pTime Where to store the time.
2452 */
2453 DECLR3CALLBACKMEMBER(PRTTIMESPEC, pfnTMUtcNow,(PPDMDEVINS pDevIns, PRTTIMESPEC pTime));
2454
2455 /**
2456 * Read physical memory.
2457 *
2458 * @returns VINF_SUCCESS (for now).
2459 * @param pDevIns The device instance.
2460 * @param GCPhys Physical address start reading from.
2461 * @param pvBuf Where to put the read bits.
2462 * @param cbRead How many bytes to read.
2463 * @thread Any thread, but the call may involve the emulation thread.
2464 */
2465 DECLR3CALLBACKMEMBER(int, pfnPhysRead,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, void *pvBuf, size_t cbRead));
2466
2467 /**
2468 * Write to physical memory.
2469 *
2470 * @returns VINF_SUCCESS for now, and later maybe VERR_EM_MEMORY.
2471 * @param pDevIns The device instance.
2472 * @param GCPhys Physical address to write to.
2473 * @param pvBuf What to write.
2474 * @param cbWrite How many bytes to write.
2475 * @thread Any thread, but the call may involve the emulation thread.
2476 */
2477 DECLR3CALLBACKMEMBER(int, pfnPhysWrite,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, const void *pvBuf, size_t cbWrite));
2478
2479 /**
2480 * Requests the mapping of a guest page into ring-3.
2481 *
2482 * When you're done with the page, call pfnPhysReleasePageMappingLock() ASAP to
2483 * release it.
2484 *
2485 * This API will assume your intention is to write to the page, and will
2486 * therefore replace shared and zero pages. If you do not intend to modify the
2487 * page, use the pfnPhysGCPhys2CCPtrReadOnly() API.
2488 *
2489 * @returns VBox status code.
2490 * @retval VINF_SUCCESS on success.
2491 * @retval VERR_PGM_PHYS_PAGE_RESERVED it it's a valid page but has no physical
2492 * backing or if the page has any active access handlers. The caller
2493 * must fall back on using PGMR3PhysWriteExternal.
2494 * @retval VERR_PGM_INVALID_GC_PHYSICAL_ADDRESS if it's not a valid physical address.
2495 *
2496 * @param pVM The VM handle.
2497 * @param GCPhys The guest physical address of the page that
2498 * should be mapped.
2499 * @param fFlags Flags reserved for future use, MBZ.
2500 * @param ppv Where to store the address corresponding to
2501 * GCPhys.
2502 * @param pLock Where to store the lock information that
2503 * pfnPhysReleasePageMappingLock needs.
2504 *
2505 * @remark Avoid calling this API from within critical sections (other than the
2506 * PGM one) because of the deadlock risk when we have to delegating the
2507 * task to an EMT.
2508 * @thread Any.
2509 */
2510 DECLR3CALLBACKMEMBER(int, pfnPhysGCPhys2CCPtr,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, uint32_t fFlags, void **ppv, PPGMPAGEMAPLOCK pLock));
2511
2512 /**
2513 * Requests the mapping of a guest page into ring-3, external threads.
2514 *
2515 * When you're done with the page, call pfnPhysReleasePageMappingLock() ASAP to
2516 * release it.
2517 *
2518 * @returns VBox status code.
2519 * @retval VINF_SUCCESS on success.
2520 * @retval VERR_PGM_PHYS_PAGE_RESERVED it it's a valid page but has no physical
2521 * backing or if the page as an active ALL access handler. The caller
2522 * must fall back on using PGMPhysRead.
2523 * @retval VERR_PGM_INVALID_GC_PHYSICAL_ADDRESS if it's not a valid physical address.
2524 *
2525 * @param pDevIns The device instance.
2526 * @param GCPhys The guest physical address of the page that
2527 * should be mapped.
2528 * @param fFlags Flags reserved for future use, MBZ.
2529 * @param ppv Where to store the address corresponding to
2530 * GCPhys.
2531 * @param pLock Where to store the lock information that
2532 * pfnPhysReleasePageMappingLock needs.
2533 *
2534 * @remark Avoid calling this API from within critical sections.
2535 * @thread Any.
2536 */
2537 DECLR3CALLBACKMEMBER(int, pfnPhysGCPhys2CCPtrReadOnly,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, uint32_t fFlags, void const **ppv, PPGMPAGEMAPLOCK pLock));
2538
2539 /**
2540 * Release the mapping of a guest page.
2541 *
2542 * This is the counter part of pfnPhysGCPhys2CCPtr and
2543 * pfnPhysGCPhys2CCPtrReadOnly.
2544 *
2545 * @param pDevIns The device instance.
2546 * @param pLock The lock structure initialized by the mapping
2547 * function.
2548 */
2549 DECLR3CALLBACKMEMBER(void, pfnPhysReleasePageMappingLock,(PPDMDEVINS pDevIns, PPGMPAGEMAPLOCK pLock));
2550
2551 /**
2552 * Read guest physical memory by virtual address.
2553 *
2554 * @param pDevIns The device instance.
2555 * @param pvDst Where to put the read bits.
2556 * @param GCVirtSrc Guest virtual address to start reading from.
2557 * @param cb How many bytes to read.
2558 * @thread The emulation thread.
2559 */
2560 DECLR3CALLBACKMEMBER(int, pfnPhysReadGCVirt,(PPDMDEVINS pDevIns, void *pvDst, RTGCPTR GCVirtSrc, size_t cb));
2561
2562 /**
2563 * Write to guest physical memory by virtual address.
2564 *
2565 * @param pDevIns The device instance.
2566 * @param GCVirtDst Guest virtual address to write to.
2567 * @param pvSrc What to write.
2568 * @param cb How many bytes to write.
2569 * @thread The emulation thread.
2570 */
2571 DECLR3CALLBACKMEMBER(int, pfnPhysWriteGCVirt,(PPDMDEVINS pDevIns, RTGCPTR GCVirtDst, const void *pvSrc, size_t cb));
2572
2573 /**
2574 * Convert a guest virtual address to a guest physical address.
2575 *
2576 * @returns VBox status code.
2577 * @param pDevIns The device instance.
2578 * @param GCPtr Guest virtual address.
2579 * @param pGCPhys Where to store the GC physical address
2580 * corresponding to GCPtr.
2581 * @thread The emulation thread.
2582 * @remark Careful with page boundaries.
2583 */
2584 DECLR3CALLBACKMEMBER(int, pfnPhysGCPtr2GCPhys, (PPDMDEVINS pDevIns, RTGCPTR GCPtr, PRTGCPHYS pGCPhys));
2585
2586 /**
2587 * Allocate memory which is associated with current VM instance
2588 * and automatically freed on it's destruction.
2589 *
2590 * @returns Pointer to allocated memory. The memory is *NOT* zero-ed.
2591 * @param pDevIns The device instance.
2592 * @param cb Number of bytes to allocate.
2593 */
2594 DECLR3CALLBACKMEMBER(void *, pfnMMHeapAlloc,(PPDMDEVINS pDevIns, size_t cb));
2595
2596 /**
2597 * Allocate memory which is associated with current VM instance
2598 * and automatically freed on it's destruction. The memory is ZEROed.
2599 *
2600 * @returns Pointer to allocated memory. The memory is *NOT* zero-ed.
2601 * @param pDevIns The device instance.
2602 * @param cb Number of bytes to allocate.
2603 */
2604 DECLR3CALLBACKMEMBER(void *, pfnMMHeapAllocZ,(PPDMDEVINS pDevIns, size_t cb));
2605
2606 /**
2607 * Free memory allocated with pfnMMHeapAlloc() and pfnMMHeapAllocZ().
2608 *
2609 * @param pDevIns The device instance.
2610 * @param pv Pointer to the memory to free.
2611 */
2612 DECLR3CALLBACKMEMBER(void, pfnMMHeapFree,(PPDMDEVINS pDevIns, void *pv));
2613
2614 /**
2615 * Gets the VM state.
2616 *
2617 * @returns VM state.
2618 * @param pDevIns The device instance.
2619 * @thread Any thread (just keep in mind that it's volatile info).
2620 */
2621 DECLR3CALLBACKMEMBER(VMSTATE, pfnVMState, (PPDMDEVINS pDevIns));
2622
2623 /**
2624 * Checks if the VM was teleported and hasn't been fully resumed yet.
2625 *
2626 * @returns true / false.
2627 * @param pDevIns The device instance.
2628 * @thread Any thread.
2629 */
2630 DECLR3CALLBACKMEMBER(bool, pfnVMTeleportedAndNotFullyResumedYet,(PPDMDEVINS pDevIns));
2631
2632 /**
2633 * Set the VM error message
2634 *
2635 * @returns rc.
2636 * @param pDevIns The device instance.
2637 * @param rc VBox status code.
2638 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
2639 * @param pszFormat Error message format string.
2640 * @param ... Error message arguments.
2641 */
2642 DECLR3CALLBACKMEMBER(int, pfnVMSetError,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, ...));
2643
2644 /**
2645 * Set the VM error message
2646 *
2647 * @returns rc.
2648 * @param pDevIns The device instance.
2649 * @param rc VBox status code.
2650 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
2651 * @param pszFormat Error message format string.
2652 * @param va Error message arguments.
2653 */
2654 DECLR3CALLBACKMEMBER(int, pfnVMSetErrorV,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, va_list va));
2655
2656 /**
2657 * Set the VM runtime error message
2658 *
2659 * @returns VBox status code.
2660 * @param pDevIns The device instance.
2661 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
2662 * @param pszErrorId Error ID string.
2663 * @param pszFormat Error message format string.
2664 * @param ... Error message arguments.
2665 */
2666 DECLR3CALLBACKMEMBER(int, pfnVMSetRuntimeError,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, ...));
2667
2668 /**
2669 * Set the VM runtime error message
2670 *
2671 * @returns VBox status code.
2672 * @param pDevIns The device instance.
2673 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
2674 * @param pszErrorId Error ID string.
2675 * @param pszFormat Error message format string.
2676 * @param va Error message arguments.
2677 */
2678 DECLR3CALLBACKMEMBER(int, pfnVMSetRuntimeErrorV,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, va_list va));
2679
2680 /**
2681 * Stops the VM and enters the debugger to look at the guest state.
2682 *
2683 * Use the PDMDeviceDBGFStop() inline function with the RT_SRC_POS macro instead of
2684 * invoking this function directly.
2685 *
2686 * @returns VBox status code which must be passed up to the VMM.
2687 * @param pDevIns The device instance.
2688 * @param pszFile Filename of the assertion location.
2689 * @param iLine The linenumber of the assertion location.
2690 * @param pszFunction Function of the assertion location.
2691 * @param pszFormat Message. (optional)
2692 * @param args Message parameters.
2693 */
2694 DECLR3CALLBACKMEMBER(int, pfnDBGFStopV,(PPDMDEVINS pDevIns, const char *pszFile, unsigned iLine, const char *pszFunction, const char *pszFormat, va_list args));
2695
2696 /**
2697 * Register a info handler with DBGF,
2698 *
2699 * @returns VBox status code.
2700 * @param pDevIns The device instance.
2701 * @param pszName The identifier of the info.
2702 * @param pszDesc The description of the info and any arguments
2703 * the handler may take.
2704 * @param pfnHandler The handler function to be called to display the
2705 * info.
2706 */
2707 DECLR3CALLBACKMEMBER(int, pfnDBGFInfoRegister,(PPDMDEVINS pDevIns, const char *pszName, const char *pszDesc, PFNDBGFHANDLERDEV pfnHandler));
2708
2709 /**
2710 * Registers a statistics sample if statistics are enabled.
2711 *
2712 * @param pDevIns Device instance of the DMA.
2713 * @param pvSample Pointer to the sample.
2714 * @param enmType Sample type. This indicates what pvSample is
2715 * pointing at.
2716 * @param pszName Sample name. The name is on this form
2717 * "/<component>/<sample>". Further nesting is
2718 * possible.
2719 * @param enmUnit Sample unit.
2720 * @param pszDesc Sample description.
2721 */
2722 DECLR3CALLBACKMEMBER(void, pfnSTAMRegister,(PPDMDEVINS pDevIns, void *pvSample, STAMTYPE enmType, const char *pszName, STAMUNIT enmUnit, const char *pszDesc));
2723
2724 /**
2725 * Same as pfnSTAMRegister except that the name is specified in a
2726 * RTStrPrintf like fashion.
2727 *
2728 * @returns VBox status.
2729 * @param pDevIns Device instance of the DMA.
2730 * @param pvSample Pointer to the sample.
2731 * @param enmType Sample type. This indicates what pvSample is
2732 * pointing at.
2733 * @param enmVisibility Visibility type specifying whether unused
2734 * statistics should be visible or not.
2735 * @param enmUnit Sample unit.
2736 * @param pszDesc Sample description.
2737 * @param pszName The sample name format string.
2738 * @param ... Arguments to the format string.
2739 */
2740 DECLR3CALLBACKMEMBER(void, pfnSTAMRegisterF,(PPDMDEVINS pDevIns, void *pvSample, STAMTYPE enmType, STAMVISIBILITY enmVisibility,
2741 STAMUNIT enmUnit, const char *pszDesc, const char *pszName, ...));
2742
2743 /**
2744 * Same as pfnSTAMRegister except that the name is specified in a
2745 * RTStrPrintfV like fashion.
2746 *
2747 * @returns VBox status.
2748 * @param pDevIns Device instance of the DMA.
2749 * @param pvSample Pointer to the sample.
2750 * @param enmType Sample type. This indicates what pvSample is
2751 * pointing at.
2752 * @param enmVisibility Visibility type specifying whether unused
2753 * statistics should be visible or not.
2754 * @param enmUnit Sample unit.
2755 * @param pszDesc Sample description.
2756 * @param pszName The sample name format string.
2757 * @param args Arguments to the format string.
2758 */
2759 DECLR3CALLBACKMEMBER(void, pfnSTAMRegisterV,(PPDMDEVINS pDevIns, void *pvSample, STAMTYPE enmType, STAMVISIBILITY enmVisibility,
2760 STAMUNIT enmUnit, const char *pszDesc, const char *pszName, va_list args));
2761
2762 /**
2763 * Registers the device with the default PCI bus.
2764 *
2765 * @returns VBox status code.
2766 * @param pDevIns The device instance.
2767 * @param pPciDev The PCI device structure.
2768 * Any PCI enabled device must keep this in it's instance data!
2769 * Fill in the PCI data config before registration, please.
2770 * @remark This is the simple interface, a Ex interface will be created if
2771 * more features are needed later.
2772 */
2773 DECLR3CALLBACKMEMBER(int, pfnPCIRegister,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev));
2774
2775 /**
2776 * Initialize MSI support in a PCI device.
2777 *
2778 * @returns VBox status code.
2779 * @param pDevIns The device instance.
2780 * @param pMsiReg MSI registartion structure.
2781 */
2782 DECLR3CALLBACKMEMBER(int, pfnPCIRegisterMsi,(PPDMDEVINS pDevIns, PPDMMSIREG pMsiReg));
2783
2784 /**
2785 * Registers a I/O region (memory mapped or I/O ports) for a PCI device.
2786 *
2787 * @returns VBox status code.
2788 * @param pDevIns The device instance.
2789 * @param iRegion The region number.
2790 * @param cbRegion Size of the region.
2791 * @param enmType PCI_ADDRESS_SPACE_MEM, PCI_ADDRESS_SPACE_IO or PCI_ADDRESS_SPACE_MEM_PREFETCH.
2792 * @param pfnCallback Callback for doing the mapping.
2793 */
2794 DECLR3CALLBACKMEMBER(int, pfnPCIIORegionRegister,(PPDMDEVINS pDevIns, int iRegion, uint32_t cbRegion, PCIADDRESSSPACE enmType, PFNPCIIOREGIONMAP pfnCallback));
2795
2796 /**
2797 * Register PCI configuration space read/write callbacks.
2798 *
2799 * @param pDevIns The device instance.
2800 * @param pPciDev The PCI device structure.
2801 * If NULL the default PCI device for this device instance is used.
2802 * @param pfnRead Pointer to the user defined PCI config read function.
2803 * @param ppfnReadOld Pointer to function pointer which will receive the old (default)
2804 * PCI config read function. This way, user can decide when (and if)
2805 * to call default PCI config read function. Can be NULL.
2806 * @param pfnWrite Pointer to the user defined PCI config write function.
2807 * @param pfnWriteOld Pointer to function pointer which will receive the old (default)
2808 * PCI config write function. This way, user can decide when (and if)
2809 * to call default PCI config write function. Can be NULL.
2810 * @thread EMT
2811 */
2812 DECLR3CALLBACKMEMBER(void, pfnPCISetConfigCallbacks,(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PFNPCICONFIGREAD pfnRead, PPFNPCICONFIGREAD ppfnReadOld,
2813 PFNPCICONFIGWRITE pfnWrite, PPFNPCICONFIGWRITE ppfnWriteOld));
2814
2815 /**
2816 * Set the IRQ for a PCI device.
2817 *
2818 * @param pDevIns The device instance.
2819 * @param iIrq IRQ number to set.
2820 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
2821 * @thread Any thread, but will involve the emulation thread.
2822 */
2823 DECLR3CALLBACKMEMBER(void, pfnPCISetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
2824
2825 /**
2826 * Set the IRQ for a PCI device, but don't wait for EMT to process
2827 * the request when not called from EMT.
2828 *
2829 * @param pDevIns The device instance.
2830 * @param iIrq IRQ number to set.
2831 * @param iLevel IRQ level.
2832 * @thread Any thread, but will involve the emulation thread.
2833 */
2834 DECLR3CALLBACKMEMBER(void, pfnPCISetIrqNoWait,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
2835
2836 /**
2837 * Set ISA IRQ for a device.
2838 *
2839 * @param pDevIns The device instance.
2840 * @param iIrq IRQ number to set.
2841 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
2842 * @thread Any thread, but will involve the emulation thread.
2843 */
2844 DECLR3CALLBACKMEMBER(void, pfnISASetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
2845
2846 /**
2847 * Set the ISA IRQ for a device, but don't wait for EMT to process
2848 * the request when not called from EMT.
2849 *
2850 * @param pDevIns The device instance.
2851 * @param iIrq IRQ number to set.
2852 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
2853 * @thread Any thread, but will involve the emulation thread.
2854 */
2855 DECLR3CALLBACKMEMBER(void, pfnISASetIrqNoWait,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
2856
2857 /**
2858 * Attaches a driver (chain) to the device.
2859 *
2860 * The first call for a LUN this will serve as a registartion of the LUN. The pBaseInterface and
2861 * the pszDesc string will be registered with that LUN and kept around for PDMR3QueryDeviceLun().
2862 *
2863 * @returns VBox status code.
2864 * @param pDevIns The device instance.
2865 * @param iLun The logical unit to attach.
2866 * @param pBaseInterface Pointer to the base interface for that LUN. (device side / down)
2867 * @param ppBaseInterface Where to store the pointer to the base interface. (driver side / up)
2868 * @param pszDesc Pointer to a string describing the LUN. This string must remain valid
2869 * for the live of the device instance.
2870 */
2871 DECLR3CALLBACKMEMBER(int, pfnDriverAttach,(PPDMDEVINS pDevIns, RTUINT iLun, PPDMIBASE pBaseInterface, PPDMIBASE *ppBaseInterface, const char *pszDesc));
2872
2873 /**
2874 * Create a queue.
2875 *
2876 * @returns VBox status code.
2877 * @param pDevIns The device instance.
2878 * @param cbItem The size of a queue item.
2879 * @param cItems The number of items in the queue.
2880 * @param cMilliesInterval The number of milliseconds between polling the queue.
2881 * If 0 then the emulation thread will be notified whenever an item arrives.
2882 * @param pfnCallback The consumer function.
2883 * @param fRZEnabled Set if the queue should work in RC and R0.
2884 * @param pszName The queue base name. The instance number will be
2885 * appended automatically.
2886 * @param ppQueue Where to store the queue handle on success.
2887 * @thread The emulation thread.
2888 */
2889 DECLR3CALLBACKMEMBER(int, pfnQueueCreate,(PPDMDEVINS pDevIns, RTUINT cbItem, RTUINT cItems, uint32_t cMilliesInterval,
2890 PFNPDMQUEUEDEV pfnCallback, bool fRZEnabled, const char *pszName, PPDMQUEUE *ppQueue));
2891
2892 /**
2893 * Initializes a PDM critical section.
2894 *
2895 * The PDM critical sections are derived from the IPRT critical sections, but
2896 * works in RC and R0 as well.
2897 *
2898 * @returns VBox status code.
2899 * @param pDevIns The device instance.
2900 * @param pCritSect Pointer to the critical section.
2901 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
2902 * @param pszNameFmt Format string for naming the critical section.
2903 * For statistics and lock validation.
2904 * @param va Arguments for the format string.
2905 */
2906 DECLR3CALLBACKMEMBER(int, pfnCritSectInit,(PPDMDEVINS pDevIns, PPDMCRITSECT pCritSect, RT_SRC_POS_DECL,
2907 const char *pszNameFmt, va_list va));
2908
2909 /**
2910 * Creates a PDM thread.
2911 *
2912 * This differs from the RTThreadCreate() API in that PDM takes care of suspending,
2913 * resuming, and destroying the thread as the VM state changes.
2914 *
2915 * @returns VBox status code.
2916 * @param pDevIns The device instance.
2917 * @param ppThread Where to store the thread 'handle'.
2918 * @param pvUser The user argument to the thread function.
2919 * @param pfnThread The thread function.
2920 * @param pfnWakeup The wakup callback. This is called on the EMT
2921 * thread when a state change is pending.
2922 * @param cbStack See RTThreadCreate.
2923 * @param enmType See RTThreadCreate.
2924 * @param pszName See RTThreadCreate.
2925 */
2926 DECLR3CALLBACKMEMBER(int, pfnThreadCreate,(PPDMDEVINS pDevIns, PPPDMTHREAD ppThread, void *pvUser, PFNPDMTHREADDEV pfnThread,
2927 PFNPDMTHREADWAKEUPDEV pfnWakeup, size_t cbStack, RTTHREADTYPE enmType, const char *pszName));
2928
2929 /**
2930 * Set up asynchronous handling of a suspend, reset or power off notification.
2931 *
2932 * This shall only be called when getting the notification. It must be called
2933 * for each one.
2934 *
2935 * @returns VBox status code.
2936 * @param pDevIns The device instance.
2937 * @param pfnAsyncNotify The callback.
2938 * @thread EMT(0)
2939 */
2940 DECLR3CALLBACKMEMBER(int, pfnSetAsyncNotification, (PPDMDEVINS pDevIns, PFNPDMDEVASYNCNOTIFY pfnAsyncNotify));
2941
2942 /**
2943 * Notify EMT(0) that the device has completed the asynchronous notification
2944 * handling.
2945 *
2946 * This can be called at any time, spurious calls will simply be ignored.
2947 *
2948 * @param pDevIns The device instance.
2949 * @thread Any
2950 */
2951 DECLR3CALLBACKMEMBER(void, pfnAsyncNotificationCompleted, (PPDMDEVINS pDevIns));
2952
2953 /**
2954 * Register the RTC device.
2955 *
2956 * @returns VBox status code.
2957 * @param pDevIns The device instance.
2958 * @param pRtcReg Pointer to a RTC registration structure.
2959 * @param ppRtcHlp Where to store the pointer to the helper
2960 * functions.
2961 */
2962 DECLR3CALLBACKMEMBER(int, pfnRTCRegister,(PPDMDEVINS pDevIns, PCPDMRTCREG pRtcReg, PCPDMRTCHLP *ppRtcHlp));
2963
2964 /**
2965 * Register the PCI Bus.
2966 *
2967 * @returns VBox status code.
2968 * @param pDevIns The device instance.
2969 * @param pPciBusReg Pointer to PCI bus registration structure.
2970 * @param ppPciHlpR3 Where to store the pointer to the PCI Bus
2971 * helpers.
2972 */
2973 DECLR3CALLBACKMEMBER(int, pfnPCIBusRegister,(PPDMDEVINS pDevIns, PPDMPCIBUSREG pPciBusReg, PCPDMPCIHLPR3 *ppPciHlpR3));
2974
2975 /**
2976 * Register the PIC device.
2977 *
2978 * @returns VBox status code.
2979 * @param pDevIns The device instance.
2980 * @param pPicReg Pointer to a PIC registration structure.
2981 * @param ppPicHlpR3 Where to store the pointer to the PIC HC
2982 * helpers.
2983 */
2984 DECLR3CALLBACKMEMBER(int, pfnPICRegister,(PPDMDEVINS pDevIns, PPDMPICREG pPicReg, PCPDMPICHLPR3 *ppPicHlpR3));
2985
2986 /**
2987 * Register the APIC device.
2988 *
2989 * @returns VBox status code.
2990 * @param pDevIns The device instance.
2991 * @param pApicReg Pointer to a APIC registration structure.
2992 * @param ppApicHlpR3 Where to store the pointer to the APIC helpers.
2993 */
2994 DECLR3CALLBACKMEMBER(int, pfnAPICRegister,(PPDMDEVINS pDevIns, PPDMAPICREG pApicReg, PCPDMAPICHLPR3 *ppApicHlpR3));
2995
2996 /**
2997 * Register the I/O APIC device.
2998 *
2999 * @returns VBox status code.
3000 * @param pDevIns The device instance.
3001 * @param pIoApicReg Pointer to a I/O APIC registration structure.
3002 * @param ppIoApicHlpR3 Where to store the pointer to the IOAPIC
3003 * helpers.
3004 */
3005 DECLR3CALLBACKMEMBER(int, pfnIOAPICRegister,(PPDMDEVINS pDevIns, PPDMIOAPICREG pIoApicReg, PCPDMIOAPICHLPR3 *ppIoApicHlpR3));
3006
3007 /**
3008 * Register the HPET device.
3009 *
3010 * @returns VBox status code.
3011 * @param pDevIns The device instance.
3012 * @param pHpetReg Pointer to a HPET registration structure.
3013 * @param ppHpetHlpR3 Where to store the pointer to the HPET
3014 * helpers.
3015 */
3016 DECLR3CALLBACKMEMBER(int, pfnHPETRegister,(PPDMDEVINS pDevIns, PPDMHPETREG pHpetReg, PCPDMHPETHLPR3 *ppHpetHlpR3));
3017
3018 /**
3019 * Register a raw PCI device.
3020 *
3021 * @returns VBox status code.
3022 * @param pDevIns The device instance.
3023 * @param pHpetReg Pointer to a raw PCI registration structure.
3024 * @param ppPciRawHlpR3 Where to store the pointer to the raw PCI
3025 * device helpers.
3026 */
3027 DECLR3CALLBACKMEMBER(int, pfnPciRawRegister,(PPDMDEVINS pDevIns, PPDMPCIRAWREG pPciRawReg, PCPDMPCIRAWHLPR3 *ppPciRawHlpR3));
3028
3029 /**
3030 * Register the DMA device.
3031 *
3032 * @returns VBox status code.
3033 * @param pDevIns The device instance.
3034 * @param pDmacReg Pointer to a DMAC registration structure.
3035 * @param ppDmacHlp Where to store the pointer to the DMA helpers.
3036 */
3037 DECLR3CALLBACKMEMBER(int, pfnDMACRegister,(PPDMDEVINS pDevIns, PPDMDMACREG pDmacReg, PCPDMDMACHLP *ppDmacHlp));
3038
3039 /**
3040 * Register transfer function for DMA channel.
3041 *
3042 * @returns VBox status code.
3043 * @param pDevIns The device instance.
3044 * @param uChannel Channel number.
3045 * @param pfnTransferHandler Device specific transfer callback function.
3046 * @param pvUser User pointer to pass to the callback.
3047 * @thread EMT
3048 */
3049 DECLR3CALLBACKMEMBER(int, pfnDMARegister,(PPDMDEVINS pDevIns, unsigned uChannel, PFNDMATRANSFERHANDLER pfnTransferHandler, void *pvUser));
3050
3051 /**
3052 * Read memory.
3053 *
3054 * @returns VBox status code.
3055 * @param pDevIns The device instance.
3056 * @param uChannel Channel number.
3057 * @param pvBuffer Pointer to target buffer.
3058 * @param off DMA position.
3059 * @param cbBlock Block size.
3060 * @param pcbRead Where to store the number of bytes which was
3061 * read. optional.
3062 * @thread EMT
3063 */
3064 DECLR3CALLBACKMEMBER(int, pfnDMAReadMemory,(PPDMDEVINS pDevIns, unsigned uChannel, void *pvBuffer, uint32_t off, uint32_t cbBlock, uint32_t *pcbRead));
3065
3066 /**
3067 * Write memory.
3068 *
3069 * @returns VBox status code.
3070 * @param pDevIns The device instance.
3071 * @param uChannel Channel number.
3072 * @param pvBuffer Memory to write.
3073 * @param off DMA position.
3074 * @param cbBlock Block size.
3075 * @param pcbWritten Where to store the number of bytes which was
3076 * written. optional.
3077 * @thread EMT
3078 */
3079 DECLR3CALLBACKMEMBER(int, pfnDMAWriteMemory,(PPDMDEVINS pDevIns, unsigned uChannel, const void *pvBuffer, uint32_t off, uint32_t cbBlock, uint32_t *pcbWritten));
3080
3081 /**
3082 * Set the DREQ line.
3083 *
3084 * @returns VBox status code.
3085 * @param pDevIns Device instance.
3086 * @param uChannel Channel number.
3087 * @param uLevel Level of the line.
3088 * @thread EMT
3089 */
3090 DECLR3CALLBACKMEMBER(int, pfnDMASetDREQ,(PPDMDEVINS pDevIns, unsigned uChannel, unsigned uLevel));
3091
3092 /**
3093 * Get channel mode.
3094 *
3095 * @returns Channel mode. See specs.
3096 * @param pDevIns The device instance.
3097 * @param uChannel Channel number.
3098 * @thread EMT
3099 */
3100 DECLR3CALLBACKMEMBER(uint8_t, pfnDMAGetChannelMode,(PPDMDEVINS pDevIns, unsigned uChannel));
3101
3102 /**
3103 * Schedule DMA execution.
3104 *
3105 * @param pDevIns The device instance.
3106 * @thread Any thread.
3107 */
3108 DECLR3CALLBACKMEMBER(void, pfnDMASchedule,(PPDMDEVINS pDevIns));
3109
3110 /**
3111 * Write CMOS value and update the checksum(s).
3112 *
3113 * @returns VBox status code.
3114 * @param pDevIns The device instance.
3115 * @param iReg The CMOS register index.
3116 * @param u8Value The CMOS register value.
3117 * @thread EMT
3118 */
3119 DECLR3CALLBACKMEMBER(int, pfnCMOSWrite,(PPDMDEVINS pDevIns, unsigned iReg, uint8_t u8Value));
3120
3121 /**
3122 * Read CMOS value.
3123 *
3124 * @returns VBox status code.
3125 * @param pDevIns The device instance.
3126 * @param iReg The CMOS register index.
3127 * @param pu8Value Where to store the CMOS register value.
3128 * @thread EMT
3129 */
3130 DECLR3CALLBACKMEMBER(int, pfnCMOSRead,(PPDMDEVINS pDevIns, unsigned iReg, uint8_t *pu8Value));
3131
3132 /**
3133 * Assert that the current thread is the emulation thread.
3134 *
3135 * @returns True if correct.
3136 * @returns False if wrong.
3137 * @param pDevIns The device instance.
3138 * @param pszFile Filename of the assertion location.
3139 * @param iLine The linenumber of the assertion location.
3140 * @param pszFunction Function of the assertion location.
3141 */
3142 DECLR3CALLBACKMEMBER(bool, pfnAssertEMT,(PPDMDEVINS pDevIns, const char *pszFile, unsigned iLine, const char *pszFunction));
3143
3144 /**
3145 * Assert that the current thread is NOT the emulation thread.
3146 *
3147 * @returns True if correct.
3148 * @returns False if wrong.
3149 * @param pDevIns The device instance.
3150 * @param pszFile Filename of the assertion location.
3151 * @param iLine The linenumber of the assertion location.
3152 * @param pszFunction Function of the assertion location.
3153 */
3154 DECLR3CALLBACKMEMBER(bool, pfnAssertOther,(PPDMDEVINS pDevIns, const char *pszFile, unsigned iLine, const char *pszFunction));
3155
3156 /**
3157 * Resolves the symbol for a raw-mode context interface.
3158 *
3159 * @returns VBox status code.
3160 * @param pDevIns The device instance.
3161 * @param pvInterface The interface structure.
3162 * @param cbInterface The size of the interface structure.
3163 * @param pszSymPrefix What to prefix the symbols in the list with
3164 * before resolving them. This must start with
3165 * 'dev' and contain the driver name.
3166 * @param pszSymList List of symbols corresponding to the interface.
3167 * There is generally a there is generally a define
3168 * holding this list associated with the interface
3169 * definition (INTERFACE_SYM_LIST). For more
3170 * details see PDMR3LdrGetInterfaceSymbols.
3171 * @thread EMT
3172 */
3173 DECLR3CALLBACKMEMBER(int, pfnLdrGetRCInterfaceSymbols,(PPDMDEVINS pDevIns, void *pvInterface, size_t cbInterface,
3174 const char *pszSymPrefix, const char *pszSymList));
3175
3176 /**
3177 * Resolves the symbol for a ring-0 context interface.
3178 *
3179 * @returns VBox status code.
3180 * @param pDevIns The device instance.
3181 * @param pvInterface The interface structure.
3182 * @param cbInterface The size of the interface structure.
3183 * @param pszSymPrefix What to prefix the symbols in the list with
3184 * before resolving them. This must start with
3185 * 'dev' and contain the driver name.
3186 * @param pszSymList List of symbols corresponding to the interface.
3187 * There is generally a there is generally a define
3188 * holding this list associated with the interface
3189 * definition (INTERFACE_SYM_LIST). For more
3190 * details see PDMR3LdrGetInterfaceSymbols.
3191 * @thread EMT
3192 */
3193 DECLR3CALLBACKMEMBER(int, pfnLdrGetR0InterfaceSymbols,(PPDMDEVINS pDevIns, void *pvInterface, size_t cbInterface,
3194 const char *pszSymPrefix, const char *pszSymList));
3195
3196 /**
3197 * Call the ring-0 request handler routine of the device.
3198 *
3199 * For this to work, the device must be ring-0 enabled and export a request
3200 * handler function. The name of the function must be the device name in
3201 * the PDMDRVREG struct prefixed with 'drvR0' and suffixed with
3202 * 'ReqHandler'. The device name will be captialized. It shall take the
3203 * exact same arguments as this function and be declared using
3204 * PDMBOTHCBDECL. See FNPDMDEVREQHANDLERR0.
3205 *
3206 * Unlike PDMDrvHlpCallR0, this is current unsuitable for more than a call
3207 * or two as the handler address will be resolved on each invocation. This
3208 * is the reason for the EMT only restriction as well.
3209 *
3210 * @returns VBox status code.
3211 * @retval VERR_SYMBOL_NOT_FOUND if the device doesn't export the required
3212 * handler function.
3213 * @retval VERR_ACCESS_DENIED if the device isn't ring-0 capable.
3214 *
3215 * @param pDevIns The device instance.
3216 * @param uOperation The operation to perform.
3217 * @param u64Arg 64-bit integer argument.
3218 * @thread EMT
3219 */
3220 DECLR3CALLBACKMEMBER(int, pfnCallR0,(PPDMDEVINS pDevIns, uint32_t uOperation, uint64_t u64Arg));
3221
3222 /** Space reserved for future members.
3223 * @{ */
3224 DECLR3CALLBACKMEMBER(void, pfnReserved1,(void));
3225 DECLR3CALLBACKMEMBER(void, pfnReserved2,(void));
3226 DECLR3CALLBACKMEMBER(void, pfnReserved3,(void));
3227 DECLR3CALLBACKMEMBER(void, pfnReserved4,(void));
3228 DECLR3CALLBACKMEMBER(void, pfnReserved5,(void));
3229 DECLR3CALLBACKMEMBER(void, pfnReserved6,(void));
3230 DECLR3CALLBACKMEMBER(void, pfnReserved7,(void));
3231 DECLR3CALLBACKMEMBER(void, pfnReserved8,(void));
3232 DECLR3CALLBACKMEMBER(void, pfnReserved9,(void));
3233 DECLR3CALLBACKMEMBER(void, pfnReserved10,(void));
3234 /** @} */
3235
3236
3237 /** API available to trusted devices only.
3238 *
3239 * These APIs are providing unrestricted access to the guest and the VM,
3240 * or they are interacting intimately with PDM.
3241 *
3242 * @{
3243 */
3244 /**
3245 * Gets the VM handle. Restricted API.
3246 *
3247 * @returns VM Handle.
3248 * @param pDevIns The device instance.
3249 */
3250 DECLR3CALLBACKMEMBER(PVM, pfnGetVM,(PPDMDEVINS pDevIns));
3251
3252 /**
3253 * Gets the VMCPU handle. Restricted API.
3254 *
3255 * @returns VMCPU Handle.
3256 * @param pDevIns The device instance.
3257 */
3258 DECLR3CALLBACKMEMBER(PVMCPU, pfnGetVMCPU,(PPDMDEVINS pDevIns));
3259
3260 /**
3261 * Registers the VMM device heap
3262 *
3263 * @returns VBox status code.
3264 * @param pDevIns The device instance.
3265 * @param GCPhys The physical address.
3266 * @param pvHeap Ring 3 heap pointer.
3267 * @param cbSize Size of the heap.
3268 * @thread EMT.
3269 */
3270 DECLR3CALLBACKMEMBER(int, pfnRegisterVMMDevHeap,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, RTR3PTR pvHeap, unsigned cbSize));
3271
3272 /**
3273 * Unregisters the VMM device heap
3274 *
3275 * @returns VBox status code.
3276 * @param pDevIns The device instance.
3277 * @param GCPhys The physical address.
3278 * @thread EMT.
3279 */
3280 DECLR3CALLBACKMEMBER(int, pfnUnregisterVMMDevHeap,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys));
3281
3282 /**
3283 * Resets the VM.
3284 *
3285 * @returns The appropriate VBox status code to pass around on reset.
3286 * @param pDevIns The device instance.
3287 * @thread The emulation thread.
3288 */
3289 DECLR3CALLBACKMEMBER(int, pfnVMReset,(PPDMDEVINS pDevIns));
3290
3291 /**
3292 * Suspends the VM.
3293 *
3294 * @returns The appropriate VBox status code to pass around on suspend.
3295 * @param pDevIns The device instance.
3296 * @thread The emulation thread.
3297 */
3298 DECLR3CALLBACKMEMBER(int, pfnVMSuspend,(PPDMDEVINS pDevIns));
3299
3300 /**
3301 * Suspends, saves and powers off the VM.
3302 *
3303 * @returns The appropriate VBox status code to pass around.
3304 * @param pDevIns The device instance.
3305 * @thread An emulation thread.
3306 */
3307 DECLR3CALLBACKMEMBER(int, pfnVMSuspendSaveAndPowerOff,(PPDMDEVINS pDevIns));
3308
3309 /**
3310 * Power off the VM.
3311 *
3312 * @returns The appropriate VBox status code to pass around on power off.
3313 * @param pDevIns The device instance.
3314 * @thread The emulation thread.
3315 */
3316 DECLR3CALLBACKMEMBER(int, pfnVMPowerOff,(PPDMDEVINS pDevIns));
3317
3318 /**
3319 * Checks if the Gate A20 is enabled or not.
3320 *
3321 * @returns true if A20 is enabled.
3322 * @returns false if A20 is disabled.
3323 * @param pDevIns The device instance.
3324 * @thread The emulation thread.
3325 */
3326 DECLR3CALLBACKMEMBER(bool, pfnA20IsEnabled,(PPDMDEVINS pDevIns));
3327
3328 /**
3329 * Enables or disables the Gate A20.
3330 *
3331 * @param pDevIns The device instance.
3332 * @param fEnable Set this flag to enable the Gate A20; clear it
3333 * to disable.
3334 * @thread The emulation thread.
3335 */
3336 DECLR3CALLBACKMEMBER(void, pfnA20Set,(PPDMDEVINS pDevIns, bool fEnable));
3337
3338 /**
3339 * Get the specified CPUID leaf for the virtual CPU associated with the calling
3340 * thread.
3341 *
3342 * @param pDevIns The device instance.
3343 * @param iLeaf The CPUID leaf to get.
3344 * @param pEax Where to store the EAX value.
3345 * @param pEbx Where to store the EBX value.
3346 * @param pEcx Where to store the ECX value.
3347 * @param pEdx Where to store the EDX value.
3348 * @thread EMT.
3349 */
3350 DECLR3CALLBACKMEMBER(void, pfnGetCpuId,(PPDMDEVINS pDevIns, uint32_t iLeaf, uint32_t *pEax, uint32_t *pEbx, uint32_t *pEcx, uint32_t *pEdx));
3351
3352 /**
3353 * Get the current virtual clock time in a VM. The clock frequency must be
3354 * queried separately.
3355 *
3356 * @returns Current clock time.
3357 * @param pDevIns The device instance.
3358 */
3359 DECLR3CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGet,(PPDMDEVINS pDevIns));
3360
3361 /**
3362 * Get the frequency of the virtual clock.
3363 *
3364 * @returns The clock frequency (not variable at run-time).
3365 * @param pDevIns The device instance.
3366 */
3367 DECLR3CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetFreq,(PPDMDEVINS pDevIns));
3368
3369 /**
3370 * Get the current virtual clock time in a VM, in nanoseconds.
3371 *
3372 * @returns Current clock time (in ns).
3373 * @param pDevIns The device instance.
3374 */
3375 DECLR3CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetNano,(PPDMDEVINS pDevIns));
3376
3377 /** @} */
3378
3379 /** Just a safety precaution. (PDM_DEVHLP_VERSION) */
3380 uint32_t u32TheEnd;
3381} PDMDEVHLPR3;
3382#endif /* !IN_RING3 */
3383/** Pointer to the R3 PDM Device API. */
3384typedef R3PTRTYPE(struct PDMDEVHLPR3 *) PPDMDEVHLPR3;
3385/** Pointer to the R3 PDM Device API, const variant. */
3386typedef R3PTRTYPE(const struct PDMDEVHLPR3 *) PCPDMDEVHLPR3;
3387
3388/** Current PDMDEVHLPR3 version number. */
3389#define PDM_DEVHLPR3_VERSION PDM_VERSION_MAKE(0xffe7, 4, 0)
3390
3391
3392/**
3393 * PDM Device API - RC Variant.
3394 */
3395typedef struct PDMDEVHLPRC
3396{
3397 /** Structure version. PDM_DEVHLPRC_VERSION defines the current version. */
3398 uint32_t u32Version;
3399
3400 /**
3401 * Set the IRQ for a PCI device.
3402 *
3403 * @param pDevIns Device instance.
3404 * @param iIrq IRQ number to set.
3405 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
3406 * @thread Any thread, but will involve the emulation thread.
3407 */
3408 DECLRCCALLBACKMEMBER(void, pfnPCISetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
3409
3410 /**
3411 * Set ISA IRQ for a device.
3412 *
3413 * @param pDevIns Device instance.
3414 * @param iIrq IRQ number to set.
3415 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
3416 * @thread Any thread, but will involve the emulation thread.
3417 */
3418 DECLRCCALLBACKMEMBER(void, pfnISASetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
3419
3420 /**
3421 * Read physical memory.
3422 *
3423 * @returns VINF_SUCCESS (for now).
3424 * @param pDevIns Device instance.
3425 * @param GCPhys Physical address start reading from.
3426 * @param pvBuf Where to put the read bits.
3427 * @param cbRead How many bytes to read.
3428 */
3429 DECLRCCALLBACKMEMBER(int, pfnPhysRead,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, void *pvBuf, size_t cbRead));
3430
3431 /**
3432 * Write to physical memory.
3433 *
3434 * @returns VINF_SUCCESS for now, and later maybe VERR_EM_MEMORY.
3435 * @param pDevIns Device instance.
3436 * @param GCPhys Physical address to write to.
3437 * @param pvBuf What to write.
3438 * @param cbWrite How many bytes to write.
3439 */
3440 DECLRCCALLBACKMEMBER(int, pfnPhysWrite,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, const void *pvBuf, size_t cbWrite));
3441
3442 /**
3443 * Checks if the Gate A20 is enabled or not.
3444 *
3445 * @returns true if A20 is enabled.
3446 * @returns false if A20 is disabled.
3447 * @param pDevIns Device instance.
3448 * @thread The emulation thread.
3449 */
3450 DECLRCCALLBACKMEMBER(bool, pfnA20IsEnabled,(PPDMDEVINS pDevIns));
3451
3452 /**
3453 * Gets the VM state.
3454 *
3455 * @returns VM state.
3456 * @param pDevIns The device instance.
3457 * @thread Any thread (just keep in mind that it's volatile info).
3458 */
3459 DECLRCCALLBACKMEMBER(VMSTATE, pfnVMState, (PPDMDEVINS pDevIns));
3460
3461 /**
3462 * Set the VM error message
3463 *
3464 * @returns rc.
3465 * @param pDrvIns Driver instance.
3466 * @param rc VBox status code.
3467 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
3468 * @param pszFormat Error message format string.
3469 * @param ... Error message arguments.
3470 */
3471 DECLRCCALLBACKMEMBER(int, pfnVMSetError,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, ...));
3472
3473 /**
3474 * Set the VM error message
3475 *
3476 * @returns rc.
3477 * @param pDrvIns Driver instance.
3478 * @param rc VBox status code.
3479 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
3480 * @param pszFormat Error message format string.
3481 * @param va Error message arguments.
3482 */
3483 DECLRCCALLBACKMEMBER(int, pfnVMSetErrorV,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, va_list va));
3484
3485 /**
3486 * Set the VM runtime error message
3487 *
3488 * @returns VBox status code.
3489 * @param pDevIns Device instance.
3490 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
3491 * @param pszErrorId Error ID string.
3492 * @param pszFormat Error message format string.
3493 * @param ... Error message arguments.
3494 */
3495 DECLRCCALLBACKMEMBER(int, pfnVMSetRuntimeError,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, ...));
3496
3497 /**
3498 * Set the VM runtime error message
3499 *
3500 * @returns VBox status code.
3501 * @param pDevIns Device instance.
3502 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
3503 * @param pszErrorId Error ID string.
3504 * @param pszFormat Error message format string.
3505 * @param va Error message arguments.
3506 */
3507 DECLRCCALLBACKMEMBER(int, pfnVMSetRuntimeErrorV,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, va_list va));
3508
3509 /**
3510 * Set parameters for pending MMIO patch operation
3511 *
3512 * @returns VBox status code.
3513 * @param pDevIns Device instance.
3514 * @param GCPhys MMIO physical address
3515 * @param pCachedData GC pointer to cached data
3516 */
3517 DECLRCCALLBACKMEMBER(int, pfnPATMSetMMIOPatchInfo,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, RTGCPTR pCachedData));
3518
3519 /**
3520 * Gets the VM handle. Restricted API.
3521 *
3522 * @returns VM Handle.
3523 * @param pDevIns Device instance.
3524 */
3525 DECLRCCALLBACKMEMBER(PVM, pfnGetVM,(PPDMDEVINS pDevIns));
3526
3527 /**
3528 * Gets the VMCPU handle. Restricted API.
3529 *
3530 * @returns VMCPU Handle.
3531 * @param pDevIns The device instance.
3532 */
3533 DECLRCCALLBACKMEMBER(PVMCPU, pfnGetVMCPU,(PPDMDEVINS pDevIns));
3534
3535 /**
3536 * Get the current virtual clock time in a VM. The clock frequency must be
3537 * queried separately.
3538 *
3539 * @returns Current clock time.
3540 * @param pDevIns The device instance.
3541 */
3542 DECLRCCALLBACKMEMBER(uint64_t, pfnTMTimeVirtGet,(PPDMDEVINS pDevIns));
3543
3544 /**
3545 * Get the frequency of the virtual clock.
3546 *
3547 * @returns The clock frequency (not variable at run-time).
3548 * @param pDevIns The device instance.
3549 */
3550 DECLRCCALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetFreq,(PPDMDEVINS pDevIns));
3551
3552 /**
3553 * Get the current virtual clock time in a VM, in nanoseconds.
3554 *
3555 * @returns Current clock time (in ns).
3556 * @param pDevIns The device instance.
3557 */
3558 DECLRCCALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetNano,(PPDMDEVINS pDevIns));
3559
3560 /** Just a safety precaution. */
3561 uint32_t u32TheEnd;
3562} PDMDEVHLPRC;
3563/** Pointer PDM Device RC API. */
3564typedef RCPTRTYPE(struct PDMDEVHLPRC *) PPDMDEVHLPRC;
3565/** Pointer PDM Device RC API. */
3566typedef RCPTRTYPE(const struct PDMDEVHLPRC *) PCPDMDEVHLPRC;
3567
3568/** Current PDMDEVHLP version number. */
3569#define PDM_DEVHLPRC_VERSION PDM_VERSION_MAKE(0xffe6, 1, 0)
3570
3571
3572/**
3573 * PDM Device API - R0 Variant.
3574 */
3575typedef struct PDMDEVHLPR0
3576{
3577 /** Structure version. PDM_DEVHLPR0_VERSION defines the current version. */
3578 uint32_t u32Version;
3579
3580 /**
3581 * Set the IRQ for a PCI device.
3582 *
3583 * @param pDevIns Device instance.
3584 * @param iIrq IRQ number to set.
3585 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
3586 * @thread Any thread, but will involve the emulation thread.
3587 */
3588 DECLR0CALLBACKMEMBER(void, pfnPCISetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
3589
3590 /**
3591 * Set ISA IRQ for a device.
3592 *
3593 * @param pDevIns Device instance.
3594 * @param iIrq IRQ number to set.
3595 * @param iLevel IRQ level. See the PDM_IRQ_LEVEL_* \#defines.
3596 * @thread Any thread, but will involve the emulation thread.
3597 */
3598 DECLR0CALLBACKMEMBER(void, pfnISASetIrq,(PPDMDEVINS pDevIns, int iIrq, int iLevel));
3599
3600 /**
3601 * Read physical memory.
3602 *
3603 * @returns VINF_SUCCESS (for now).
3604 * @param pDevIns Device instance.
3605 * @param GCPhys Physical address start reading from.
3606 * @param pvBuf Where to put the read bits.
3607 * @param cbRead How many bytes to read.
3608 */
3609 DECLR0CALLBACKMEMBER(int, pfnPhysRead,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, void *pvBuf, size_t cbRead));
3610
3611 /**
3612 * Write to physical memory.
3613 *
3614 * @returns VINF_SUCCESS for now, and later maybe VERR_EM_MEMORY.
3615 * @param pDevIns Device instance.
3616 * @param GCPhys Physical address to write to.
3617 * @param pvBuf What to write.
3618 * @param cbWrite How many bytes to write.
3619 */
3620 DECLR0CALLBACKMEMBER(int, pfnPhysWrite,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, const void *pvBuf, size_t cbWrite));
3621
3622 /**
3623 * Checks if the Gate A20 is enabled or not.
3624 *
3625 * @returns true if A20 is enabled.
3626 * @returns false if A20 is disabled.
3627 * @param pDevIns Device instance.
3628 * @thread The emulation thread.
3629 */
3630 DECLR0CALLBACKMEMBER(bool, pfnA20IsEnabled,(PPDMDEVINS pDevIns));
3631
3632 /**
3633 * Gets the VM state.
3634 *
3635 * @returns VM state.
3636 * @param pDevIns The device instance.
3637 * @thread Any thread (just keep in mind that it's volatile info).
3638 */
3639 DECLR0CALLBACKMEMBER(VMSTATE, pfnVMState, (PPDMDEVINS pDevIns));
3640
3641 /**
3642 * Set the VM error message
3643 *
3644 * @returns rc.
3645 * @param pDrvIns Driver instance.
3646 * @param rc VBox status code.
3647 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
3648 * @param pszFormat Error message format string.
3649 * @param ... Error message arguments.
3650 */
3651 DECLR0CALLBACKMEMBER(int, pfnVMSetError,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, ...));
3652
3653 /**
3654 * Set the VM error message
3655 *
3656 * @returns rc.
3657 * @param pDrvIns Driver instance.
3658 * @param rc VBox status code.
3659 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
3660 * @param pszFormat Error message format string.
3661 * @param va Error message arguments.
3662 */
3663 DECLR0CALLBACKMEMBER(int, pfnVMSetErrorV,(PPDMDEVINS pDevIns, int rc, RT_SRC_POS_DECL, const char *pszFormat, va_list va));
3664
3665 /**
3666 * Set the VM runtime error message
3667 *
3668 * @returns VBox status code.
3669 * @param pDevIns Device instance.
3670 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
3671 * @param pszErrorId Error ID string.
3672 * @param pszFormat Error message format string.
3673 * @param ... Error message arguments.
3674 */
3675 DECLR0CALLBACKMEMBER(int, pfnVMSetRuntimeError,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, ...));
3676
3677 /**
3678 * Set the VM runtime error message
3679 *
3680 * @returns VBox status code.
3681 * @param pDevIns Device instance.
3682 * @param fFlags The action flags. See VMSETRTERR_FLAGS_*.
3683 * @param pszErrorId Error ID string.
3684 * @param pszFormat Error message format string.
3685 * @param va Error message arguments.
3686 */
3687 DECLR0CALLBACKMEMBER(int, pfnVMSetRuntimeErrorV,(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, va_list va));
3688
3689 /**
3690 * Set parameters for pending MMIO patch operation
3691 *
3692 * @returns rc.
3693 * @param pDevIns Device instance.
3694 * @param GCPhys MMIO physical address
3695 * @param pCachedData GC pointer to cached data
3696 */
3697 DECLR0CALLBACKMEMBER(int, pfnPATMSetMMIOPatchInfo,(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, RTGCPTR pCachedData));
3698
3699 /**
3700 * Gets the VM handle. Restricted API.
3701 *
3702 * @returns VM Handle.
3703 * @param pDevIns Device instance.
3704 */
3705 DECLR0CALLBACKMEMBER(PVM, pfnGetVM,(PPDMDEVINS pDevIns));
3706
3707 /**
3708 * Checks if our current CPU state allows for IO block emulation fallback to the recompiler
3709 *
3710 * @returns true = yes, false = no
3711 * @param pDevIns Device instance.
3712 */
3713 DECLR0CALLBACKMEMBER(bool, pfnCanEmulateIoBlock,(PPDMDEVINS pDevIns));
3714
3715 /**
3716 * Gets the VMCPU handle. Restricted API.
3717 *
3718 * @returns VMCPU Handle.
3719 * @param pDevIns The device instance.
3720 */
3721 DECLR0CALLBACKMEMBER(PVMCPU, pfnGetVMCPU,(PPDMDEVINS pDevIns));
3722
3723 /**
3724 * Get the current virtual clock time in a VM. The clock frequency must be
3725 * queried separately.
3726 *
3727 * @returns Current clock time.
3728 * @param pDevIns The device instance.
3729 */
3730 DECLR0CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGet,(PPDMDEVINS pDevIns));
3731
3732 /**
3733 * Get the frequency of the virtual clock.
3734 *
3735 * @returns The clock frequency (not variable at run-time).
3736 * @param pDevIns The device instance.
3737 */
3738 DECLR0CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetFreq,(PPDMDEVINS pDevIns));
3739
3740 /**
3741 * Get the current virtual clock time in a VM, in nanoseconds.
3742 *
3743 * @returns Current clock time (in ns).
3744 * @param pDevIns The device instance.
3745 */
3746 DECLR0CALLBACKMEMBER(uint64_t, pfnTMTimeVirtGetNano,(PPDMDEVINS pDevIns));
3747
3748 /** Just a safety precaution. */
3749 uint32_t u32TheEnd;
3750} PDMDEVHLPR0;
3751/** Pointer PDM Device R0 API. */
3752typedef R0PTRTYPE(struct PDMDEVHLPR0 *) PPDMDEVHLPR0;
3753/** Pointer PDM Device GC API. */
3754typedef R0PTRTYPE(const struct PDMDEVHLPR0 *) PCPDMDEVHLPR0;
3755
3756/** Current PDMDEVHLP version number. */
3757#define PDM_DEVHLPR0_VERSION PDM_VERSION_MAKE(0xffe5, 1, 0)
3758
3759
3760
3761/**
3762 * PDM Device Instance.
3763 */
3764typedef struct PDMDEVINS
3765{
3766 /** Structure version. PDM_DEVINS_VERSION defines the current version. */
3767 uint32_t u32Version;
3768 /** Device instance number. */
3769 uint32_t iInstance;
3770
3771 /** Pointer the GC PDM Device API. */
3772 PCPDMDEVHLPRC pHlpRC;
3773 /** Pointer to device instance data. */
3774 RTRCPTR pvInstanceDataRC;
3775 /** The critical section for the device, see pCritSectR3.
3776 * This is automatically resolved by PDM when pCritSectR3 is set by the
3777 * constructor. */
3778 RCPTRTYPE(PPDMCRITSECT) pCritSectRC;
3779 /** Alignment padding. */
3780 RTRCPTR pAlignmentRC;
3781
3782 /** Pointer the R0 PDM Device API. */
3783 PCPDMDEVHLPR0 pHlpR0;
3784 /** Pointer to device instance data (R0). */
3785 RTR0PTR pvInstanceDataR0;
3786 /** The critical section for the device, see pCritSectR3.
3787 * This is automatically resolved by PDM when pCritSectR3 is set by the
3788 * constructor. */
3789 R0PTRTYPE(PPDMCRITSECT) pCritSectR0;
3790
3791 /** Pointer the HC PDM Device API. */
3792 PCPDMDEVHLPR3 pHlpR3;
3793 /** Pointer to device instance data. */
3794 RTR3PTR pvInstanceDataR3;
3795 /** The critical section for the device. (Optional)
3796 *
3797 * The device constructor initializes this if it has a critical section for
3798 * the device and desires it to be taken automatically by MMIO, I/O port
3799 * and timer callbacks to the device. The advantages using this locking
3800 * approach is both less code and avoiding the global IOM lock.
3801 *
3802 * @remarks Will not yet be taken by SSM.
3803 */
3804 R3PTRTYPE(PPDMCRITSECT) pCritSectR3;
3805
3806 /** Pointer to device registration structure. */
3807 R3PTRTYPE(PCPDMDEVREG) pReg;
3808 /** Configuration handle. */
3809 R3PTRTYPE(PCFGMNODE) pCfg;
3810
3811 /** The base interface of the device.
3812 *
3813 * The device constructor initializes this if it has any
3814 * device level interfaces to export. To obtain this interface
3815 * call PDMR3QueryDevice(). */
3816 PDMIBASE IBase;
3817 /** Align the internal data more naturally. */
3818 RTR3PTR R3PtrPadding;
3819
3820 /** Internal data. */
3821 union
3822 {
3823#ifdef PDMDEVINSINT_DECLARED
3824 PDMDEVINSINT s;
3825#endif
3826 uint8_t padding[HC_ARCH_BITS == 32 ? 64 + 0 : 112 + 0x28];
3827 } Internal;
3828
3829 /** Device instance data. The size of this area is defined
3830 * in the PDMDEVREG::cbInstanceData field. */
3831 char achInstanceData[8];
3832} PDMDEVINS;
3833
3834/** Current PDMDEVINS version number. */
3835#define PDM_DEVINS_VERSION PDM_VERSION_MAKE(0xffe4, 2, 0)
3836
3837/** Converts a pointer to the PDMDEVINS::IBase to a pointer to PDMDEVINS. */
3838#define PDMIBASE_2_PDMDEV(pInterface) ( (PPDMDEVINS)((char *)(pInterface) - RT_OFFSETOF(PDMDEVINS, IBase)) )
3839
3840/**
3841 * Checks the structure versions of the device instance and device helpers,
3842 * returning if they are incompatible.
3843 *
3844 * This is for use in the constructor.
3845 *
3846 * @param pDevIns The device instance pointer.
3847 */
3848#define PDMDEV_CHECK_VERSIONS_RETURN(pDevIns) \
3849 do \
3850 { \
3851 PPDMDEVINS pDevInsTypeCheck = (pDevIns); NOREF(pDevInsTypeCheck); \
3852 AssertLogRelMsgReturn(PDM_VERSION_ARE_COMPATIBLE((pDevIns)->u32Version, PDM_DEVINS_VERSION), \
3853 ("DevIns=%#x mine=%#x\n", (pDevIns)->u32Version, PDM_DEVINS_VERSION), \
3854 VERR_PDM_DEVINS_VERSION_MISMATCH); \
3855 AssertLogRelMsgReturn(PDM_VERSION_ARE_COMPATIBLE((pDevIns)->pHlpR3->u32Version, PDM_DEVHLPR3_VERSION), \
3856 ("DevHlp=%#x mine=%#x\n", (pDevIns)->pHlpR3->u32Version, PDM_DEVHLPR3_VERSION), \
3857 VERR_PDM_DEVHLPR3_VERSION_MISMATCH); \
3858 } while (0)
3859
3860/**
3861 * Quietly checks the structure versions of the device instance and device
3862 * helpers, returning if they are incompatible.
3863 *
3864 * This is for use in the destructor.
3865 *
3866 * @param pDevIns The device instance pointer.
3867 */
3868#define PDMDEV_CHECK_VERSIONS_RETURN_QUIET(pDevIns) \
3869 do \
3870 { \
3871 PPDMDEVINS pDevInsTypeCheck = (pDevIns); NOREF(pDevInsTypeCheck); \
3872 if (RT_UNLIKELY(!PDM_VERSION_ARE_COMPATIBLE((pDevIns)->u32Version, PDM_DEVINS_VERSION) )) \
3873 return VERR_PDM_DEVINS_VERSION_MISMATCH; \
3874 if (RT_UNLIKELY(!PDM_VERSION_ARE_COMPATIBLE((pDevIns)->pHlpR3->u32Version, PDM_DEVHLPR3_VERSION) )) \
3875 return VERR_PDM_DEVHLPR3_VERSION_MISMATCH; \
3876 } while (0)
3877
3878/**
3879 * Wrapper around CFGMR3ValidateConfig for the root config for use in the
3880 * constructor - returns on failure.
3881 *
3882 * This should be invoked after having initialized the instance data
3883 * sufficiently for the correct operation of the destructor. The destructor is
3884 * always called!
3885 *
3886 * @param pDevIns Pointer to the PDM device instance.
3887 * @param pszValidValues Patterns describing the valid value names. See
3888 * RTStrSimplePatternMultiMatch for details on the
3889 * pattern syntax.
3890 * @param pszValidNodes Patterns describing the valid node (key) names.
3891 * Pass empty string if no valid nodess.
3892 */
3893#define PDMDEV_VALIDATE_CONFIG_RETURN(pDevIns, pszValidValues, pszValidNodes) \
3894 do \
3895 { \
3896 int rcValCfg = CFGMR3ValidateConfig((pDevIns)->pCfg, "/", pszValidValues, pszValidNodes, \
3897 (pDevIns)->pReg->szName, (pDevIns)->iInstance); \
3898 if (RT_FAILURE(rcValCfg)) \
3899 return rcValCfg; \
3900 } while (0)
3901
3902/** @def PDMDEV_ASSERT_EMT
3903 * Assert that the current thread is the emulation thread.
3904 */
3905#ifdef VBOX_STRICT
3906# define PDMDEV_ASSERT_EMT(pDevIns) pDevIns->pHlpR3->pfnAssertEMT(pDevIns, __FILE__, __LINE__, __FUNCTION__)
3907#else
3908# define PDMDEV_ASSERT_EMT(pDevIns) do { } while (0)
3909#endif
3910
3911/** @def PDMDEV_ASSERT_OTHER
3912 * Assert that the current thread is NOT the emulation thread.
3913 */
3914#ifdef VBOX_STRICT
3915# define PDMDEV_ASSERT_OTHER(pDevIns) pDevIns->pHlpR3->pfnAssertOther(pDevIns, __FILE__, __LINE__, __FUNCTION__)
3916#else
3917# define PDMDEV_ASSERT_OTHER(pDevIns) do { } while (0)
3918#endif
3919
3920/** @def PDMDEV_ASSERT_VMLOCK_OWNER
3921 * Assert that the current thread is owner of the VM lock.
3922 */
3923#ifdef VBOX_STRICT
3924# define PDMDEV_ASSERT_VMLOCK_OWNER(pDevIns) pDevIns->pHlpR3->pfnAssertVMLock(pDevIns, __FILE__, __LINE__, __FUNCTION__)
3925#else
3926# define PDMDEV_ASSERT_VMLOCK_OWNER(pDevIns) do { } while (0)
3927#endif
3928
3929/** @def PDMDEV_SET_ERROR
3930 * Set the VM error. See PDMDevHlpVMSetError() for printf like message formatting.
3931 */
3932#define PDMDEV_SET_ERROR(pDevIns, rc, pszError) \
3933 PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS, "%s", pszError)
3934
3935/** @def PDMDEV_SET_RUNTIME_ERROR
3936 * Set the VM runtime error. See PDMDevHlpVMSetRuntimeError() for printf like message formatting.
3937 */
3938#define PDMDEV_SET_RUNTIME_ERROR(pDevIns, fFlags, pszErrorId, pszError) \
3939 PDMDevHlpVMSetRuntimeError(pDevIns, fFlags, pszErrorId, "%s", pszError)
3940
3941/** @def PDMDEVINS_2_RCPTR
3942 * Converts a PDM Device instance pointer a RC PDM Device instance pointer.
3943 */
3944#define PDMDEVINS_2_RCPTR(pDevIns) ( (RCPTRTYPE(PPDMDEVINS))((RTGCUINTPTR)(pDevIns)->pvInstanceDataRC - RT_OFFSETOF(PDMDEVINS, achInstanceData)) )
3945
3946/** @def PDMDEVINS_2_R3PTR
3947 * Converts a PDM Device instance pointer a R3 PDM Device instance pointer.
3948 */
3949#define PDMDEVINS_2_R3PTR(pDevIns) ( (R3PTRTYPE(PPDMDEVINS))((RTHCUINTPTR)(pDevIns)->pvInstanceDataR3 - RT_OFFSETOF(PDMDEVINS, achInstanceData)) )
3950
3951/** @def PDMDEVINS_2_R0PTR
3952 * Converts a PDM Device instance pointer a R0 PDM Device instance pointer.
3953 */
3954#define PDMDEVINS_2_R0PTR(pDevIns) ( (R0PTRTYPE(PPDMDEVINS))((RTR0UINTPTR)(pDevIns)->pvInstanceDataR0 - RT_OFFSETOF(PDMDEVINS, achInstanceData)) )
3955
3956
3957#ifdef IN_RING3
3958
3959/**
3960 * @copydoc PDMDEVHLPR3::pfnIOPortRegister
3961 */
3962DECLINLINE(int) PDMDevHlpIOPortRegister(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTHCPTR pvUser,
3963 PFNIOMIOPORTOUT pfnOut, PFNIOMIOPORTIN pfnIn,
3964 PFNIOMIOPORTOUTSTRING pfnOutStr, PFNIOMIOPORTINSTRING pfnInStr, const char *pszDesc)
3965{
3966 return pDevIns->pHlpR3->pfnIOPortRegister(pDevIns, Port, cPorts, pvUser, pfnOut, pfnIn, pfnOutStr, pfnInStr, pszDesc);
3967}
3968
3969/**
3970 * @copydoc PDMDEVHLPR3::pfnIOPortRegisterRC
3971 */
3972DECLINLINE(int) PDMDevHlpIOPortRegisterRC(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTRCPTR pvUser,
3973 const char *pszOut, const char *pszIn, const char *pszOutStr,
3974 const char *pszInStr, const char *pszDesc)
3975{
3976 return pDevIns->pHlpR3->pfnIOPortRegisterRC(pDevIns, Port, cPorts, pvUser, pszOut, pszIn, pszOutStr, pszInStr, pszDesc);
3977}
3978
3979/**
3980 * @copydoc PDMDEVHLPR3::pfnIOPortRegisterR0
3981 */
3982DECLINLINE(int) PDMDevHlpIOPortRegisterR0(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts, RTR0PTR pvUser,
3983 const char *pszOut, const char *pszIn, const char *pszOutStr,
3984 const char *pszInStr, const char *pszDesc)
3985{
3986 return pDevIns->pHlpR3->pfnIOPortRegisterR0(pDevIns, Port, cPorts, pvUser, pszOut, pszIn, pszOutStr, pszInStr, pszDesc);
3987}
3988
3989/**
3990 * @copydoc PDMDEVHLPR3::pfnIOPortDeregister
3991 */
3992DECLINLINE(int) PDMDevHlpIOPortDeregister(PPDMDEVINS pDevIns, RTIOPORT Port, RTUINT cPorts)
3993{
3994 return pDevIns->pHlpR3->pfnIOPortDeregister(pDevIns, Port, cPorts);
3995}
3996
3997/**
3998 * @copydoc PDMDEVHLPR3::pfnMMIORegister
3999 */
4000DECLINLINE(int) PDMDevHlpMMIORegister(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTHCPTR pvUser,
4001 PFNIOMMMIOWRITE pfnWrite, PFNIOMMMIOREAD pfnRead, PFNIOMMMIOFILL pfnFill,
4002 const char *pszDesc)
4003{
4004 return pDevIns->pHlpR3->pfnMMIORegister(pDevIns, GCPhysStart, cbRange, pvUser, pfnWrite, pfnRead, pfnFill, pszDesc);
4005}
4006
4007/**
4008 * @copydoc PDMDEVHLPR3::pfnMMIORegisterRC
4009 */
4010DECLINLINE(int) PDMDevHlpMMIORegisterRC(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTGCPTR pvUser,
4011 const char *pszWrite, const char *pszRead, const char *pszFill)
4012{
4013 return pDevIns->pHlpR3->pfnMMIORegisterRC(pDevIns, GCPhysStart, cbRange, pvUser, pszWrite, pszRead, pszFill, NULL);
4014}
4015
4016/**
4017 * @copydoc PDMDEVHLPR3::pfnMMIORegisterR0
4018 */
4019DECLINLINE(int) PDMDevHlpMMIORegisterR0(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, RTR0PTR pvUser,
4020 const char *pszWrite, const char *pszRead, const char *pszFill)
4021{
4022 return pDevIns->pHlpR3->pfnMMIORegisterR0(pDevIns, GCPhysStart, cbRange, pvUser, pszWrite, pszRead, pszFill, NULL);
4023}
4024
4025/**
4026 * @copydoc PDMDEVHLPR3::pfnMMIODeregister
4027 */
4028DECLINLINE(int) PDMDevHlpMMIODeregister(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange)
4029{
4030 return pDevIns->pHlpR3->pfnMMIODeregister(pDevIns, GCPhysStart, cbRange);
4031}
4032
4033/**
4034 * @copydoc PDMDEVHLPR3::pfnMMIO2Register
4035 */
4036DECLINLINE(int) PDMDevHlpMMIO2Register(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS cb, uint32_t fFlags, void **ppv, const char *pszDesc)
4037{
4038 return pDevIns->pHlpR3->pfnMMIO2Register(pDevIns, iRegion, cb, fFlags, ppv, pszDesc);
4039}
4040
4041/**
4042 * @copydoc PDMDEVHLPR3::pfnMMIO2Deregister
4043 */
4044DECLINLINE(int) PDMDevHlpMMIO2Deregister(PPDMDEVINS pDevIns, uint32_t iRegion)
4045{
4046 return pDevIns->pHlpR3->pfnMMIO2Deregister(pDevIns, iRegion);
4047}
4048
4049/**
4050 * @copydoc PDMDEVHLPR3::pfnMMIO2Map
4051 */
4052DECLINLINE(int) PDMDevHlpMMIO2Map(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS GCPhys)
4053{
4054 return pDevIns->pHlpR3->pfnMMIO2Map(pDevIns, iRegion, GCPhys);
4055}
4056
4057/**
4058 * @copydoc PDMDEVHLPR3::pfnMMIO2Unmap
4059 */
4060DECLINLINE(int) PDMDevHlpMMIO2Unmap(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS GCPhys)
4061{
4062 return pDevIns->pHlpR3->pfnMMIO2Unmap(pDevIns, iRegion, GCPhys);
4063}
4064
4065/**
4066 * @copydoc PDMDEVHLPR3::pfnMMHyperMapMMIO2
4067 */
4068DECLINLINE(int) PDMDevHlpMMHyperMapMMIO2(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS off, RTGCPHYS cb,
4069 const char *pszDesc, PRTRCPTR pRCPtr)
4070{
4071 return pDevIns->pHlpR3->pfnMMHyperMapMMIO2(pDevIns, iRegion, off, cb, pszDesc, pRCPtr);
4072}
4073
4074/**
4075 * @copydoc PDMDEVHLPR3::pfnMMIO2MapKernel
4076 */
4077DECLINLINE(int) PDMDevHlpMMIO2MapKernel(PPDMDEVINS pDevIns, uint32_t iRegion, RTGCPHYS off, RTGCPHYS cb,
4078 const char *pszDesc, PRTR0PTR pR0Ptr)
4079{
4080 return pDevIns->pHlpR3->pfnMMIO2MapKernel(pDevIns, iRegion, off, cb, pszDesc, pR0Ptr);
4081}
4082
4083/**
4084 * @copydoc PDMDEVHLPR3::pfnROMRegister
4085 */
4086DECLINLINE(int) PDMDevHlpROMRegister(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange,
4087 const void *pvBinary, uint32_t cbBinary, uint32_t fFlags, const char *pszDesc)
4088{
4089 return pDevIns->pHlpR3->pfnROMRegister(pDevIns, GCPhysStart, cbRange, pvBinary, cbBinary, fFlags, pszDesc);
4090}
4091
4092/**
4093 * @copydoc PDMDEVHLPR3::pfnROMProtectShadow
4094 */
4095DECLINLINE(int) PDMDevHlpROMProtectShadow(PPDMDEVINS pDevIns, RTGCPHYS GCPhysStart, RTUINT cbRange, PGMROMPROT enmProt)
4096{
4097 return pDevIns->pHlpR3->pfnROMProtectShadow(pDevIns, GCPhysStart, cbRange, enmProt);
4098}
4099
4100/**
4101 * Register a save state data unit.
4102 *
4103 * @returns VBox status.
4104 * @param pDevIns The device instance.
4105 * @param uVersion Data layout version number.
4106 * @param cbGuess The approximate amount of data in the unit.
4107 * Only for progress indicators.
4108 * @param pfnSaveExec Execute save callback, optional.
4109 * @param pfnLoadExec Execute load callback, optional.
4110 */
4111DECLINLINE(int) PDMDevHlpSSMRegister(PPDMDEVINS pDevIns, uint32_t uVersion, size_t cbGuess,
4112 PFNSSMDEVSAVEEXEC pfnSaveExec, PFNSSMDEVLOADEXEC pfnLoadExec)
4113{
4114 return pDevIns->pHlpR3->pfnSSMRegister(pDevIns, uVersion, cbGuess, NULL /*pszBefore*/,
4115 NULL /*pfnLivePrep*/, NULL /*pfnLiveExec*/, NULL /*pfnLiveDone*/,
4116 NULL /*pfnSavePrep*/, pfnSaveExec, NULL /*pfnSaveDone*/,
4117 NULL /*pfnLoadPrep*/, pfnLoadExec, NULL /*pfnLoadDone*/);
4118}
4119
4120/**
4121 * Register a save state data unit with a live save callback as well.
4122 *
4123 * @returns VBox status.
4124 * @param pDevIns The device instance.
4125 * @param uVersion Data layout version number.
4126 * @param cbGuess The approximate amount of data in the unit.
4127 * Only for progress indicators.
4128 * @param pfnLiveExec Execute live callback, optional.
4129 * @param pfnSaveExec Execute save callback, optional.
4130 * @param pfnLoadExec Execute load callback, optional.
4131 */
4132DECLINLINE(int) PDMDevHlpSSMRegister3(PPDMDEVINS pDevIns, uint32_t uVersion, size_t cbGuess,
4133 FNSSMDEVLIVEEXEC pfnLiveExec, PFNSSMDEVSAVEEXEC pfnSaveExec, PFNSSMDEVLOADEXEC pfnLoadExec)
4134{
4135 return pDevIns->pHlpR3->pfnSSMRegister(pDevIns, uVersion, cbGuess, NULL /*pszBefore*/,
4136 NULL /*pfnLivePrep*/, pfnLiveExec, NULL /*pfnLiveDone*/,
4137 NULL /*pfnSavePrep*/, pfnSaveExec, NULL /*pfnSaveDone*/,
4138 NULL /*pfnLoadPrep*/, pfnLoadExec, NULL /*pfnLoadDone*/);
4139}
4140
4141/**
4142 * @copydoc PDMDEVHLPR3::pfnSSMRegister
4143 */
4144DECLINLINE(int) PDMDevHlpSSMRegisterEx(PPDMDEVINS pDevIns, uint32_t uVersion, size_t cbGuess, const char *pszBefore,
4145 PFNSSMDEVLIVEPREP pfnLivePrep, PFNSSMDEVLIVEEXEC pfnLiveExec, PFNSSMDEVLIVEVOTE pfnLiveVote,
4146 PFNSSMDEVSAVEPREP pfnSavePrep, PFNSSMDEVSAVEEXEC pfnSaveExec, PFNSSMDEVSAVEDONE pfnSaveDone,
4147 PFNSSMDEVLOADPREP pfnLoadPrep, PFNSSMDEVLOADEXEC pfnLoadExec, PFNSSMDEVLOADDONE pfnLoadDone)
4148{
4149 return pDevIns->pHlpR3->pfnSSMRegister(pDevIns, uVersion, cbGuess, pszBefore,
4150 pfnLivePrep, pfnLiveExec, pfnLiveVote,
4151 pfnSavePrep, pfnSaveExec, pfnSaveDone,
4152 pfnLoadPrep, pfnLoadExec, pfnLoadDone);
4153}
4154
4155/**
4156 * @copydoc PDMDEVHLPR3::pfnTMTimerCreate
4157 */
4158DECLINLINE(int) PDMDevHlpTMTimerCreate(PPDMDEVINS pDevIns, TMCLOCK enmClock, PFNTMTIMERDEV pfnCallback, void *pvUser, uint32_t fFlags,
4159 const char *pszDesc, PPTMTIMERR3 ppTimer)
4160{
4161 return pDevIns->pHlpR3->pfnTMTimerCreate(pDevIns, enmClock, pfnCallback, pvUser, fFlags, pszDesc, ppTimer);
4162}
4163
4164/**
4165 * @copydoc PDMDEVHLPR3::pfnTMUtcNow
4166 */
4167DECLINLINE(PRTTIMESPEC) PDMDevHlpTMUtcNow(PPDMDEVINS pDevIns, PRTTIMESPEC pTime)
4168{
4169 return pDevIns->pHlpR3->pfnTMUtcNow(pDevIns, pTime);
4170}
4171
4172#endif /* IN_RING3 */
4173
4174/**
4175 * @copydoc PDMDEVHLPR3::pfnPhysRead
4176 */
4177DECLINLINE(int) PDMDevHlpPhysRead(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, void *pvBuf, size_t cbRead)
4178{
4179 return pDevIns->CTX_SUFF(pHlp)->pfnPhysRead(pDevIns, GCPhys, pvBuf, cbRead);
4180}
4181
4182/**
4183 * @copydoc PDMDEVHLPR3::pfnPhysWrite
4184 */
4185DECLINLINE(int) PDMDevHlpPhysWrite(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, const void *pvBuf, size_t cbWrite)
4186{
4187 return pDevIns->CTX_SUFF(pHlp)->pfnPhysWrite(pDevIns, GCPhys, pvBuf, cbWrite);
4188}
4189
4190#ifdef IN_RING3
4191
4192/**
4193 * @copydoc PDMDEVHLPR3::pfnPhysGCPhys2CCPtr
4194 */
4195DECLINLINE(int) PDMDevHlpPhysGCPhys2CCPtr(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, uint32_t fFlags, void **ppv, PPGMPAGEMAPLOCK pLock)
4196{
4197 return pDevIns->CTX_SUFF(pHlp)->pfnPhysGCPhys2CCPtr(pDevIns, GCPhys, fFlags, ppv, pLock);
4198}
4199
4200/**
4201 * @copydoc PDMDEVHLPR3::pfnPhysGCPhys2CCPtrReadOnly
4202 */
4203DECLINLINE(int) PDMDevHlpPhysGCPhys2CCPtrReadOnly(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, uint32_t fFlags, void const **ppv, PPGMPAGEMAPLOCK pLock)
4204{
4205 return pDevIns->CTX_SUFF(pHlp)->pfnPhysGCPhys2CCPtrReadOnly(pDevIns, GCPhys, fFlags, ppv, pLock);
4206}
4207
4208/**
4209 * @copydoc PDMDEVHLPR3::pfnPhysReleasePageMappingLock
4210 */
4211DECLINLINE(void) PDMDevHlpPhysReleasePageMappingLock(PPDMDEVINS pDevIns, PPGMPAGEMAPLOCK pLock)
4212{
4213 pDevIns->CTX_SUFF(pHlp)->pfnPhysReleasePageMappingLock(pDevIns, pLock);
4214}
4215
4216/**
4217 * @copydoc PDMDEVHLPR3::pfnPhysReadGCVirt
4218 */
4219DECLINLINE(int) PDMDevHlpPhysReadGCVirt(PPDMDEVINS pDevIns, void *pvDst, RTGCPTR GCVirtSrc, size_t cb)
4220{
4221 return pDevIns->pHlpR3->pfnPhysReadGCVirt(pDevIns, pvDst, GCVirtSrc, cb);
4222}
4223
4224/**
4225 * @copydoc PDMDEVHLPR3::pfnPhysWriteGCVirt
4226 */
4227DECLINLINE(int) PDMDevHlpPhysWriteGCVirt(PPDMDEVINS pDevIns, RTGCPTR GCVirtDst, const void *pvSrc, size_t cb)
4228{
4229 return pDevIns->pHlpR3->pfnPhysWriteGCVirt(pDevIns, GCVirtDst, pvSrc, cb);
4230}
4231
4232/**
4233 * @copydoc PDMDEVHLPR3::pfnPhysGCPtr2GCPhys
4234 */
4235DECLINLINE(int) PDMDevHlpPhysGCPtr2GCPhys(PPDMDEVINS pDevIns, RTGCPTR GCPtr, PRTGCPHYS pGCPhys)
4236{
4237 return pDevIns->pHlpR3->pfnPhysGCPtr2GCPhys(pDevIns, GCPtr, pGCPhys);
4238}
4239
4240/**
4241 * @copydoc PDMDEVHLPR3::pfnMMHeapAlloc
4242 */
4243DECLINLINE(void *) PDMDevHlpMMHeapAlloc(PPDMDEVINS pDevIns, size_t cb)
4244{
4245 return pDevIns->pHlpR3->pfnMMHeapAlloc(pDevIns, cb);
4246}
4247
4248/**
4249 * @copydoc PDMDEVHLPR3::pfnMMHeapAllocZ
4250 */
4251DECLINLINE(void *) PDMDevHlpMMHeapAllocZ(PPDMDEVINS pDevIns, size_t cb)
4252{
4253 return pDevIns->pHlpR3->pfnMMHeapAllocZ(pDevIns, cb);
4254}
4255
4256/**
4257 * @copydoc PDMDEVHLPR3::pfnMMHeapFree
4258 */
4259DECLINLINE(void) PDMDevHlpMMHeapFree(PPDMDEVINS pDevIns, void *pv)
4260{
4261 pDevIns->pHlpR3->pfnMMHeapFree(pDevIns, pv);
4262}
4263#endif /* IN_RING3 */
4264
4265/**
4266 * @copydoc PDMDEVHLPR3::pfnVMState
4267 */
4268DECLINLINE(VMSTATE) PDMDevHlpVMState(PPDMDEVINS pDevIns)
4269{
4270 return pDevIns->CTX_SUFF(pHlp)->pfnVMState(pDevIns);
4271}
4272
4273#ifdef IN_RING3
4274/**
4275 * @copydoc PDMDEVHLPR3::pfnVMTeleportedAndNotFullyResumedYet
4276 */
4277DECLINLINE(bool) PDMDevHlpVMTeleportedAndNotFullyResumedYet(PPDMDEVINS pDevIns)
4278{
4279 return pDevIns->pHlpR3->pfnVMTeleportedAndNotFullyResumedYet(pDevIns);
4280}
4281#endif /* IN_RING3 */
4282
4283/**
4284 * @copydoc PDMDEVHLPR3::pfnVMSetError
4285 */
4286DECLINLINE(int) PDMDevHlpVMSetError(PPDMDEVINS pDevIns, const int rc, RT_SRC_POS_DECL, const char *pszFormat, ...)
4287{
4288 va_list va;
4289 va_start(va, pszFormat);
4290 pDevIns->CTX_SUFF(pHlp)->pfnVMSetErrorV(pDevIns, rc, RT_SRC_POS_ARGS, pszFormat, va);
4291 va_end(va);
4292 return rc;
4293}
4294
4295/**
4296 * @copydoc PDMDEVHLPR3::pfnVMSetRuntimeError
4297 */
4298DECLINLINE(int) PDMDevHlpVMSetRuntimeError(PPDMDEVINS pDevIns, uint32_t fFlags, const char *pszErrorId, const char *pszFormat, ...)
4299{
4300 va_list va;
4301 int rc;
4302 va_start(va, pszFormat);
4303 rc = pDevIns->CTX_SUFF(pHlp)->pfnVMSetRuntimeErrorV(pDevIns, fFlags, pszErrorId, pszFormat, va);
4304 va_end(va);
4305 return rc;
4306}
4307
4308/**
4309 * VBOX_STRICT wrapper for pHlp->pfnDBGFStopV.
4310 *
4311 * @returns VBox status code which must be passed up to the VMM. This will be
4312 * VINF_SUCCESS in non-strict builds.
4313 * @param pDevIns The device instance.
4314 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
4315 * @param pszFormat Message. (optional)
4316 * @param ... Message parameters.
4317 */
4318DECLINLINE(int) PDMDevHlpDBGFStop(PPDMDEVINS pDevIns, RT_SRC_POS_DECL, const char *pszFormat, ...)
4319{
4320#ifdef VBOX_STRICT
4321# ifdef IN_RING3
4322 int rc;
4323 va_list args;
4324 va_start(args, pszFormat);
4325 rc = pDevIns->pHlpR3->pfnDBGFStopV(pDevIns, RT_SRC_POS_ARGS, pszFormat, args);
4326 va_end(args);
4327 return rc;
4328# else
4329 return VINF_EM_DBG_STOP;
4330# endif
4331#else
4332 NOREF(pDevIns);
4333 NOREF(pszFile);
4334 NOREF(iLine);
4335 NOREF(pszFunction);
4336 NOREF(pszFormat);
4337 return VINF_SUCCESS;
4338#endif
4339}
4340
4341#ifdef IN_RING3
4342
4343/**
4344 * @copydoc PDMDEVHLPR3::pfnDBGFInfoRegister
4345 */
4346DECLINLINE(int) PDMDevHlpDBGFInfoRegister(PPDMDEVINS pDevIns, const char *pszName, const char *pszDesc, PFNDBGFHANDLERDEV pfnHandler)
4347{
4348 return pDevIns->pHlpR3->pfnDBGFInfoRegister(pDevIns, pszName, pszDesc, pfnHandler);
4349}
4350
4351/**
4352 * @copydoc PDMDEVHLPR3::pfnSTAMRegister
4353 */
4354DECLINLINE(void) PDMDevHlpSTAMRegister(PPDMDEVINS pDevIns, void *pvSample, STAMTYPE enmType, const char *pszName, STAMUNIT enmUnit, const char *pszDesc)
4355{
4356 pDevIns->pHlpR3->pfnSTAMRegister(pDevIns, pvSample, enmType, pszName, enmUnit, pszDesc);
4357}
4358
4359/**
4360 * @copydoc PDMDEVHLPR3::pfnSTAMRegisterF
4361 */
4362DECLINLINE(void) PDMDevHlpSTAMRegisterF(PPDMDEVINS pDevIns, void *pvSample, STAMTYPE enmType, STAMVISIBILITY enmVisibility, STAMUNIT enmUnit,
4363 const char *pszDesc, const char *pszName, ...)
4364{
4365 va_list va;
4366 va_start(va, pszName);
4367 pDevIns->pHlpR3->pfnSTAMRegisterV(pDevIns, pvSample, enmType, enmVisibility, enmUnit, pszDesc, pszName, va);
4368 va_end(va);
4369}
4370
4371/**
4372 * @copydoc PDMDEVHLPR3::pfnPCIRegister
4373 */
4374DECLINLINE(int) PDMDevHlpPCIRegister(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev)
4375{
4376 return pDevIns->pHlpR3->pfnPCIRegister(pDevIns, pPciDev);
4377}
4378
4379/**
4380 * @copydoc PDMDEVHLPR3::pfnPCIIORegionRegister
4381 */
4382DECLINLINE(int) PDMDevHlpPCIIORegionRegister(PPDMDEVINS pDevIns, int iRegion, uint32_t cbRegion, PCIADDRESSSPACE enmType, PFNPCIIOREGIONMAP pfnCallback)
4383{
4384 return pDevIns->pHlpR3->pfnPCIIORegionRegister(pDevIns, iRegion, cbRegion, enmType, pfnCallback);
4385}
4386
4387/**
4388 * @copydoc PDMDEVHLPR3::pfnPCIRegisterMsi
4389 */
4390DECLINLINE(int) PDMDevHlpPCIRegisterMsi(PPDMDEVINS pDevIns, PPDMMSIREG pMsiReg)
4391{
4392 return pDevIns->pHlpR3->pfnPCIRegisterMsi(pDevIns, pMsiReg);
4393}
4394
4395
4396/**
4397 * @copydoc PDMDEVHLPR3::pfnPCISetConfigCallbacks
4398 */
4399DECLINLINE(void) PDMDevHlpPCISetConfigCallbacks(PPDMDEVINS pDevIns, PPCIDEVICE pPciDev, PFNPCICONFIGREAD pfnRead, PPFNPCICONFIGREAD ppfnReadOld,
4400 PFNPCICONFIGWRITE pfnWrite, PPFNPCICONFIGWRITE ppfnWriteOld)
4401{
4402 pDevIns->pHlpR3->pfnPCISetConfigCallbacks(pDevIns, pPciDev, pfnRead, ppfnReadOld, pfnWrite, ppfnWriteOld);
4403}
4404
4405#endif /* IN_RING3 */
4406
4407/**
4408 * @copydoc PDMDEVHLPR3::pfnPCISetIrq
4409 */
4410DECLINLINE(void) PDMDevHlpPCISetIrq(PPDMDEVINS pDevIns, int iIrq, int iLevel)
4411{
4412 pDevIns->CTX_SUFF(pHlp)->pfnPCISetIrq(pDevIns, iIrq, iLevel);
4413}
4414
4415/**
4416 * @copydoc PDMDEVHLPR3::pfnPCISetIrqNoWait
4417 */
4418DECLINLINE(void) PDMDevHlpPCISetIrqNoWait(PPDMDEVINS pDevIns, int iIrq, int iLevel)
4419{
4420 pDevIns->CTX_SUFF(pHlp)->pfnPCISetIrq(pDevIns, iIrq, iLevel);
4421}
4422
4423/**
4424 * @copydoc PDMDEVHLPR3::pfnISASetIrq
4425 */
4426DECLINLINE(void) PDMDevHlpISASetIrq(PPDMDEVINS pDevIns, int iIrq, int iLevel)
4427{
4428 pDevIns->CTX_SUFF(pHlp)->pfnISASetIrq(pDevIns, iIrq, iLevel);
4429}
4430
4431/**
4432 * @copydoc PDMDEVHLPR3::pfnISASetIrqNoWait
4433 */
4434DECLINLINE(void) PDMDevHlpISASetIrqNoWait(PPDMDEVINS pDevIns, int iIrq, int iLevel)
4435{
4436 pDevIns->CTX_SUFF(pHlp)->pfnISASetIrq(pDevIns, iIrq, iLevel);
4437}
4438
4439#ifdef IN_RING3
4440
4441/**
4442 * @copydoc PDMDEVHLPR3::pfnDriverAttach
4443 */
4444DECLINLINE(int) PDMDevHlpDriverAttach(PPDMDEVINS pDevIns, RTUINT iLun, PPDMIBASE pBaseInterface, PPDMIBASE *ppBaseInterface, const char *pszDesc)
4445{
4446 return pDevIns->pHlpR3->pfnDriverAttach(pDevIns, iLun, pBaseInterface, ppBaseInterface, pszDesc);
4447}
4448
4449/**
4450 * @copydoc PDMDEVHLPR3::pfnQueueCreate
4451 */
4452DECLINLINE(int) PDMDevHlpQueueCreate(PPDMDEVINS pDevIns, RTUINT cbItem, RTUINT cItems, uint32_t cMilliesInterval,
4453 PFNPDMQUEUEDEV pfnCallback, bool fGCEnabled, const char *pszName, PPDMQUEUE *ppQueue)
4454{
4455 return pDevIns->pHlpR3->pfnQueueCreate(pDevIns, cbItem, cItems, cMilliesInterval, pfnCallback, fGCEnabled, pszName, ppQueue);
4456}
4457
4458/**
4459 * Initializes a PDM critical section.
4460 *
4461 * The PDM critical sections are derived from the IPRT critical sections, but
4462 * works in RC and R0 as well.
4463 *
4464 * @returns VBox status code.
4465 * @param pDevIns The device instance.
4466 * @param pCritSect Pointer to the critical section.
4467 * @param RT_SRC_POS_DECL Use RT_SRC_POS.
4468 * @param pszNameFmt Format string for naming the critical section.
4469 * For statistics and lock validation.
4470 * @param ... Arguments for the format string.
4471 */
4472DECLINLINE(int) PDMDevHlpCritSectInit(PPDMDEVINS pDevIns, PPDMCRITSECT pCritSect, RT_SRC_POS_DECL, const char *pszNameFmt, ...)
4473{
4474 int rc;
4475 va_list va;
4476 va_start(va, pszNameFmt);
4477 rc = pDevIns->pHlpR3->pfnCritSectInit(pDevIns, pCritSect, RT_SRC_POS_ARGS, pszNameFmt, va);
4478 va_end(va);
4479 return rc;
4480}
4481
4482/**
4483 * @copydoc PDMDEVHLPR3::pfnThreadCreate
4484 */
4485DECLINLINE(int) PDMDevHlpThreadCreate(PPDMDEVINS pDevIns, PPPDMTHREAD ppThread, void *pvUser, PFNPDMTHREADDEV pfnThread,
4486 PFNPDMTHREADWAKEUPDEV pfnWakeup, size_t cbStack, RTTHREADTYPE enmType, const char *pszName)
4487{
4488 return pDevIns->pHlpR3->pfnThreadCreate(pDevIns, ppThread, pvUser, pfnThread, pfnWakeup, cbStack, enmType, pszName);
4489}
4490
4491/**
4492 * @copydoc PDMDEVHLPR3::pfnSetAsyncNotification
4493 */
4494DECLINLINE(int) PDMDevHlpSetAsyncNotification(PPDMDEVINS pDevIns, PFNPDMDEVASYNCNOTIFY pfnAsyncNotify)
4495{
4496 return pDevIns->pHlpR3->pfnSetAsyncNotification(pDevIns, pfnAsyncNotify);
4497}
4498
4499/**
4500 * @copydoc PDMDEVHLPR3::pfnAsyncNotificationCompleted
4501 */
4502DECLINLINE(void) PDMDevHlpAsyncNotificationCompleted(PPDMDEVINS pDevIns)
4503{
4504 pDevIns->pHlpR3->pfnAsyncNotificationCompleted(pDevIns);
4505}
4506
4507/**
4508 * @copydoc PDMDEVHLPR3::pfnA20Set
4509 */
4510DECLINLINE(void) PDMDevHlpA20Set(PPDMDEVINS pDevIns, bool fEnable)
4511{
4512 pDevIns->pHlpR3->pfnA20Set(pDevIns, fEnable);
4513}
4514
4515/**
4516 * @copydoc PDMDEVHLPR3::pfnRTCRegister
4517 */
4518DECLINLINE(int) PDMDevHlpRTCRegister(PPDMDEVINS pDevIns, PCPDMRTCREG pRtcReg, PCPDMRTCHLP *ppRtcHlp)
4519{
4520 return pDevIns->pHlpR3->pfnRTCRegister(pDevIns, pRtcReg, ppRtcHlp);
4521}
4522
4523/**
4524 * @copydoc PDMDEVHLPR3::pfnPCIBusRegister
4525 */
4526DECLINLINE(int) PDMDevHlpPCIBusRegister(PPDMDEVINS pDevIns, PPDMPCIBUSREG pPciBusReg, PCPDMPCIHLPR3 *ppPciHlpR3)
4527{
4528 return pDevIns->pHlpR3->pfnPCIBusRegister(pDevIns, pPciBusReg, ppPciHlpR3);
4529}
4530
4531/**
4532 * @copydoc PDMDEVHLPR3::pfnPICRegister
4533 */
4534DECLINLINE(int) PDMDevHlpPICRegister(PPDMDEVINS pDevIns, PPDMPICREG pPicReg, PCPDMPICHLPR3 *ppPicHlpR3)
4535{
4536 return pDevIns->pHlpR3->pfnPICRegister(pDevIns, pPicReg, ppPicHlpR3);
4537}
4538
4539/**
4540 * @copydoc PDMDEVHLPR3::pfnAPICRegister
4541 */
4542DECLINLINE(int) PDMDevHlpAPICRegister(PPDMDEVINS pDevIns, PPDMAPICREG pApicReg, PCPDMAPICHLPR3 *ppApicHlpR3)
4543{
4544 return pDevIns->pHlpR3->pfnAPICRegister(pDevIns, pApicReg, ppApicHlpR3);
4545}
4546
4547/**
4548 * @copydoc PDMDEVHLPR3::pfn
4549 */
4550DECLINLINE(int) PDMDevHlpIOAPICRegister(PPDMDEVINS pDevIns, PPDMIOAPICREG pIoApicReg, PCPDMIOAPICHLPR3 *ppIoApicHlpR3)
4551{
4552 return pDevIns->pHlpR3->pfnIOAPICRegister(pDevIns, pIoApicReg, ppIoApicHlpR3);
4553}
4554
4555/**
4556 * @copydoc PDMDEVHLPR3::pfnHPETRegister
4557 */
4558DECLINLINE(int) PDMDevHlpHPETRegister(PPDMDEVINS pDevIns, PPDMHPETREG pHpetReg, PCPDMHPETHLPR3 *ppHpetHlpR3)
4559{
4560 return pDevIns->pHlpR3->pfnHPETRegister(pDevIns, pHpetReg, ppHpetHlpR3);
4561}
4562
4563/**
4564 * @copydoc PDMDEVHLPR3::pfnPciRawRegister
4565 */
4566DECLINLINE(int) PDMDevHlpPciRawRegister(PPDMDEVINS pDevIns, PPDMPCIRAWREG pPciRawReg, PCPDMPCIRAWHLPR3 *ppPciRawHlpR3)
4567{
4568 return pDevIns->pHlpR3->pfnPciRawRegister(pDevIns, pPciRawReg, ppPciRawHlpR3);
4569}
4570
4571/**
4572 * @copydoc PDMDEVHLPR3::pfnDMACRegister
4573 */
4574DECLINLINE(int) PDMDevHlpDMACRegister(PPDMDEVINS pDevIns, PPDMDMACREG pDmacReg, PCPDMDMACHLP *ppDmacHlp)
4575{
4576 return pDevIns->pHlpR3->pfnDMACRegister(pDevIns, pDmacReg, ppDmacHlp);
4577}
4578
4579/**
4580 * @copydoc PDMDEVHLPR3::pfnDMARegister
4581 */
4582DECLINLINE(int) PDMDevHlpDMARegister(PPDMDEVINS pDevIns, unsigned uChannel, PFNDMATRANSFERHANDLER pfnTransferHandler, void *pvUser)
4583{
4584 return pDevIns->pHlpR3->pfnDMARegister(pDevIns, uChannel, pfnTransferHandler, pvUser);
4585}
4586
4587/**
4588 * @copydoc PDMDEVHLPR3::pfnDMAReadMemory
4589 */
4590DECLINLINE(int) PDMDevHlpDMAReadMemory(PPDMDEVINS pDevIns, unsigned uChannel, void *pvBuffer, uint32_t off, uint32_t cbBlock, uint32_t *pcbRead)
4591{
4592 return pDevIns->pHlpR3->pfnDMAReadMemory(pDevIns, uChannel, pvBuffer, off, cbBlock, pcbRead);
4593}
4594
4595/**
4596 * @copydoc PDMDEVHLPR3::pfnDMAWriteMemory
4597 */
4598DECLINLINE(int) PDMDevHlpDMAWriteMemory(PPDMDEVINS pDevIns, unsigned uChannel, const void *pvBuffer, uint32_t off, uint32_t cbBlock, uint32_t *pcbWritten)
4599{
4600 return pDevIns->pHlpR3->pfnDMAWriteMemory(pDevIns, uChannel, pvBuffer, off, cbBlock, pcbWritten);
4601}
4602
4603/**
4604 * @copydoc PDMDEVHLPR3::pfnDMASetDREQ
4605 */
4606DECLINLINE(int) PDMDevHlpDMASetDREQ(PPDMDEVINS pDevIns, unsigned uChannel, unsigned uLevel)
4607{
4608 return pDevIns->pHlpR3->pfnDMASetDREQ(pDevIns, uChannel, uLevel);
4609}
4610
4611/**
4612 * @copydoc PDMDEVHLPR3::pfnDMAGetChannelMode
4613 */
4614DECLINLINE(uint8_t) PDMDevHlpDMAGetChannelMode(PPDMDEVINS pDevIns, unsigned uChannel)
4615{
4616 return pDevIns->pHlpR3->pfnDMAGetChannelMode(pDevIns, uChannel);
4617}
4618
4619/**
4620 * @copydoc PDMDEVHLPR3::pfnDMASchedule
4621 */
4622DECLINLINE(void) PDMDevHlpDMASchedule(PPDMDEVINS pDevIns)
4623{
4624 pDevIns->pHlpR3->pfnDMASchedule(pDevIns);
4625}
4626
4627/**
4628 * @copydoc PDMDEVHLPR3::pfnCMOSWrite
4629 */
4630DECLINLINE(int) PDMDevHlpCMOSWrite(PPDMDEVINS pDevIns, unsigned iReg, uint8_t u8Value)
4631{
4632 return pDevIns->pHlpR3->pfnCMOSWrite(pDevIns, iReg, u8Value);
4633}
4634
4635/**
4636 * @copydoc PDMDEVHLPR3::pfnCMOSRead
4637 */
4638DECLINLINE(int) PDMDevHlpCMOSRead(PPDMDEVINS pDevIns, unsigned iReg, uint8_t *pu8Value)
4639{
4640 return pDevIns->pHlpR3->pfnCMOSRead(pDevIns, iReg, pu8Value);
4641}
4642
4643/**
4644 * @copydoc PDMDEVHLP::pfnCallR0
4645 */
4646DECLINLINE(int) PDMDevHlpCallR0(PPDMDEVINS pDevIns, uint32_t uOperation, uint64_t u64Arg)
4647{
4648 return pDevIns->pHlpR3->pfnCallR0(pDevIns, uOperation, u64Arg);
4649}
4650
4651#endif /* IN_RING3 */
4652
4653/**
4654 * @copydoc PDMDEVHLPR3::pfnGetVM
4655 */
4656DECLINLINE(PVM) PDMDevHlpGetVM(PPDMDEVINS pDevIns)
4657{
4658 return pDevIns->CTX_SUFF(pHlp)->pfnGetVM(pDevIns);
4659}
4660
4661/**
4662 * @copydoc PDMDEVHLPR3::pfnGetVMCPU
4663 */
4664DECLINLINE(PVMCPU) PDMDevHlpGetVMCPU(PPDMDEVINS pDevIns)
4665{
4666 return pDevIns->CTX_SUFF(pHlp)->pfnGetVMCPU(pDevIns);
4667}
4668
4669/**
4670 * @copydoc PDMDEVHLPR3::pfnTMTimeVirtGet
4671 */
4672DECLINLINE(uint64_t) PDMDevHlpTMTimeVirtGet(PPDMDEVINS pDevIns)
4673{
4674 return pDevIns->CTX_SUFF(pHlp)->pfnTMTimeVirtGet(pDevIns);
4675}
4676
4677/**
4678 * @copydoc PDMDEVHLPR3::pfnTMTimeVirtGetFreq
4679 */
4680DECLINLINE(uint64_t) PDMDevHlpTMTimeVirtGetFreq(PPDMDEVINS pDevIns)
4681{
4682 return pDevIns->CTX_SUFF(pHlp)->pfnTMTimeVirtGetFreq(pDevIns);
4683}
4684
4685/**
4686 * @copydoc PDMDEVHLPR3::pfnTMTimeVirtGetFreq
4687 */
4688DECLINLINE(uint64_t) PDMDevHlpTMTimeVirtGetNano(PPDMDEVINS pDevIns)
4689{
4690 return pDevIns->CTX_SUFF(pHlp)->pfnTMTimeVirtGetNano(pDevIns);
4691}
4692
4693#ifdef IN_RING3
4694
4695/**
4696 * @copydoc PDMDEVHLPR3::pfnRegisterVMMDevHeap
4697 */
4698DECLINLINE(int) PDMDevHlpRegisterVMMDevHeap(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, RTR3PTR pvHeap, unsigned cbSize)
4699{
4700 return pDevIns->pHlpR3->pfnRegisterVMMDevHeap(pDevIns, GCPhys, pvHeap, cbSize);
4701}
4702
4703/**
4704 * @copydoc PDMDEVHLPR3::pfnUnregisterVMMDevHeap
4705 */
4706DECLINLINE(int) PDMDevHlpUnregisterVMMDevHeap(PPDMDEVINS pDevIns, RTGCPHYS GCPhys)
4707{
4708 return pDevIns->pHlpR3->pfnUnregisterVMMDevHeap(pDevIns, GCPhys);
4709}
4710
4711/**
4712 * @copydoc PDMDEVHLPR3::pfnVMReset
4713 */
4714DECLINLINE(int) PDMDevHlpVMReset(PPDMDEVINS pDevIns)
4715{
4716 return pDevIns->pHlpR3->pfnVMReset(pDevIns);
4717}
4718
4719/**
4720 * @copydoc PDMDEVHLPR3::pfnVMSuspend
4721 */
4722DECLINLINE(int) PDMDevHlpVMSuspend(PPDMDEVINS pDevIns)
4723{
4724 return pDevIns->pHlpR3->pfnVMSuspend(pDevIns);
4725}
4726
4727/**
4728 * @copydoc PDMDEVHLPR3::pfnVMSuspendSaveAndPowerOff
4729 */
4730DECLINLINE(int) PDMDevHlpVMSuspendSaveAndPowerOff(PPDMDEVINS pDevIns)
4731{
4732 return pDevIns->pHlpR3->pfnVMSuspendSaveAndPowerOff(pDevIns);
4733}
4734
4735/**
4736 * @copydoc PDMDEVHLPR3::pfnVMPowerOff
4737 */
4738DECLINLINE(int) PDMDevHlpVMPowerOff(PPDMDEVINS pDevIns)
4739{
4740 return pDevIns->pHlpR3->pfnVMPowerOff(pDevIns);
4741}
4742
4743#endif /* IN_RING3 */
4744
4745/**
4746 * @copydoc PDMDEVHLPR3::pfnA20IsEnabled
4747 */
4748DECLINLINE(bool) PDMDevHlpA20IsEnabled(PPDMDEVINS pDevIns)
4749{
4750 return pDevIns->CTX_SUFF(pHlp)->pfnA20IsEnabled(pDevIns);
4751}
4752
4753#ifdef IN_RING3
4754
4755/**
4756 * @copydoc PDMDEVHLPR3::pfnGetCpuId
4757 */
4758DECLINLINE(void) PDMDevHlpGetCpuId(PPDMDEVINS pDevIns, uint32_t iLeaf, uint32_t *pEax, uint32_t *pEbx, uint32_t *pEcx, uint32_t *pEdx)
4759{
4760 pDevIns->pHlpR3->pfnGetCpuId(pDevIns, iLeaf, pEax, pEbx, pEcx, pEdx);
4761}
4762
4763#endif /* IN_RING3 */
4764#ifdef IN_RING0
4765
4766/**
4767 * @copydoc PDMDEVHLPR0::pfnCanEmulateIoBlock
4768 */
4769DECLINLINE(bool) PDMDevHlpCanEmulateIoBlock(PPDMDEVINS pDevIns)
4770{
4771 return pDevIns->CTX_SUFF(pHlp)->pfnCanEmulateIoBlock(pDevIns);
4772}
4773
4774#endif /* IN_RING0 */
4775
4776
4777
4778
4779/** Pointer to callbacks provided to the VBoxDeviceRegister() call. */
4780typedef struct PDMDEVREGCB *PPDMDEVREGCB;
4781
4782/**
4783 * Callbacks for VBoxDeviceRegister().
4784 */
4785typedef struct PDMDEVREGCB
4786{
4787 /** Interface version.
4788 * This is set to PDM_DEVREG_CB_VERSION. */
4789 uint32_t u32Version;
4790
4791 /**
4792 * Registers a device with the current VM instance.
4793 *
4794 * @returns VBox status code.
4795 * @param pCallbacks Pointer to the callback table.
4796 * @param pReg Pointer to the device registration record.
4797 * This data must be permanent and readonly.
4798 */
4799 DECLR3CALLBACKMEMBER(int, pfnRegister,(PPDMDEVREGCB pCallbacks, PCPDMDEVREG pReg));
4800} PDMDEVREGCB;
4801
4802/** Current version of the PDMDEVREGCB structure. */
4803#define PDM_DEVREG_CB_VERSION PDM_VERSION_MAKE(0xffe3, 1, 0)
4804
4805
4806/**
4807 * The VBoxDevicesRegister callback function.
4808 *
4809 * PDM will invoke this function after loading a device module and letting
4810 * the module decide which devices to register and how to handle conflicts.
4811 *
4812 * @returns VBox status code.
4813 * @param pCallbacks Pointer to the callback table.
4814 * @param u32Version VBox version number.
4815 */
4816typedef DECLCALLBACK(int) FNPDMVBOXDEVICESREGISTER(PPDMDEVREGCB pCallbacks, uint32_t u32Version);
4817
4818/** @} */
4819
4820RT_C_DECLS_END
4821
4822#endif
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