VirtualBox

Changeset 81886 in vbox for trunk/src/VBox/Devices/Storage


Ignore:
Timestamp:
Nov 15, 2019 10:27:05 PM (5 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
134681
Message:

DevAHCI: Split up structures. More or less done converting to new PDM device style. bugref:9218

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Storage/DevAHCI.cpp

    r81885 r81886  
    281281
    282282/**
    283  * @implements PDMIBASE
    284  * @implements PDMIMEDIAPORT
    285  * @implements PDMIMEDIAEXPORT
    286  */
    287 typedef struct AHCIPort
    288 {
    289     /** Pointer to the device instance - HC ptr */
    290     PPDMDEVINSR3                    pDevInsR3;
    291     /** Pointer to the device instance - R0 ptr */
    292     PPDMDEVINSR0                    pDevInsR0;
    293     /** Pointer to the device instance - RC ptr. */
    294     PPDMDEVINSRC                    pDevInsRC;
    295 
    296 #if HC_ARCH_BITS == 64
    297     uint32_t                        Alignment0;
    298 #endif
    299 
    300     /** Pointer to the parent AHCI structure - R3 ptr. */
    301     R3PTRTYPE(struct AHCI *)        pAhciR3;
    302     /** Pointer to the parent AHCI structure - R0 ptr. */
    303     R0PTRTYPE(struct AHCI *)        pAhciR0;
    304     /** Pointer to the parent AHCI structure - RC ptr. */
    305     RCPTRTYPE(struct AHCI *)        pAhciRC;
    306 
     283 * The shared state of an AHCI port.
     284 */
     285typedef struct AHCIPORT
     286{
    307287    /** Command List Base Address. */
    308288    uint32_t                        regCLB;
     
    336316    /** Current number of active tasks. */
    337317    volatile uint32_t               cTasksActive;
     318    uint32_t                        u32Alignment1;
    338319    /** Command List Base Address */
    339320    volatile RTGCPHYS               GCPhysAddrClb;
     
    362343    volatile bool                   fWrkThreadSleeping;
    363344
    364     bool                            afAlignment[4];
     345    bool                            afAlignment1[2];
    365346
    366347    /** Number of total sectors. */
     
    370351    /** Currently configured number of sectors in a multi-sector transfer. */
    371352    uint32_t                        cMultSectors;
     353    /** The LUN (same as port number). */
     354    uint32_t                        iLUN;
     355    /** Set if there is a device present at the port. */
     356    bool                            fPresent;
    372357    /** Currently active transfer mode (MDMA/UDMA) and speed. */
    373358    uint8_t                         uATATransferMode;
     359    /** Exponent of logical sectors in a physical sector, number of logical sectors is 2^exp. */
     360    uint8_t                         cLogSectorsPerPhysicalExp;
     361    uint8_t                         bAlignment2;
    374362    /** ATAPI sense data. */
    375363    uint8_t                         abATAPISense[ATAPI_SENSE_SIZE];
    376     /** Exponent of logical sectors in a physical sector, number of logical sectors is 2^exp. */
    377     uint8_t                         cLogSectorsPerPhysicalExp;
    378     /** The LUN. */
    379     RTUINT                          iLUN;
    380364
    381365    /** Bitmap for finished tasks (R3 -> Guest). */
     
    393377    volatile uint32_t               u32CurrentCommandSlot;
    394378
    395 #if HC_ARCH_BITS == 64
    396     uint32_t                        u32Alignment2;
    397 #endif
    398 
    399     /** Device specific settings (R3 only stuff). */
    400     /** Pointer to the attached driver's base interface. */
    401     R3PTRTYPE(PPDMIBASE)            pDrvBase;
    402     /** Pointer to the attached driver's block interface. */
    403     R3PTRTYPE(PPDMIMEDIA)           pDrvMedia;
    404     /** Pointer to the attached driver's extended interface. */
    405     R3PTRTYPE(PPDMIMEDIAEX)         pDrvMediaEx;
    406     /** Port description. */
    407     R3PTRTYPE(char *)               pszDesc;
    408     /** The base interface. */
    409     PDMIBASE                        IBase;
    410     /** The block port interface. */
    411     PDMIMEDIAPORT                   IPort;
    412     /** The extended media port interface. */
    413     PDMIMEDIAEXPORT                 IMediaExPort;
    414379    /** Physical geometry of this image. */
    415380    PDMMEDIAGEOMETRY                PCHSGeometry;
     381
    416382    /** The status LED state for this drive. */
    417383    PDMLED                          Led;
    418 
    419 #if HC_ARCH_BITS == 64
    420     uint32_t                        u32Alignment3;
    421 #endif
    422 
    423     /** Async IO Thread. */
    424     R3PTRTYPE(PPDMTHREAD)           pAsyncIOThread;
    425     /** First task throwing an error. */
    426     R3PTRTYPE(volatile PAHCIREQ)    pTaskErr;
    427384
    428385    /** The event semaphore the processing thread waits on. */
     
    445402
    446403    uint32_t                        u32Alignment5;
    447 
    448 } AHCIPort;
    449 AssertCompileSizeAlignment(AHCIPort, 8);
    450 /** Pointer to the state of an AHCI port. */
    451 typedef AHCIPort *PAHCIPort;
     404} AHCIPORT;
     405AssertCompileSizeAlignment(AHCIPORT, 8);
     406/** Pointer to the shared state of an AHCI port. */
     407typedef AHCIPORT *PAHCIPORT;
     408
     409
     410/**
     411 * The ring-3 state of an AHCI port.
     412 *
     413 * @implements PDMIBASE
     414 * @implements PDMIMEDIAPORT
     415 * @implements PDMIMEDIAEXPORT
     416 */
     417typedef struct AHCIPORTR3
     418{
     419    /** Pointer to the device instance - only to get our bearings in an interface
     420     *  method, nothing else. */
     421    PPDMDEVINSR3                    pDevIns;
     422
     423    /** The LUN (same as port number). */
     424    uint32_t                        iLUN;
     425
     426    /** Device specific settings (R3 only stuff). */
     427    /** Pointer to the attached driver's base interface. */
     428    R3PTRTYPE(PPDMIBASE)            pDrvBase;
     429    /** Pointer to the attached driver's block interface. */
     430    R3PTRTYPE(PPDMIMEDIA)           pDrvMedia;
     431    /** Pointer to the attached driver's extended interface. */
     432    R3PTRTYPE(PPDMIMEDIAEX)         pDrvMediaEx;
     433    /** Port description. */
     434    char                            szDesc[8];
     435    /** The base interface. */
     436    PDMIBASE                        IBase;
     437    /** The block port interface. */
     438    PDMIMEDIAPORT                   IPort;
     439    /** The extended media port interface. */
     440    PDMIMEDIAEXPORT                 IMediaExPort;
     441
     442    /** Async IO Thread. */
     443    R3PTRTYPE(PPDMTHREAD)           pAsyncIOThread;
     444    /** First task throwing an error. */
     445    R3PTRTYPE(volatile PAHCIREQ)    pTaskErr;
     446
     447} AHCIPORTR3;
     448AssertCompileSizeAlignment(AHCIPORTR3, 8);
     449/** Pointer to the ring-3 state of an AHCI port. */
     450typedef AHCIPORTR3 *PAHCIPORTR3;
    452451
    453452
     
    459458typedef struct AHCI
    460459{
    461     /** Pointer to the device instance - R3 ptr */
    462     PPDMDEVINSR3                    pDevInsR3;
    463     /** Pointer to the device instance - R0 ptr */
    464     PPDMDEVINSR0                    pDevInsR0;
    465     /** Pointer to the device instance - RC ptr. */
    466     PPDMDEVINSRC                    pDevInsRC;
    467 
    468 #if HC_ARCH_BITS == 64
    469     uint32_t                        Alignment0;
    470 #endif
    471 
    472     /** Status LUN: The base interface. */
    473     PDMIBASE                        IBase;
    474     /** Status LUN: Leds interface. */
    475     PDMILEDPORTS                    ILeds;
    476     /** Status LUN: Partner of ILeds. */
    477     R3PTRTYPE(PPDMILEDCONNECTORS)   pLedsConnector;
    478     /** Status LUN: Media Notifys. */
    479     R3PTRTYPE(PPDMIMEDIANOTIFY)     pMediaNotify;
    480 
    481 #if HC_ARCH_BITS == 32
    482     uint32_t                        Alignment1;
    483 #endif
    484 
    485460    /** Global Host Control register of the HBA
    486461     *  @todo r=bird: Make this a 'name' doxygen comment with { and add a
     
    506481    uint32_t                        regIdx;
    507482
    508 #if HC_ARCH_BITS == 64
    509     uint32_t                        Alignment3;
    510 #endif
    511 
    512483    /** Countdown timer for command completion coalescing. */
    513484    TMTIMERHANDLE                   hHbaCccTimer;
     
    515486    /** Which port number is used to mark an CCC interrupt */
    516487    uint8_t                         uCccPortNr;
    517 
    518 #if HC_ARCH_BITS == 64
    519     uint32_t                        Alignment6;
    520 #endif
     488    uint8_t                         abAlignment1[7];
    521489
    522490    /** Timeout value */
     
    528496
    529497    /** Register structure per port */
    530     AHCIPort                        ahciPort[AHCI_MAX_NR_PORTS_IMPL];
     498    AHCIPORT                        ahciPort[AHCI_MAX_NR_PORTS_IMPL];
    531499
    532500    /** The critical section. */
     
    537505    /** Number of I/O threads currently active - used for async controller reset handling. */
    538506    volatile uint32_t               cThreadsActive;
    539     /** Device is in a reset state. */
    540     bool                            fReset;
    541     /** Supports 64bit addressing */
    542     bool                            f64BitAddr;
    543     /** Indicates that PDMDevHlpAsyncNotificationCompleted should be called when
    544      * a port is entering the idle state. */
    545     bool volatile                   fSignalIdle;
    546     /** Flag whether the controller has BIOS access enabled. */
    547     bool                            fBootable;
     507
    548508    /** Flag whether the legacy port reset method should be used to make it work with saved states. */
    549509    bool                            fLegacyPortResetMethod;
    550510    /** Enable tiger (10.4.x) SSTS hack or not. */
    551511    bool                            fTigerHack;
    552     bool                            afAlignment7[2];
     512    /** Flag whether we have written the first 4bytes in an 8byte MMIO write successfully. */
     513    volatile bool                   f8ByteMMIO4BytesWrittenSuccessfully;
     514
     515    /** Device is in a reset state.
     516     * @todo r=bird: This isn't actually being modified by anyone...  */
     517    bool                            fReset;
     518    /** Supports 64bit addressing
     519     * @todo r=bird: This isn't really being modified by anyone (always false). */
     520    bool                            f64BitAddr;
     521    /** Flag whether the controller has BIOS access enabled.
     522     * @todo r=bird: Not used, just queried from CFGM.  */
     523    bool                            fBootable;
     524
     525    bool                            afAlignment2[2];
    553526
    554527    /** Number of usable ports on this controller. */
     
    556529    /** Number of usable command slots for each port. */
    557530    uint32_t                        cCmdSlotsAvail;
    558 
    559     /** Flag whether we have written the first 4bytes in an 8byte MMIO write successfully. */
    560     volatile bool                   f8ByteMMIO4BytesWrittenSuccessfully;
    561 
    562 #if HC_ARCH_BITS == 64
    563     uint32_t                        Alignment8;
    564 #endif
    565531
    566532    /** PCI region \#0: Legacy IDE fake, 8 ports. */
     
    584550
    585551/**
     552 * Main AHCI device ring-3 state.
     553 *
     554 * @implements  PDMILEDPORTS
     555 */
     556typedef struct AHCIR3
     557{
     558    /** Pointer to the device instance - only for getting our bearings in
     559     *  interface methods. */
     560    PPDMDEVINSR3                    pDevIns;
     561
     562    /** Status LUN: The base interface. */
     563    PDMIBASE                        IBase;
     564    /** Status LUN: Leds interface. */
     565    PDMILEDPORTS                    ILeds;
     566    /** Status LUN: Partner of ILeds. */
     567    R3PTRTYPE(PPDMILEDCONNECTORS)   pLedsConnector;
     568    /** Status LUN: Media Notifys. */
     569    R3PTRTYPE(PPDMIMEDIANOTIFY)     pMediaNotify;
     570
     571    /** Register structure per port */
     572    AHCIPORTR3                      aPorts[AHCI_MAX_NR_PORTS_IMPL];
     573
     574    /** Indicates that PDMDevHlpAsyncNotificationCompleted should be called when
     575     * a port is entering the idle state. */
     576    bool volatile                   fSignalIdle;
     577    bool                            afAlignment7[2+4];
     578} AHCIR3;
     579/** Pointer to the ring-3 state of an AHCI device. */
     580typedef AHCIR3 *PAHCIR3;
     581
     582
     583/**
     584 * Main AHCI device ring-0 state.
     585 */
     586typedef struct AHCIR0
     587{
     588    uint64_t                        uUnused;
     589} AHCIR0;
     590/** Pointer to the ring-0 state of an AHCI device. */
     591typedef AHCIR0 *PAHCIR0;
     592
     593
     594/**
     595 * Main AHCI device raw-mode state.
     596 */
     597typedef struct AHCIRC
     598{
     599    uint64_t                        uUnused;
     600} AHCIRC;
     601/** Pointer to the raw-mode state of an AHCI device. */
     602typedef AHCIRC *PAHCIRC;
     603
     604
     605/** Main AHCI device current context state. */
     606typedef CTX_SUFF(AHCI)  AHCICC;
     607/** Pointer to the current context state of an AHCI device. */
     608typedef CTX_SUFF(PAHCI) PAHCICC;
     609
     610
     611/**
    586612 * Scatter gather list entry.
    587613 */
     
    604630 *
    605631 * @returns nothing.
    606  * @param   pThis    The NVME controller instance.
     632 * @param   pDevIns  The device instance.
    607633 * @param   GCPhys   The guest physical address of the memory buffer.
    608634 * @param   pSgBuf   The pointer to the host R3 S/G buffer.
     
    614640 *                   cbCopy < *pcbSkip or 0 otherwise.
    615641 */
    616 typedef DECLCALLBACK(void) AHCIR3MEMCOPYCALLBACK(PAHCI pThis, RTGCPHYS GCPhys, PRTSGBUF pSgBuf, size_t cbCopy, size_t *pcbSkip);
     642typedef DECLCALLBACK(void) AHCIR3MEMCOPYCALLBACK(PPDMDEVINS pDevIns, RTGCPHYS GCPhys,
     643                                                 PRTSGBUF pSgBuf, size_t cbCopy, size_t *pcbSkip);
    617644/** Pointer to a memory copy buffer callback. */
    618645typedef AHCIR3MEMCOPYCALLBACK *PAHCIR3MEMCOPYCALLBACK;
     
    805832{
    806833    const char *pszName;
    807     int (*pfnRead )(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value);
    808     int (*pfnWrite)(PAHCI pThis, uint32_t iReg, uint32_t u32Value);
     834    VBOXSTRICTRC (*pfnRead )(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value);
     835    VBOXSTRICTRC (*pfnWrite)(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value);
    809836} AHCIOPREG;
    810837
     
    815842{
    816843    const char *pszName;
    817     int (*pfnRead )(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value);
    818     int (*pfnWrite)(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value);
     844    VBOXSTRICTRC (*pfnRead )(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value);
     845    VBOXSTRICTRC (*pfnWrite)(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value);
    819846} AHCIPORTOPREG;
    820847
     
    826853RT_C_DECLS_BEGIN
    827854#ifdef IN_RING3
    828 static void ahciHBAReset(PAHCI pThis);
    829 static int  ahciPostFisIntoMemory(PAHCIPort pAhciPort, unsigned uFisType, uint8_t *cmdFis);
    830 static void ahciPostFirstD2HFisIntoMemory(PAHCIPort pAhciPort);
    831 static size_t ahciR3CopyBufferToPrdtl(PAHCI pThis, PAHCIREQ pAhciReq, const void *pvSrc,
    832                                       size_t cbSrc, size_t cbSkip);
    833 static bool ahciCancelActiveTasks(PAHCIPort pAhciPort);
     855static void ahciR3HBAReset(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIR3 pThisCC);
     856static int ahciPostFisIntoMemory(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort, unsigned uFisType, uint8_t *pCmdFis);
     857static void ahciPostFirstD2HFisIntoMemory(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort);
     858static size_t ahciR3CopyBufferToPrdtl(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, const void *pvSrc, size_t cbSrc, size_t cbSkip);
     859static bool ahciR3CancelActiveTasks(PAHCIPORTR3 pAhciPortR3);
    834860#endif
    835861RT_C_DECLS_END
     
    839865*   Defined Constants And Macros                                                                                                 *
    840866*********************************************************************************************************************************/
    841 #define PDMIBASE_2_PAHCIPORT(pInterface)         ( (PAHCIPort)((uintptr_t)(pInterface) - RT_UOFFSETOF(AHCIPort, IBase)) )
    842 #define PDMIMEDIAPORT_2_PAHCIPORT(pInterface)    ( (PAHCIPort)((uintptr_t)(pInterface) - RT_UOFFSETOF(AHCIPort, IPort)) )
    843 #define PDMIBASE_2_PAHCI(pInterface)             ( (PAHCI)((uintptr_t)(pInterface) - RT_UOFFSETOF(AHCI, IBase)) )
    844 #define PDMILEDPORTS_2_PAHCI(pInterface)         ( (PAHCI)((uintptr_t)(pInterface) - RT_UOFFSETOF(AHCI, ILeds)) )
    845 
    846867#define AHCI_RTGCPHYS_FROM_U32(Hi, Lo)             ( (RTGCPHYS)RT_MAKE_U64(Lo, Hi) )
    847868
     
    883904 * Update PCI IRQ levels
    884905 */
    885 static void ahciHbaClearInterrupt(PAHCI pThis)
     906static void ahciHbaClearInterrupt(PPDMDEVINS pDevIns)
    886907{
    887908    Log(("%s: Clearing interrupt\n", __FUNCTION__));
    888     PDMDevHlpPCISetIrq(pThis->CTX_SUFF(pDevIns), 0, 0);
     909    PDMDevHlpPCISetIrq(pDevIns, 0, 0);
    889910}
    890911
     
    892913 * Updates the IRQ level and sets port bit in the global interrupt status register of the HBA.
    893914 */
    894 static int ahciHbaSetInterrupt(PAHCI pThis, uint8_t iPort, int rcBusy)
     915static int ahciHbaSetInterrupt(PPDMDEVINS pDevIns, PAHCI pThis, uint8_t iPort, int rcBusy)
    895916{
    896917    Log(("P%u: %s: Setting interrupt\n", iPort, __FUNCTION__));
    897918
    898     int rc = PDMDevHlpCritSectEnter(pThis->CTX_SUFF(pDevIns), &pThis->lock, rcBusy);
     919    int rc = PDMDevHlpCritSectEnter(pDevIns, &pThis->lock, rcBusy);
    899920    if (rc != VINF_SUCCESS)
    900921        return rc;
     
    908929            {
    909930                /* Reset command completion coalescing state. */
    910                 PDMDevHlpTimerSetMillies(pThis->CTX_SUFF(pDevIns), pThis->hHbaCccTimer, pThis->uCccTimeout);
     931                PDMDevHlpTimerSetMillies(pDevIns, pThis->hHbaCccTimer, pThis->uCccTimeout);
    911932                pThis->uCccCurrentNr = 0;
    912933
     
    915936                {
    916937                    Log(("P%u: %s: Fire interrupt\n", iPort, __FUNCTION__));
    917                     PDMDevHlpPCISetIrq(pThis->CTX_SUFF(pDevIns), 0, 1);
     938                    PDMDevHlpPCISetIrq(pDevIns, 0, 1);
    918939                }
    919940            }
     
    930951            {
    931952                Log(("P%u: %s: Fire interrupt\n", iPort, __FUNCTION__));
    932                 PDMDevHlpPCISetIrq(pThis->CTX_SUFF(pDevIns), 0, 1);
     953                PDMDevHlpPCISetIrq(pDevIns, 0, 1);
    933954            }
    934955        }
    935956    }
    936957
    937     PDMDevHlpCritSectLeave(pThis->CTX_SUFF(pDevIns), &pThis->lock);
     958    PDMDevHlpCritSectLeave(pDevIns, &pThis->lock);
    938959    return VINF_SUCCESS;
    939960}
     
    949970    PAHCI pThis = (PAHCI)pvUser;
    950971
    951     int rc = ahciHbaSetInterrupt(pThis, pThis->uCccPortNr, VERR_IGNORED);
     972    int rc = ahciHbaSetInterrupt(pDevIns, pThis, pThis->uCccPortNr, VERR_IGNORED);
    952973    AssertRC(rc);
    953974}
     
    957978 *
    958979 * @returns nothing.
    959  * @param   pAhciPort    The port to finish the reset on.
    960  */
    961 static void ahciPortResetFinish(PAHCIPort pAhciPort)
     980 * @param   pDevIns     The device instance.
     981 * @param   pThis       The shared AHCI state.
     982 * @param   pAhciPort   The port to finish the reset on, shared bits.
     983 * @param   pAhciPortR3 The port to finish the reset on, ring-3 bits.
     984 */
     985static void ahciPortResetFinish(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3)
    962986{
    963987    ahciLog(("%s: Initiated.\n", __FUNCTION__));
    964988
    965989    /* Cancel all tasks first. */
    966     bool fAllTasksCanceled = ahciCancelActiveTasks(pAhciPort);
     990    bool fAllTasksCanceled = ahciR3CancelActiveTasks(pAhciPortR3);
    967991    Assert(fAllTasksCanceled); NOREF(fAllTasksCanceled);
    968992
     
    9801004    if ((pAhciPort->regCMD & AHCI_PORT_CMD_FRE) && (!pAhciPort->fFirstD2HFisSent))
    9811005    {
    982         ahciPostFirstD2HFisIntoMemory(pAhciPort);
     1006        ahciPostFirstD2HFisIntoMemory(pDevIns, pAhciPort);
    9831007        ASMAtomicOrU32(&pAhciPort->regIS, AHCI_PORT_IS_DHRS);
    9841008
    9851009        if (pAhciPort->regIE & AHCI_PORT_IE_DHRE)
    9861010        {
    987             int rc = ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     1011            int rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    9881012            AssertRC(rc);
    9891013        }
     
    10181042 *
    10191043 * @returns nothing.
    1020  * @param   pThis     The AHCI controller instance.
    1021  * @param   pAhciPort The port to kick.
    1022  */
    1023 static void ahciIoThreadKick(PAHCI pThis, PAHCIPort pAhciPort)
     1044 * @param   pDevIns     The device instance.
     1045 * @param   pAhciPort   The port to kick.
     1046 */
     1047static void ahciIoThreadKick(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort)
    10241048{
    10251049    LogFlowFunc(("Signal event semaphore\n"));
    1026     int rc = PDMDevHlpSUPSemEventSignal(pThis->CTX_SUFF(pDevIns), pAhciPort->hEvtProcess);
     1050    int rc = PDMDevHlpSUPSemEventSignal(pDevIns, pAhciPort->hEvtProcess);
    10271051    AssertRC(rc);
    10281052}
    10291053
    1030 static int PortCmdIssue_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1031 {
    1032     RT_NOREF(iReg);
     1054static VBOXSTRICTRC PortCmdIssue_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1055{
    10331056    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
     1057    RT_NOREF(pThis, iReg);
    10341058
    10351059    /* Update the CI register first. */
     
    10501074        /* Send a notification to R3 if u32TasksNew was 0 before our write. */
    10511075        if (ASMAtomicReadBool(&pAhciPort->fWrkThreadSleeping))
    1052             ahciIoThreadKick(pThis, pAhciPort);
     1076            ahciIoThreadKick(pDevIns, pAhciPort);
    10531077        else
    10541078            ahciLog(("%s: Worker thread busy, no need to kick.\n", __FUNCTION__));
     
    10621086}
    10631087
    1064 static int PortCmdIssue_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1065 {
    1066     RT_NOREF(pThis, iReg);
     1088static VBOXSTRICTRC PortCmdIssue_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1089{
     1090    RT_NOREF(pDevIns, pThis, iReg);
    10671091
    10681092    uint32_t uCIValue = ASMAtomicXchgU32(&pAhciPort->u32TasksFinished, 0);
     
    10751099}
    10761100
    1077 static int PortSActive_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1078 {
    1079     RT_NOREF(pThis, iReg);
     1101static VBOXSTRICTRC PortSActive_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1102{
    10801103    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
     1104    RT_NOREF(pDevIns, pThis, iReg);
    10811105
    10821106    pAhciPort->regSACT |= u32Value;
     
    10851109}
    10861110
    1087 static int PortSActive_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1088 {
    1089     RT_NOREF(pThis, iReg);
     1111static VBOXSTRICTRC PortSActive_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1112{
     1113    RT_NOREF(pDevIns, pThis, iReg);
    10901114
    10911115    uint32_t u32TasksFinished = ASMAtomicXchgU32(&pAhciPort->u32QueuedTasksFinished, 0);
     
    11001124}
    11011125
    1102 static int PortSError_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1103 {
    1104     RT_NOREF(pThis, iReg);
     1126static VBOXSTRICTRC PortSError_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1127{
     1128    RT_NOREF(pDevIns, pThis, iReg);
    11051129    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    11061130
     
    11221146}
    11231147
    1124 static int PortSError_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1125 {
    1126     RT_NOREF(pThis, iReg);
     1148static VBOXSTRICTRC PortSError_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1149{
     1150    RT_NOREF(pDevIns, pThis, iReg);
    11271151    ahciLog(("%s: read regSERR=%#010x\n", __FUNCTION__, pAhciPort->regSERR));
    11281152    *pu32Value = pAhciPort->regSERR;
     
    11301154}
    11311155
    1132 static int PortSControl_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
     1156static VBOXSTRICTRC PortSControl_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
    11331157{
    11341158    RT_NOREF(pThis, iReg);
     
    11381162
    11391163#ifndef IN_RING3
    1140     RT_NOREF(pAhciPort, u32Value);
     1164    RT_NOREF(pDevIns, pAhciPort, u32Value);
    11411165    return VINF_IOM_R3_MMIO_WRITE;
    11421166#else
     
    11441168    {
    11451169        if (!ASMAtomicXchgBool(&pAhciPort->fPortReset, true))
    1146             LogRel(("AHCI#%u: Port %d reset\n", pThis->CTX_SUFF(pDevIns)->iInstance,
     1170            LogRel(("AHCI#%u: Port %d reset\n", pDevIns->iInstance,
    11471171                    pAhciPort->iLUN));
    11481172
     
    11551179    else if (   (u32Value & AHCI_PORT_SCTL_DET) == AHCI_PORT_SCTL_DET_NINIT
    11561180             && (pAhciPort->regSCTL & AHCI_PORT_SCTL_DET) == AHCI_PORT_SCTL_DET_INIT
    1157              && pAhciPort->pDrvBase)
     1181             && pAhciPort->fPresent)
    11581182    {
    11591183        /* Do the port reset here, so the guest sees the new status immediately. */
    11601184        if (pThis->fLegacyPortResetMethod)
    11611185        {
    1162             ahciPortResetFinish(pAhciPort);
     1186            PAHCIR3     pThisCC     = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     1187            PAHCIPORTR3 pAhciPortR3 = &RT_SAFE_SUBSCRIPT(pThisCC->aPorts, pAhciPort->iLUN);
     1188            ahciPortResetFinish(pDevIns, pThis, pAhciPort, pAhciPortR3);
    11631189            pAhciPort->regSCTL = u32Value; /* Update after finishing the reset, so the I/O thread doesn't get a chance to do the reset. */
    11641190        }
     
    11721198
    11731199            /* Kick the thread to finish the reset. */
    1174             ahciIoThreadKick(pThis, pAhciPort);
     1200            ahciIoThreadKick(pDevIns, pAhciPort);
    11751201        }
    11761202    }
     
    11821208}
    11831209
    1184 static int PortSControl_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1185 {
    1186     RT_NOREF(pThis, iReg);
     1210static VBOXSTRICTRC PortSControl_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1211{
     1212    RT_NOREF(pDevIns, pThis, iReg);
    11871213    ahciLog(("%s: read regSCTL=%#010x\n", __FUNCTION__, pAhciPort->regSCTL));
    11881214    ahciLog(("%s: IPM=%d SPD=%d DET=%d\n", __FUNCTION__,
     
    11941220}
    11951221
    1196 static int PortSStatus_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1197 {
    1198     RT_NOREF(pThis, iReg);
     1222static VBOXSTRICTRC PortSStatus_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1223{
     1224    RT_NOREF(pDevIns, pThis, iReg);
    11991225    ahciLog(("%s: read regSSTS=%#010x\n", __FUNCTION__, pAhciPort->regSSTS));
    12001226    ahciLog(("%s: IPM=%d SPD=%d DET=%d\n", __FUNCTION__,
     
    12061232}
    12071233
    1208 static int PortSignature_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1209 {
    1210     RT_NOREF(pThis, iReg);
     1234static VBOXSTRICTRC PortSignature_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1235{
     1236    RT_NOREF(pDevIns, pThis, iReg);
    12111237    ahciLog(("%s: read regSIG=%#010x\n", __FUNCTION__, pAhciPort->regSIG));
    12121238    *pu32Value = pAhciPort->regSIG;
     
    12141240}
    12151241
    1216 static int PortTaskFileData_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1217 {
    1218     RT_NOREF(pThis, iReg);
     1242static VBOXSTRICTRC PortTaskFileData_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1243{
     1244    RT_NOREF(pDevIns, pThis, iReg);
    12191245    ahciLog(("%s: read regTFD=%#010x\n", __FUNCTION__, pAhciPort->regTFD));
    12201246    ahciLog(("%s: ERR=%x BSY=%d DRQ=%d ERR=%d\n", __FUNCTION__,
     
    12281254 * Read from the port command register.
    12291255 */
    1230 static int PortCmd_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1231 {
    1232     RT_NOREF(pThis, iReg);
     1256static VBOXSTRICTRC PortCmd_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1257{
     1258    RT_NOREF(pDevIns, pThis, iReg);
    12331259    ahciLog(("%s: read regCMD=%#010x\n", __FUNCTION__, pAhciPort->regCMD | AHCI_PORT_CMD_CCS_SHIFT(pAhciPort->u32CurrentCommandSlot)));
    12341260    ahciLog(("%s: ICC=%d ASP=%d ALPE=%d DLAE=%d ATAPI=%d CPD=%d ISP=%d HPCP=%d PMA=%d CPS=%d CR=%d FR=%d ISS=%d CCS=%d FRE=%d CLO=%d POD=%d SUD=%d ST=%d\n",
     
    12511277 * This is the register where all the data transfer is started
    12521278 */
    1253 static int PortCmd_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1254 {
    1255     RT_NOREF(iReg);
     1279static VBOXSTRICTRC PortCmd_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1280{
     1281    RT_NOREF(pDevIns, pThis, iReg);
    12561282    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    12571283    ahciLog(("%s: ICC=%d ASP=%d ALPE=%d DLAE=%d ATAPI=%d CPD=%d ISP=%d HPCP=%d PMA=%d CPS=%d CR=%d FR=%d ISS=%d CCS=%d FRE=%d CLO=%d POD=%d SUD=%d ST=%d\n",
     
    12861312             * IS.PCS is clear.
    12871313             */
    1288             if (   pAhciPort->pDrvBase
     1314            if (   pAhciPort->fPresent
    12891315                && !(pAhciPort->regIS & AHCI_PORT_IS_PCS))
    12901316            {
     
    12981324                    ASMAtomicOrU32(&pAhciPort->u32TasksNew, pAhciPort->regCI);
    12991325                    LogFlowFunc(("Signal event semaphore\n"));
    1300                     int rc = PDMDevHlpSUPSemEventSignal(pThis->CTX_SUFF(pDevIns), pAhciPort->hEvtProcess);
     1326                    int rc = PDMDevHlpSUPSemEventSignal(pDevIns, pAhciPort->hEvtProcess);
    13011327                    AssertRC(rc);
    13021328                }
     
    13041330            else
    13051331            {
    1306                 if (!pAhciPort->pDrvBase)
     1332                if (!pAhciPort->fPresent)
    13071333                    ahciLog(("%s: No pDrvBase, clearing PxCMD.CR!\n", __FUNCTION__));
    13081334                else
     
    13231349        }
    13241350    }
    1325     else if (pAhciPort->pDrvBase)
     1351    else if (pAhciPort->fPresent)
    13261352    {
    13271353        if ((u32Value & AHCI_PORT_CMD_POD) && (pAhciPort->regCMD & AHCI_PORT_CMD_CPS) && !pAhciPort->fPoweredOn)
     
    13461372                return VINF_IOM_R3_MMIO_WRITE;
    13471373#else
    1348                 ahciPostFirstD2HFisIntoMemory(pAhciPort);
     1374                ahciPostFirstD2HFisIntoMemory(pDevIns, pAhciPort);
    13491375                ASMAtomicOrU32(&pAhciPort->regIS, AHCI_PORT_IS_DHRS);
    13501376
    13511377                if (pAhciPort->regIE & AHCI_PORT_IE_DHRE)
    13521378                {
    1353                     int rc = ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     1379                    int rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    13541380                    AssertRC(rc);
    13551381                }
     
    13751401        /* Send the first D2H FIS only if it wasn't already sent. */
    13761402        if (   !pAhciPort->fFirstD2HFisSent
    1377             && pAhciPort->pDrvBase)
     1403            && pAhciPort->fPresent)
    13781404        {
    13791405#ifndef IN_RING3
    13801406            return VINF_IOM_R3_MMIO_WRITE;
    13811407#else
    1382             ahciPostFirstD2HFisIntoMemory(pAhciPort);
     1408            ahciPostFirstD2HFisIntoMemory(pDevIns, pAhciPort);
    13831409            pAhciPort->fFirstD2HFisSent = true;
    13841410#endif
     
    13991425 * Read from the port interrupt enable register.
    14001426 */
    1401 static int PortIntrEnable_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1402 {
    1403     RT_NOREF(pThis, iReg);
     1427static VBOXSTRICTRC PortIntrEnable_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1428{
     1429    RT_NOREF(pDevIns, pThis, iReg);
    14041430    ahciLog(("%s: read regIE=%#010x\n", __FUNCTION__, pAhciPort->regIE));
    14051431    ahciLog(("%s: CPDE=%d TFEE=%d HBFE=%d HBDE=%d IFE=%d INFE=%d OFE=%d IPME=%d PRCE=%d DIE=%d PCE=%d DPE=%d UFE=%d SDBE=%d DSE=%d PSE=%d DHRE=%d\n",
     
    14201446 * Write to the port interrupt enable register.
    14211447 */
    1422 static int PortIntrEnable_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
     1448static VBOXSTRICTRC PortIntrEnable_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
    14231449{
    14241450    RT_NOREF(iReg);
     
    14421468    int rc = VINF_SUCCESS;
    14431469    if (u32Value & u32IntrStatus)
    1444         rc = ahciHbaSetInterrupt(pThis, pAhciPort->iLUN, VINF_IOM_R3_MMIO_WRITE);
     1470        rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VINF_IOM_R3_MMIO_WRITE);
    14451471
    14461472    if (rc == VINF_SUCCESS)
     
    14531479 * Read from the port interrupt status register.
    14541480 */
    1455 static int PortIntrSts_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1456 {
    1457     RT_NOREF(pThis, iReg);
     1481static VBOXSTRICTRC PortIntrSts_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1482{
     1483    RT_NOREF(pDevIns, pThis, iReg);
    14581484    ahciLog(("%s: read regIS=%#010x\n", __FUNCTION__, pAhciPort->regIS));
    14591485    ahciLog(("%s: CPDS=%d TFES=%d HBFS=%d HBDS=%d IFS=%d INFS=%d OFS=%d IPMS=%d PRCS=%d DIS=%d PCS=%d DPS=%d UFS=%d SDBS=%d DSS=%d PSS=%d DHRS=%d\n",
     
    14741500 * Write to the port interrupt status register.
    14751501 */
    1476 static int PortIntrSts_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1477 {
    1478     RT_NOREF(pThis, iReg);
     1502static VBOXSTRICTRC PortIntrSts_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1503{
     1504    RT_NOREF(pDevIns, pThis, iReg);
    14791505    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    14801506    ASMAtomicAndU32(&pAhciPort->regIS, ~(u32Value & AHCI_PORT_IS_READONLY));
     
    14861512 * Read from the port FIS base address upper 32bit register.
    14871513 */
    1488 static int PortFisAddrUp_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1489 {
    1490     RT_NOREF(pThis, iReg);
     1514static VBOXSTRICTRC PortFisAddrUp_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1515{
     1516    RT_NOREF(pDevIns, pThis, iReg);
    14911517    ahciLog(("%s: read regFBU=%#010x\n", __FUNCTION__, pAhciPort->regFBU));
    14921518    *pu32Value = pAhciPort->regFBU;
     
    14971523 * Write to the port FIS base address upper 32bit register.
    14981524 */
    1499 static int PortFisAddrUp_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1500 {
    1501     RT_NOREF(pThis, iReg);
     1525static VBOXSTRICTRC PortFisAddrUp_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1526{
     1527    RT_NOREF(pDevIns, pThis, iReg);
    15021528    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    15031529
     
    15111537 * Read from the port FIS base address register.
    15121538 */
    1513 static int PortFisAddr_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1514 {
    1515     RT_NOREF(pThis, iReg);
     1539static VBOXSTRICTRC PortFisAddr_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1540{
     1541    RT_NOREF(pDevIns, pThis, iReg);
    15161542    ahciLog(("%s: read regFB=%#010x\n", __FUNCTION__, pAhciPort->regFB));
    15171543    *pu32Value = pAhciPort->regFB;
     
    15221548 * Write to the port FIS base address register.
    15231549 */
    1524 static int PortFisAddr_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1525 {
    1526     RT_NOREF(pThis, iReg);
     1550static VBOXSTRICTRC PortFisAddr_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1551{
     1552    RT_NOREF(pDevIns, pThis, iReg);
    15271553    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    15281554
     
    15381564 * Write to the port command list base address upper 32bit register.
    15391565 */
    1540 static int PortCmdLstAddrUp_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1541 {
    1542     RT_NOREF(pThis, iReg);
     1566static VBOXSTRICTRC PortCmdLstAddrUp_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1567{
     1568    RT_NOREF(pDevIns, pThis, iReg);
    15431569    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    15441570
     
    15521578 * Read from the port command list base address upper 32bit register.
    15531579 */
    1554 static int PortCmdLstAddrUp_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1555 {
    1556     RT_NOREF(pThis, iReg);
     1580static VBOXSTRICTRC PortCmdLstAddrUp_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1581{
     1582    RT_NOREF(pDevIns, pThis, iReg);
    15571583    ahciLog(("%s: read regCLBU=%#010x\n", __FUNCTION__, pAhciPort->regCLBU));
    15581584    *pu32Value = pAhciPort->regCLBU;
     
    15631589 * Read from the port command list base address register.
    15641590 */
    1565 static int PortCmdLstAddr_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1566 {
    1567     RT_NOREF(pThis, iReg);
     1591static VBOXSTRICTRC PortCmdLstAddr_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1592{
     1593    RT_NOREF(pDevIns, pThis, iReg);
    15681594    ahciLog(("%s: read regCLB=%#010x\n", __FUNCTION__, pAhciPort->regCLB));
    15691595    *pu32Value = pAhciPort->regCLB;
     
    15741600 * Write to the port command list base address register.
    15751601 */
    1576 static int PortCmdLstAddr_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1577 {
    1578     RT_NOREF(pThis, iReg);
     1602static VBOXSTRICTRC PortCmdLstAddr_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1603{
     1604    RT_NOREF(pDevIns, pThis, iReg);
    15791605    ahciLog(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    15801606
     
    15901616 * Read from the global Version register.
    15911617 */
    1592 static int HbaVersion_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1593 {
    1594     RT_NOREF(iReg);
     1618static VBOXSTRICTRC HbaVersion_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1619{
     1620    RT_NOREF(pDevIns, iReg);
    15951621    Log(("%s: read regHbaVs=%#010x\n", __FUNCTION__, pThis->regHbaVs));
    15961622    *pu32Value = pThis->regHbaVs;
     
    16011627 * Read from the global Ports implemented register.
    16021628 */
    1603 static int HbaPortsImplemented_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1604 {
    1605     RT_NOREF(iReg);
     1629static VBOXSTRICTRC HbaPortsImplemented_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1630{
     1631    RT_NOREF(pDevIns, iReg);
    16061632    Log(("%s: read regHbaPi=%#010x\n", __FUNCTION__, pThis->regHbaPi));
    16071633    *pu32Value = pThis->regHbaPi;
     
    16121638 * Write to the global interrupt status register.
    16131639 */
    1614 static int HbaInterruptStatus_w(PAHCI pThis, uint32_t iReg, uint32_t u32Value)
     1640static VBOXSTRICTRC HbaInterruptStatus_w(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value)
    16151641{
    16161642    RT_NOREF(iReg);
    16171643    Log(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    16181644
    1619     int rc = PDMDevHlpCritSectEnter(pThis->CTX_SUFF(pDevIns), &pThis->lock, VINF_IOM_R3_MMIO_WRITE);
     1645    int rc = PDMDevHlpCritSectEnter(pDevIns, &pThis->lock, VINF_IOM_R3_MMIO_WRITE);
    16201646    if (rc != VINF_SUCCESS)
    16211647        return rc;
     
    16381664            if (u32Value & 0x01)
    16391665            {
    1640                 PAHCIPort pAhciPort = &pThis->ahciPort[i];
     1666                PAHCIPORT pAhciPort = &pThis->ahciPort[i];
    16411667
    16421668                if (pAhciPort->regIE & pAhciPort->regIS)
     
    16561682
    16571683    if (fClear)
    1658         ahciHbaClearInterrupt(pThis);
     1684        ahciHbaClearInterrupt(pDevIns);
    16591685    else
    16601686    {
     
    16651691         * We need to clear it first because the PCI bus only calls the interrupt controller if the state changes.
    16661692         */
    1667         PDMDevHlpPCISetIrq(pThis->CTX_SUFF(pDevIns), 0, 0);
    1668         PDMDevHlpPCISetIrq(pThis->CTX_SUFF(pDevIns), 0, 1);
    1669     }
    1670 
    1671     PDMDevHlpCritSectLeave(pThis->CTX_SUFF(pDevIns), &pThis->lock);
     1693        PDMDevHlpPCISetIrq(pDevIns, 0, 0);
     1694        PDMDevHlpPCISetIrq(pDevIns, 0, 1);
     1695    }
     1696
     1697    PDMDevHlpCritSectLeave(pDevIns, &pThis->lock);
    16721698    return VINF_SUCCESS;
    16731699}
     
    16761702 * Read from the global interrupt status register.
    16771703 */
    1678 static int HbaInterruptStatus_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1704static VBOXSTRICTRC HbaInterruptStatus_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    16791705{
    16801706    RT_NOREF(iReg);
    16811707
    1682     int rc = PDMDevHlpCritSectEnter(pThis->CTX_SUFF(pDevIns), &pThis->lock, VINF_IOM_R3_MMIO_READ);
     1708    int rc = PDMDevHlpCritSectEnter(pDevIns, &pThis->lock, VINF_IOM_R3_MMIO_READ);
    16831709    if (rc != VINF_SUCCESS)
    16841710        return rc;
     
    16861712    uint32_t u32PortsInterrupted = ASMAtomicXchgU32(&pThis->u32PortsInterrupted, 0);
    16871713
    1688     PDMDevHlpCritSectLeave(pThis->CTX_SUFF(pDevIns), &pThis->lock);
     1714    PDMDevHlpCritSectLeave(pDevIns, &pThis->lock);
    16891715    Log(("%s: read regHbaIs=%#010x u32PortsInterrupted=%#010x\n", __FUNCTION__, pThis->regHbaIs, u32PortsInterrupted));
    16901716
     
    16931719#ifdef LOG_ENABLED
    16941720    Log(("%s:", __FUNCTION__));
    1695     unsigned i;
    1696     for (i = 0; i < pThis->cPortsImpl; i++)
     1721    uint32_t const cPortsImpl = RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort));
     1722    for (unsigned i = 0; i < cPortsImpl; i++)
    16971723    {
    16981724        if ((pThis->regHbaIs >> i) & 0x01)
     
    17101736 * Write to the global control register.
    17111737 */
    1712 static int HbaControl_w(PAHCI pThis, uint32_t iReg, uint32_t u32Value)
    1713 {
    1714     RT_NOREF(iReg);
     1738static VBOXSTRICTRC HbaControl_w(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value)
     1739{
    17151740    Log(("%s: write u32Value=%#010x\n"
    17161741         "%s: AE=%d IE=%d HR=%d\n",
     
    17181743         __FUNCTION__, (u32Value & AHCI_HBA_CTRL_AE) >> 31, (u32Value & AHCI_HBA_CTRL_IE) >> 1,
    17191744         (u32Value & AHCI_HBA_CTRL_HR)));
     1745    RT_NOREF(iReg);
    17201746
    17211747#ifndef IN_RING3
    1722     RT_NOREF(pThis, u32Value);
     1748    RT_NOREF(pDevIns, pThis, u32Value);
    17231749    return VINF_IOM_R3_MMIO_WRITE;
    17241750#else
     
    17371763    if (   (u32Value & AHCI_HBA_CTRL_HR)
    17381764        && !cThreadsActive)
    1739         ahciHBAReset(pThis);
     1765        ahciR3HBAReset(pDevIns, pThis, PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC));
    17401766
    17411767    return VINF_SUCCESS;
     
    17461772 * Read the global control register.
    17471773 */
    1748 static int HbaControl_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1749 {
    1750     RT_NOREF(iReg);
     1774static VBOXSTRICTRC HbaControl_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1775{
     1776    RT_NOREF(pDevIns, iReg);
    17511777    Log(("%s: read regHbaCtrl=%#010x\n"
    17521778         "%s: AE=%d IE=%d HR=%d\n",
     
    17611787 * Read the global capabilities register.
    17621788 */
    1763 static int HbaCapabilities_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1764 {
    1765     RT_NOREF(iReg);
     1789static VBOXSTRICTRC HbaCapabilities_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1790{
     1791    RT_NOREF(pDevIns, iReg);
    17661792    Log(("%s: read regHbaCap=%#010x\n"
    17671793         "%s: S64A=%d SNCQ=%d SIS=%d SSS=%d SALP=%d SAL=%d SCLO=%d ISS=%d SNZO=%d SAM=%d SPM=%d PMD=%d SSC=%d PSC=%d NCS=%d NP=%d\n",
     
    17821808 * Write to the global command completion coalescing control register.
    17831809 */
    1784 static int HbaCccCtl_w(PAHCI pThis, uint32_t iReg, uint32_t u32Value)
     1810static VBOXSTRICTRC HbaCccCtl_w(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value)
    17851811{
    17861812    RT_NOREF(iReg);
     
    17971823
    17981824    if (u32Value & AHCI_HBA_CCC_CTL_EN)
    1799         PDMDevHlpTimerSetMillies(pThis->CTX_SUFF(pDevIns), pThis->hHbaCccTimer, pThis->uCccTimeout); /* Arm the timer */
     1825        PDMDevHlpTimerSetMillies(pDevIns, pThis->hHbaCccTimer, pThis->uCccTimeout); /* Arm the timer */
    18001826    else
    1801         PDMDevHlpTimerStop(pThis->CTX_SUFF(pDevIns), pThis->hHbaCccTimer);
     1827        PDMDevHlpTimerStop(pDevIns, pThis->hHbaCccTimer);
    18021828
    18031829    return VINF_SUCCESS;
     
    18071833 * Read the global command completion coalescing control register.
    18081834 */
    1809 static int HbaCccCtl_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1810 {
    1811     RT_NOREF(iReg);
     1835static VBOXSTRICTRC HbaCccCtl_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1836{
     1837    RT_NOREF(pDevIns, iReg);
    18121838    Log(("%s: read regHbaCccCtl=%#010x\n"
    18131839         "%s: TV=%d CC=%d INT=%d EN=%d\n",
     
    18221848 * Write to the global command completion coalescing ports register.
    18231849 */
    1824 static int HbaCccPorts_w(PAHCI pThis, uint32_t iReg, uint32_t u32Value)
    1825 {
    1826     RT_NOREF(iReg);
     1850static VBOXSTRICTRC HbaCccPorts_w(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value)
     1851{
     1852    RT_NOREF(pDevIns, iReg);
    18271853    Log(("%s: write u32Value=%#010x\n", __FUNCTION__, u32Value));
    18281854
     
    18351861 * Read the global command completion coalescing ports register.
    18361862 */
    1837 static int HbaCccPorts_r(PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
    1838 {
    1839     RT_NOREF(iReg);
     1863static VBOXSTRICTRC HbaCccPorts_r(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t *pu32Value)
     1864{
     1865    RT_NOREF(pDevIns, iReg);
    18401866    Log(("%s: read regHbaCccPorts=%#010x\n", __FUNCTION__, pThis->regHbaCccPorts));
    18411867
    18421868#ifdef LOG_ENABLED
    18431869    Log(("%s:", __FUNCTION__));
    1844     unsigned i;
    1845     for (i = 0; i < pThis->cPortsImpl; i++)
     1870    uint32_t const cPortsImpl = RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort));
     1871    for (unsigned i = 0; i < cPortsImpl; i++)
    18461872    {
    18471873        if ((pThis->regHbaCccPorts >> i) & 0x01)
     
    18581884 * Invalid write to global register
    18591885 */
    1860 static int HbaInvalid_w(PAHCI pThis, uint32_t iReg, uint32_t u32Value)
    1861 {
    1862     RT_NOREF(pThis, iReg, u32Value);
     1886static VBOXSTRICTRC HbaInvalid_w(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t iReg, uint32_t u32Value)
     1887{
     1888    RT_NOREF(pDevIns, pThis, iReg, u32Value);
    18631889    Log(("%s: Write denied!!! iReg=%u u32Value=%#010x\n", __FUNCTION__, iReg, u32Value));
    18641890    return VINF_SUCCESS;
     
    18681894 * Invalid Port write.
    18691895 */
    1870 static int PortInvalid_w(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t u32Value)
    1871 {
    1872     RT_NOREF(pThis, pAhciPort, iReg, u32Value);
     1896static VBOXSTRICTRC PortInvalid_w(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t u32Value)
     1897{
     1898    RT_NOREF(pDevIns, pThis, pAhciPort, iReg, u32Value);
    18731899    ahciLog(("%s: Write denied!!! iReg=%u u32Value=%#010x\n", __FUNCTION__, iReg, u32Value));
    18741900    return VINF_SUCCESS;
     
    18781904 * Invalid Port read.
    18791905 */
    1880 static int PortInvalid_r(PAHCI pThis, PAHCIPort pAhciPort, uint32_t iReg, uint32_t *pu32Value)
    1881 {
    1882     RT_NOREF(pThis, pAhciPort, iReg, pu32Value);
     1906static VBOXSTRICTRC PortInvalid_r(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t iReg, uint32_t *pu32Value)
     1907{
     1908    RT_NOREF(pDevIns, pThis, pAhciPort, iReg, pu32Value);
    18831909    ahciLog(("%s: Read denied!!! iReg=%u\n", __FUNCTION__, iReg));
    18841910    return VINF_SUCCESS;
     
    19231949
    19241950#ifdef IN_RING3
     1951
    19251952/**
    19261953 * Reset initiated by system software for one port.
    19271954 *
    1928  * @param pAhciPort     The port to reset.
    1929  */
    1930 static void ahciPortSwReset(PAHCIPort pAhciPort)
     1955 * @param   pAhciPort       The port to reset, shared bits.
     1956 * @param   pAhciPortR3     The port to reset, ring-3 bits.
     1957 */
     1958static void ahciR3PortSwReset(PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3)
    19311959{
    19321960    bool fAllTasksCanceled;
    19331961
    19341962    /* Cancel all tasks first. */
    1935     fAllTasksCanceled = ahciCancelActiveTasks(pAhciPort);
     1963    fAllTasksCanceled = ahciR3CancelActiveTasks(pAhciPortR3);
    19361964    Assert(fAllTasksCanceled);
    19371965
     
    19681996    pAhciPort->u32CurrentCommandSlot = 0;
    19691997
    1970     if (pAhciPort->pDrvBase)
     1998    if (pAhciPort->fPresent)
    19711999    {
    19722000        pAhciPort->regCMD |= AHCI_PORT_CMD_CPS; /* Indicate that there is a device on that port */
     
    19932021 * @param pAhciPort     The port to reset.
    19942022 */
    1995 static void ahciPortHwReset(PAHCIPort pAhciPort)
     2023static void ahciPortHwReset(PAHCIPORT pAhciPort)
    19962024{
    19972025    /* Reset the address registers. */
     
    20252053 * Reset the entire HBA.
    20262054 *
    2027  * @param   pThis       The HBA state.
    2028  */
    2029 static void ahciHBAReset(PAHCI pThis)
     2055 * @param   pDevIns     The device instance.
     2056 * @param   pThis       The shared AHCI state.
     2057 * @param   pThisCC     The ring-3 AHCI state.
     2058 */
     2059static void ahciR3HBAReset(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIR3 pThisCC)
    20302060{
    20312061    unsigned i;
    20322062    int rc = VINF_SUCCESS;
    20332063
    2034     LogRel(("AHCI#%u: Reset the HBA\n", pThis->CTX_SUFF(pDevIns)->iInstance));
     2064    LogRel(("AHCI#%u: Reset the HBA\n", pDevIns->iInstance));
    20352065
    20362066    /* Stop the CCC timer. */
    20372067    if (pThis->regHbaCccCtl & AHCI_HBA_CCC_CTL_EN)
    20382068    {
    2039         rc = PDMDevHlpTimerStop(pThis->CTX_SUFF(pDevIns), pThis->hHbaCccTimer);
     2069        rc = PDMDevHlpTimerStop(pDevIns, pThis->hHbaCccTimer);
    20402070        if (RT_FAILURE(rc))
    20412071            AssertMsgFailed(("%s: Failed to stop timer!\n", __FUNCTION__));
     
    20432073
    20442074    /* Reset every port */
    2045     for (i = 0; i < pThis->cPortsImpl; i++)
    2046     {
    2047         PAHCIPort pAhciPort = &pThis->ahciPort[i];
    2048 
    2049         pAhciPort->iLUN = i;
    2050         ahciPortSwReset(pAhciPort);
     2075    uint32_t const cPortsImpl = RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThisCC->aPorts));
     2076    for (i = 0; i < cPortsImpl; i++)
     2077    {
     2078        PAHCIPORT   pAhciPort   = &pThis->ahciPort[i];
     2079        PAHCIPORTR3 pAhciPortR3 = &pThisCC->aPorts[i];
     2080
     2081        pAhciPort->iLUN   = i;
     2082        pAhciPortR3->iLUN = i;
     2083        ahciR3PortSwReset(pAhciPort, pAhciPortR3);
    20512084    }
    20522085
    20532086    /* Init Global registers */
    2054     pThis->regHbaCap      = AHCI_HBA_CAP_ISS_SHIFT(AHCI_HBA_CAP_ISS_GEN2) |
    2055                             AHCI_HBA_CAP_S64A | /* 64bit addressing supported */
    2056                             AHCI_HBA_CAP_SAM  | /* AHCI mode only */
    2057                             AHCI_HBA_CAP_SNCQ | /* Support native command queuing */
    2058                             AHCI_HBA_CAP_SSS  | /* Staggered spin up */
    2059                             AHCI_HBA_CAP_CCCS | /* Support command completion coalescing */
    2060                             AHCI_HBA_CAP_NCS_SET(pThis->cCmdSlotsAvail) | /* Number of command slots we support */
    2061                             AHCI_HBA_CAP_NP_SET(pThis->cPortsImpl); /* Number of supported ports */
     2087    pThis->regHbaCap      = AHCI_HBA_CAP_ISS_SHIFT(AHCI_HBA_CAP_ISS_GEN2)
     2088                          | AHCI_HBA_CAP_S64A /* 64bit addressing supported */
     2089                          | AHCI_HBA_CAP_SAM /* AHCI mode only */
     2090                          | AHCI_HBA_CAP_SNCQ /* Support native command queuing */
     2091                          | AHCI_HBA_CAP_SSS /* Staggered spin up */
     2092                          | AHCI_HBA_CAP_CCCS /* Support command completion coalescing */
     2093                          | AHCI_HBA_CAP_NCS_SET(pThis->cCmdSlotsAvail) /* Number of command slots we support */
     2094                          | AHCI_HBA_CAP_NP_SET(pThis->cPortsImpl); /* Number of supported ports */
    20622095    pThis->regHbaCtrl     = AHCI_HBA_CTRL_AE;
    20632096    pThis->regHbaPi       = ahciGetPortsImplemented(pThis->cPortsImpl);
     
    20722105    pThis->regHbaIs            = 0;
    20732106    pThis->u32PortsInterrupted = 0;
    2074     ahciHbaClearInterrupt(pThis);
     2107    ahciHbaClearInterrupt(pDevIns);
    20752108
    20762109    pThis->f64BitAddr = false;
     
    20802113    pThis->regHbaCtrl &= ~AHCI_HBA_CTRL_HR;
    20812114}
    2082 #endif
     2115
     2116#endif /* IN_RING3 */
    20832117
    20842118/**
    20852119 * Reads from a AHCI controller register.
    20862120 *
    2087  * @returns VBox status code.
    2088  *
    2089  * @param   pThis       The AHCI instance.
     2121 * @returns Strict VBox status code.
     2122 *
     2123 * @param   pDevIns     The device instance.
     2124 * @param   pThis       The shared AHCI state.
    20902125 * @param   uReg        The register to write.
    20912126 * @param   pv          Where to store the result.
    20922127 * @param   cb          Number of bytes read.
    20932128 */
    2094 static int ahciRegisterRead(PAHCI pThis, uint32_t uReg, void *pv, unsigned cb)
    2095 {
    2096     int rc = VINF_SUCCESS;
     2129static VBOXSTRICTRC ahciRegisterRead(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t uReg, void *pv, unsigned cb)
     2130{
     2131    VBOXSTRICTRC rc;
    20972132    uint32_t iReg;
    20982133
     
    21082143        {
    21092144            const AHCIOPREG *pReg = &g_aOpRegs[iReg];
    2110             rc = pReg->pfnRead(pThis, iReg, (uint32_t *)pv);
     2145            rc = pReg->pfnRead(pDevIns, pThis, iReg, (uint32_t *)pv);
    21112146        }
    21122147        else
     
    21142149            Log3(("%s: Trying to read global register %u/%u!!!\n", __FUNCTION__, iReg, RT_ELEMENTS(g_aOpRegs)));
    21152150            *(uint32_t *)pv = 0;
     2151            rc = VINF_SUCCESS;
    21162152        }
    21172153    }
     
    21292165        Log3(("%s: Trying to read from port %u and register %u\n", __FUNCTION__, iPort, iReg));
    21302166
    2131         if (RT_LIKELY(   iPort < pThis->cPortsImpl
     2167        if (RT_LIKELY(   iPort < RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort))
    21322168                      && iReg < RT_ELEMENTS(g_aPortOpRegs)))
    21332169        {
    21342170            const AHCIPORTOPREG *pPortReg = &g_aPortOpRegs[iReg];
    2135             rc = pPortReg->pfnRead(pThis, &pThis->ahciPort[iPort], iReg, (uint32_t *)pv);
     2171            rc = pPortReg->pfnRead(pDevIns, pThis, &pThis->ahciPort[iPort], iReg, (uint32_t *)pv);
    21362172        }
    21372173        else
     
    21632199                }
    21642200                default:
    2165                     AssertMsgFailed(("%s: unsupported access width cb=%d iPort=%x iRegOffset=%x iReg=%x!!!\n",
    2166                                      __FUNCTION__, cb, iPort, iRegOffset, iReg));
     2201                    ASSERT_GUEST_MSG_FAILED(("%s: unsupported access width cb=%d iPort=%x iRegOffset=%x iReg=%x!!!\n",
     2202                                             __FUNCTION__, cb, iPort, iRegOffset, iReg));
    21672203            }
    21682204        }
     
    21752211 * Writes a value to one of the AHCI controller registers.
    21762212 *
    2177  * @returns VBox status code.
    2178  *
    2179  * @param   pThis       The AHCI instance.
     2213 * @returns Strict VBox status code.
     2214 *
     2215 * @param   pDevIns     The device instance.
     2216 * @param   pThis       The shared AHCI state.
    21802217 * @param   offReg      The offset of the register to write to.
    21812218 * @param   u32Value    The value to write.
    21822219 */
    2183 static int ahciRegisterWrite(PAHCI pThis, uint32_t offReg, uint32_t u32Value)
    2184 {
    2185     int rc;
     2220static VBOXSTRICTRC ahciRegisterWrite(PPDMDEVINS pDevIns, PAHCI pThis, uint32_t offReg, uint32_t u32Value)
     2221{
     2222    VBOXSTRICTRC rc;
    21862223    uint32_t iReg;
    21872224
     
    21972234        {
    21982235            const AHCIOPREG *pReg = &g_aOpRegs[iReg];
    2199             rc = pReg->pfnWrite(pThis, iReg, u32Value);
     2236            rc = pReg->pfnWrite(pDevIns, pThis, iReg, u32Value);
    22002237        }
    22012238        else
     
    22142251        iReg    = (offReg % AHCI_PORT_REGISTER_SIZE) >> 2;
    22152252        Log3(("%s: Trying to write to port %u and register %u\n", __FUNCTION__, iPort, iReg));
    2216         if (RT_LIKELY(   iPort < pThis->cPortsImpl
     2253        if (RT_LIKELY(   iPort < RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort))
    22172254                      && iReg < RT_ELEMENTS(g_aPortOpRegs)))
    22182255        {
    22192256            const AHCIPORTOPREG *pPortReg = &g_aPortOpRegs[iReg];
    2220             rc = pPortReg->pfnWrite(pThis, &pThis->ahciPort[iPort], iReg, u32Value);
     2257            rc = pPortReg->pfnWrite(pDevIns, pThis, &pThis->ahciPort[iPort], iReg, u32Value);
    22212258        }
    22222259        else
     
    22402277    RT_NOREF(pvUser);
    22412278
    2242     VBOXSTRICTRC rc = ahciRegisterRead(pThis, off, pv, cb);
     2279    VBOXSTRICTRC rc = ahciRegisterRead(pDevIns, pThis, off, pv, cb);
    22432280
    22442281    Log2(("#%d ahciMMIORead: return pvUser=%p:{%.*Rhxs} cb=%d off=%RGp rc=%Rrc\n",
     
    22922329    /* Do the access. */
    22932330    Log2(("#%d ahciMMIOWrite: pvUser=%p:{%.*Rhxs} cb=%d GCPhysAddr=%RGp\n", pDevIns->iInstance, pv, cb, pv, cb, off));
    2294     return ahciRegisterWrite(pThis, off, *(uint32_t const *)pv);
     2331    return ahciRegisterWrite(pDevIns, pThis, off, *(uint32_t const *)pv);
    22952332}
    22962333
     
    23462383            /** @todo range check? */
    23472384            ASSERT_GUEST(iReg == 1);
    2348             rc = ahciRegisterWrite(pThis, pThis->regIdx, u32);
     2385            rc = ahciRegisterWrite(pDevIns, pThis, pThis->regIdx, u32);
    23492386            if (rc == VINF_IOM_R3_MMIO_WRITE)
    23502387                rc = VINF_IOM_R3_IOPORT_WRITE;
     
    23822419            /** @todo range check? */
    23832420            ASSERT_GUEST(iReg == 1);
    2384             rc = ahciRegisterRead(pThis, pThis->regIdx, pu32, cb);
     2421            rc = ahciRegisterRead(pDevIns, pThis, pThis->regIdx, pu32, cb);
    23852422            if (rc == VINF_IOM_R3_MMIO_READ)
    23862423                rc = VINF_IOM_R3_IOPORT_READ;
     
    24112448static DECLCALLBACK(int) ahciR3Status_QueryStatusLed(PPDMILEDPORTS pInterface, unsigned iLUN, PPDMLED *ppLed)
    24122449{
    2413     PAHCI pThis = PDMILEDPORTS_2_PAHCI(pInterface);
     2450    PAHCICC pThisCC = RT_FROM_MEMBER(pInterface, AHCICC, ILeds);
    24142451    if (iLUN < AHCI_MAX_NR_PORTS_IMPL)
    24152452    {
     2453        PAHCI pThis = PDMDEVINS_2_DATA(pThisCC->pDevIns, PAHCI);
    24162454        *ppLed = &pThis->ahciPort[iLUN].Led;
    24172455        Assert((*ppLed)->u32Magic == PDMLED_MAGIC);
     
    24262464static DECLCALLBACK(void *) ahciR3Status_QueryInterface(PPDMIBASE pInterface, const char *pszIID)
    24272465{
    2428     PAHCI pThis = PDMIBASE_2_PAHCI(pInterface);
    2429     PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pThis->IBase);
    2430     PDMIBASE_RETURN_INTERFACE(pszIID, PDMILEDPORTS, &pThis->ILeds);
     2466    PAHCICC pThisCC = RT_FROM_MEMBER(pInterface, AHCICC, IBase);
     2467    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pThisCC->IBase);
     2468    PDMIBASE_RETURN_INTERFACE(pszIID, PDMILEDPORTS, &pThisCC->ILeds);
    24312469    return NULL;
    24322470}
     
    24372475static DECLCALLBACK(void *) ahciR3PortQueryInterface(PPDMIBASE pInterface, const char *pszIID)
    24382476{
    2439     PAHCIPort pAhciPort = PDMIBASE_2_PAHCIPORT(pInterface);
    2440     PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pAhciPort->IBase);
    2441     PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMEDIAPORT, &pAhciPort->IPort);
    2442     PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMEDIAEXPORT, &pAhciPort->IMediaExPort);
     2477    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IBase);
     2478    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIBASE, &pAhciPortR3->IBase);
     2479    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMEDIAPORT, &pAhciPortR3->IPort);
     2480    PDMIBASE_RETURN_INTERFACE(pszIID, PDMIMEDIAEXPORT, &pAhciPortR3->IMediaExPort);
    24432481    return NULL;
    24442482}
     
    24502488                                                       uint32_t *piInstance, uint32_t *piLUN)
    24512489{
    2452     PAHCIPort pAhciPort = PDMIMEDIAPORT_2_PAHCIPORT(pInterface);
    2453     PPDMDEVINS pDevIns = pAhciPort->CTX_SUFF(pDevIns);
     2490    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IPort);
     2491    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
    24542492
    24552493    AssertPtrReturn(ppcszController, VERR_INVALID_POINTER);
     
    24592497    *ppcszController = pDevIns->pReg->szName;
    24602498    *piInstance = pDevIns->iInstance;
    2461     *piLUN = pAhciPort->iLUN;
     2499    *piLUN = pAhciPortR3->iLUN;
    24622500
    24632501    return VINF_SUCCESS;
     
    24702508                                                       const char **ppszProductId, const char **ppszRevision)
    24712509{
    2472     PAHCIPort pAhciPort = PDMIMEDIAPORT_2_PAHCIPORT(pInterface);
     2510    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IPort);
     2511    PAHCI       pThis       = PDMDEVINS_2_DATA(pAhciPortR3->pDevIns, PAHCI);
     2512    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
    24732513
    24742514    if (ppszVendorId)
     
    24902530 * @param   cmdFis        The FIS to print info from.
    24912531 */
    2492 static void ahciDumpFisInfo(PAHCIPort pAhciPort, uint8_t *cmdFis)
     2532static void ahciDumpFisInfo(PAHCIPORT pAhciPort, uint8_t *cmdFis)
    24932533{
    24942534    ahciLog(("%s: *** Begin FIS info dump. ***\n", __FUNCTION__));
     
    25722612 * @param   pCmdHdr     The command header to print info from.
    25732613 */
    2574 static void ahciDumpCmdHdrInfo(PAHCIPort pAhciPort, CmdHdr *pCmdHdr)
     2614static void ahciDumpCmdHdrInfo(PAHCIPORT pAhciPort, CmdHdr *pCmdHdr)
    25752615{
    25762616    ahciLog(("%s: *** Begin command header info dump. ***\n", __FUNCTION__));
     
    26032643 *
    26042644 * @returns nothing
    2605  * @param   pAhciPort    Pointer to the port which "receives" the FIS.
    2606  */
    2607 static void ahciPostFirstD2HFisIntoMemory(PAHCIPort pAhciPort)
     2645 * @param   pDevIns     The device instance.
     2646 * @param   pAhciPort   Pointer to the port which "receives" the FIS.
     2647 */
     2648static void ahciPostFirstD2HFisIntoMemory(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort)
    26082649{
    26092650    uint8_t d2hFis[AHCI_CMDFIS_TYPE_D2H_SIZE];
     
    26382679        pAhciPort->regTFD |= ATA_STAT_READY;
    26392680
    2640     ahciPostFisIntoMemory(pAhciPort, AHCI_CMDFIS_TYPE_D2H, d2hFis);
     2681    ahciPostFisIntoMemory(pDevIns, pAhciPort, AHCI_CMDFIS_TYPE_D2H, d2hFis);
    26412682}
    26422683
     
    26452686 *
    26462687 * @returns VBox status code
     2688 * @param   pDevIns     The device instance.
    26472689 * @param   pAhciPort  The port which "receives" the FIS.
    26482690 * @param   uFisType   The type of the FIS.
    26492691 * @param   pCmdFis    Pointer to the FIS which is to be posted into memory.
    26502692 */
    2651 static int ahciPostFisIntoMemory(PAHCIPort pAhciPort, unsigned uFisType, uint8_t *pCmdFis)
     2693static int ahciPostFisIntoMemory(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort, unsigned uFisType, uint8_t *pCmdFis)
    26522694{
    26532695    int         rc = VINF_SUCCESS;
     
    26982740        /* Post the FIS into memory. */
    26992741        ahciLog(("%s: PDMDevHlpPCIPhysWrite GCPhysAddrRecFis=%RGp cbFis=%u\n", __FUNCTION__, GCPhysAddrRecFis, cbFis));
    2700         PDMDevHlpPCIPhysWrite(pAhciPort->CTX_SUFF(pDevIns), GCPhysAddrRecFis, pCmdFis, cbFis);
     2742        PDMDevHlpPCIPhysWrite(pDevIns, GCPhysAddrRecFis, pCmdFis, cbFis);
    27012743    }
    27022744
     
    27342776}
    27352777
    2736 static int ahciIdentifySS(PAHCIPort pAhciPort, void *pvBuf)
     2778static int ahciIdentifySS(PAHCI pThis, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3, void *pvBuf)
    27372779{
    27382780    uint16_t *p = (uint16_t *)pvBuf;
     
    27852827    if (   pAhciPort->fTrimEnabled
    27862828        || pAhciPort->cbSector != 512
    2787         || pAhciPort->pDrvMedia->pfnIsNonRotational(pAhciPort->pDrvMedia))
     2829        || pAhciPortR3->pDrvMedia->pfnIsNonRotational(pAhciPortR3->pDrvMedia))
    27882830    {
    27892831        p[80] = RT_H2LE_U16(0x1f0); /* support everything up to ATA/ATAPI-8 ACS */
     
    28212863    }
    28222864
    2823     if (pAhciPort->pDrvMedia->pfnIsNonRotational(pAhciPort->pDrvMedia))
     2865    if (pAhciPortR3->pDrvMedia->pfnIsNonRotational(pAhciPortR3->pDrvMedia))
    28242866        p[217] = RT_H2LE_U16(1); /* Non-rotational medium */
    28252867
     
    28282870
    28292871    /* The following are SATA specific */
    2830     p[75] = RT_H2LE_U16(pAhciPort->CTX_SUFF(pAhci)->cCmdSlotsAvail-1); /* Number of commands we support, 0's based */
     2872    p[75] = RT_H2LE_U16(pThis->cCmdSlotsAvail - 1); /* Number of commands we support, 0's based */
    28312873    p[76] = RT_H2LE_U16((1 << 8) | (1 << 2)); /* Native command queuing and Serial ATA Gen2 (3.0 Gbps) speed supported */
    28322874
     
    28372879}
    28382880
    2839 static int ahciR3AtapiIdentify(PAHCIREQ pAhciReq, PAHCIPort pAhciPort, size_t cbData, size_t *pcbData)
     2881static int ahciR3AtapiIdentify(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, PAHCIPORT pAhciPort, size_t cbData, size_t *pcbData)
    28402882{
    28412883    uint16_t p[256];
     
    28782920
    28792921    /* Copy the buffer in to the scatter gather list. */
    2880     *pcbData = ahciR3CopyBufferToPrdtl(pAhciPort->CTX_SUFF(pAhci), pAhciReq, (void *)&p[0],
    2881                                        RT_MIN(cbData, sizeof(p)), 0 /* cbSkip */);
     2922    *pcbData = ahciR3CopyBufferToPrdtl(pDevIns, pAhciReq, (void *)&p[0], RT_MIN(cbData, sizeof(p)), 0 /* cbSkip */);
    28822923    return VINF_SUCCESS;
    28832924}
     
    28872928 *
    28882929 * @returns nothing
    2889  * @param pAhciPort             The port the device is attached to.
    2890  * @param pAhciReq    The state to get the tag number from.
    2891  */
    2892 static void ahciFinishStorageDeviceReset(PAHCIPort pAhciPort, PAHCIREQ pAhciReq)
     2930 * @param   pDevIns     The device instance.
     2931 * @param   pThis       The shared AHCI state.
     2932 * @param   pAhciPort   The port the device is attached to, shared bits.
     2933 * @param   pAhciReq    The state to get the tag number from.
     2934 */
     2935static void ahciFinishStorageDeviceReset(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIREQ pAhciReq)
    28932936{
    28942937    int rc;
     
    28972940    pAhciPort->fResetDevice = false;
    28982941    if (pAhciPort->regCMD & AHCI_PORT_CMD_FRE)
    2899         ahciPostFirstD2HFisIntoMemory(pAhciPort);
     2942        ahciPostFirstD2HFisIntoMemory(pDevIns, pAhciPort);
    29002943
    29012944    /* As this is the first D2H FIS after the reset update the signature in the SIG register of the port. */
     
    29062949    ASMAtomicOrU32(&pAhciPort->u32TasksFinished, (1 << pAhciReq->uTag));
    29072950
    2908     rc = ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     2951    rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    29092952    AssertRC(rc);
    29102953}
     
    29142957 *
    29152958 * @returns nothing.
    2916  * @param   pAhciPort          The device to reset.
    2917  * @param   pAhciReq The task state.
    2918  */
    2919 static void ahciDeviceReset(PAHCIPort pAhciPort, PAHCIREQ pAhciReq)
     2959 * @param   pDevIns     The device instance.
     2960 * @param   pThis       The shared AHCI state.
     2961 * @param   pAhciPort   The device to reset.
     2962 * @param   pAhciReq    The task state.
     2963 */
     2964static void ahciDeviceReset(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIREQ pAhciReq)
    29202965{
    29212966    ASMAtomicWriteBool(&pAhciPort->fResetDevice, true);
     
    29272972     */
    29282973    Assert(ASMAtomicReadU32(&pAhciPort->cTasksActive) == 0);
    2929     ahciFinishStorageDeviceReset(pAhciPort, pAhciReq);
     2974    ahciFinishStorageDeviceReset(pDevIns, pThis, pAhciPort, pAhciReq);
    29302975}
    29312976
     
    29342979 *
    29352980 * @returns nothing.
    2936  * @param   pAhciPort          The port of the SATA controller.
    2937  * @param   cbTransfer         Transfer size of the request.
    2938  * @param   pCmdFis            Pointer to the command FIS from the guest.
    2939  * @param   fRead              Flag whether this is a read request.
    2940  * @param   fInterrupt         If an interrupt should be send to the guest.
    2941  */
    2942 static void ahciSendPioSetupFis(PAHCIPort pAhciPort, size_t cbTransfer, uint8_t *pCmdFis,
    2943                                 bool fRead, bool fInterrupt)
     2981 * @param   pDevIns     The device instance.
     2982 * @param   pThis       The shared AHCI state.
     2983 * @param   pAhciPort   The port of the SATA controller.
     2984 * @param   cbTransfer  Transfer size of the request.
     2985 * @param   pCmdFis     Pointer to the command FIS from the guest.
     2986 * @param   fRead       Flag whether this is a read request.
     2987 * @param   fInterrupt  If an interrupt should be send to the guest.
     2988 */
     2989static void ahciSendPioSetupFis(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort,
     2990                                size_t cbTransfer, uint8_t *pCmdFis, bool fRead, bool fInterrupt)
    29442991{
    29452992    uint8_t abPioSetupFis[20];
    29462993    bool fAssertIntr = false;
    2947     PAHCI pThis = pAhciPort->CTX_SUFF(pAhci);
    29482994
    29492995    ahciLog(("%s: building PIO setup Fis\n", __FUNCTION__));
     
    29793025        pAhciPort->regTFD = (pCmdFis[AHCI_CMDFIS_ERR] << 8) | pCmdFis[AHCI_CMDFIS_STS];
    29803026
    2981         ahciPostFisIntoMemory(pAhciPort, AHCI_CMDFIS_TYPE_PIOSETUP, abPioSetupFis);
     3027        ahciPostFisIntoMemory(pDevIns, pAhciPort, AHCI_CMDFIS_TYPE_PIOSETUP, abPioSetupFis);
    29823028
    29833029        if (fInterrupt)
     
    29913037        if (fAssertIntr)
    29923038        {
    2993             int rc = ahciHbaSetInterrupt(pThis, pAhciPort->iLUN, VERR_IGNORED);
     3039            int rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    29943040            AssertRC(rc);
    29953041        }
     
    30013047 *
    30023048 * @returns Nothing
    3003  * @param   pAhciPort          The port of the SATA controller.
    3004  * @param   uTag               The tag of the request.
    3005  * @param   pCmdFis            Pointer to the command FIS from the guest.
    3006  * @param   fInterrupt         If an interrupt should be send to the guest.
    3007  */
    3008 static void ahciSendD2HFis(PAHCIPort pAhciPort, uint32_t uTag, uint8_t *pCmdFis, bool fInterrupt)
     3049 * @param   pDevIns     The device instance.
     3050 * @param   pThis       The shared AHCI state.
     3051 * @param   pAhciPort   The port of the SATA controller.
     3052 * @param   uTag        The tag of the request.
     3053 * @param   pCmdFis     Pointer to the command FIS from the guest.
     3054 * @param   fInterrupt  If an interrupt should be send to the guest.
     3055 */
     3056static void ahciSendD2HFis(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, uint32_t uTag, uint8_t *pCmdFis, bool fInterrupt)
    30093057{
    30103058    uint8_t d2hFis[20];
    30113059    bool fAssertIntr = false;
    3012     PAHCI pThis = pAhciPort->CTX_SUFF(pAhci);
    30133060
    30143061    ahciLog(("%s: building D2H Fis\n", __FUNCTION__));
     
    30343081        pAhciPort->regTFD = (pCmdFis[AHCI_CMDFIS_ERR] << 8) | pCmdFis[AHCI_CMDFIS_STS];
    30353082
    3036         ahciPostFisIntoMemory(pAhciPort, AHCI_CMDFIS_TYPE_D2H, d2hFis);
     3083        ahciPostFisIntoMemory(pDevIns, pAhciPort, AHCI_CMDFIS_TYPE_D2H, d2hFis);
    30373084
    30383085        if (pCmdFis[AHCI_CMDFIS_STS] & ATA_STAT_ERR)
     
    30603107        if (fAssertIntr)
    30613108        {
    3062             int rc = ahciHbaSetInterrupt(pThis, pAhciPort->iLUN, VERR_IGNORED);
     3109            int rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    30633110            AssertRC(rc);
    30643111        }
     
    30703117 *
    30713118 * @returns Nothing
    3072  * @param   pAhciPort           The port for which the SDB Fis is send.
    3073  * @param   uFinishedTasks      Bitmask of finished tasks.
    3074  * @param   fInterrupt          If an interrupt should be asserted.
    3075  */
    3076 static void ahciSendSDBFis(PAHCIPort pAhciPort, uint32_t uFinishedTasks, bool fInterrupt)
     3119 * @param   pDevIns         The device instance.
     3120 * @param   pThis           The shared AHCI state.
     3121 * @param   pAhciPort       The port for which the SDB Fis is send, shared bits.
     3122 * @param   pAhciPortR3     The port for which the SDB Fis is send, ring-3 bits.
     3123 * @param   uFinishedTasks  Bitmask of finished tasks.
     3124 * @param   fInterrupt      If an interrupt should be asserted.
     3125 */
     3126static void ahciSendSDBFis(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3,
     3127                           uint32_t uFinishedTasks, bool fInterrupt)
    30773128{
    30783129    uint32_t sdbFis[2];
    30793130    bool fAssertIntr = false;
    3080     PAHCI pThis = pAhciPort->CTX_SUFF(pAhci);
    3081     PAHCIREQ pTaskErr = ASMAtomicReadPtrT(&pAhciPort->pTaskErr, PAHCIREQ);
     3131    PAHCIREQ pTaskErr = ASMAtomicReadPtrT(&pAhciPortR3->pTaskErr, PAHCIREQ);
    30823132
    30833133    ahciLog(("%s: Building SDB FIS\n", __FUNCTION__));
     
    31053155        sdbFis[1] = pAhciPort->u32QueuedTasksFinished | uFinishedTasks;
    31063156
    3107         ahciPostFisIntoMemory(pAhciPort, AHCI_CMDFIS_TYPE_SETDEVBITS, (uint8_t *)sdbFis);
     3157        ahciPostFisIntoMemory(pDevIns, pAhciPort, AHCI_CMDFIS_TYPE_SETDEVBITS, (uint8_t *)sdbFis);
    31083158
    31093159        if (RT_UNLIKELY(pTaskErr))
     
    31273177        if (fAssertIntr)
    31283178        {
    3129             int rc = ahciHbaSetInterrupt(pThis, pAhciPort->iLUN, VERR_IGNORED);
     3179            int rc = ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    31303180            AssertRC(rc);
    31313181        }
     
    31523202}
    31533203
    3154 static uint64_t ahciGetSector(PAHCIPort pAhciPort, uint8_t *pCmdFis, bool fLBA48)
     3204static uint64_t ahciGetSector(PAHCIPORT pAhciPort, uint8_t *pCmdFis, bool fLBA48)
    31553205{
    31563206    uint64_t iLBA;
     
    32123262 * @copydoc AHCIR3MEMCOPYCALLBACK
    32133263 */
    3214 static DECLCALLBACK(void) ahciR3CopyBufferFromGuestWorker(PAHCI pThis, RTGCPHYS GCPhys, PRTSGBUF pSgBuf,
     3264static DECLCALLBACK(void) ahciR3CopyBufferFromGuestWorker(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, PRTSGBUF pSgBuf,
    32153265                                                          size_t cbCopy, size_t *pcbSkip)
    32163266{
     
    32263276
    32273277        AssertPtr(pvSeg);
    3228         PDMDevHlpPhysRead(pThis->CTX_SUFF(pDevIns), GCPhys, pvSeg, cbSeg);
     3278        PDMDevHlpPhysRead(pDevIns, GCPhys, pvSeg, cbSeg);
    32293279        GCPhys += cbSeg;
    32303280        cbCopy -= cbSeg;
     
    32373287 * @copydoc AHCIR3MEMCOPYCALLBACK
    32383288 */
    3239 static DECLCALLBACK(void) ahciR3CopyBufferToGuestWorker(PAHCI pThis, RTGCPHYS GCPhys, PRTSGBUF pSgBuf,
     3289static DECLCALLBACK(void) ahciR3CopyBufferToGuestWorker(PPDMDEVINS pDevIns, RTGCPHYS GCPhys, PRTSGBUF pSgBuf,
    32403290                                                        size_t cbCopy, size_t *pcbSkip)
    32413291{
     
    32513301
    32523302        AssertPtr(pvSeg);
    3253         PDMDevHlpPCIPhysWrite(pThis->CTX_SUFF(pDevIns), GCPhys, pvSeg, cbSeg);
     3303        PDMDevHlpPCIPhysWrite(pDevIns, GCPhys, pvSeg, cbSeg);
    32543304        GCPhys += cbSeg;
    32553305        cbCopy -= cbSeg;
     
    32613311 *
    32623312 * @returns Amount of bytes copied.
    3263  * @param   pThis          The AHCI controller device instance.
    3264  * @param   pAhciReq       AHCI request structure.
    3265  * @param   pfnCopyWorker  The copy method to apply for each guest buffer.
    3266  * @param   pSgBuf         The host S/G buffer.
    3267  * @param   cbSkip         How many bytes to skip in advance before starting to copy.
    3268  * @param   cbCopy         How many bytes to copy.
    3269  */
    3270 static size_t ahciR3PrdtlWalk(PAHCI pThis, PAHCIREQ pAhciReq,
     3313 * @param   pDevIns         The device instance.
     3314 * @param   pAhciReq        AHCI request structure.
     3315 * @param   pfnCopyWorker   The copy method to apply for each guest buffer.
     3316 * @param   pSgBuf          The host S/G buffer.
     3317 * @param   cbSkip          How many bytes to skip in advance before starting to copy.
     3318 * @param   cbCopy          How many bytes to copy.
     3319 */
     3320static size_t ahciR3PrdtlWalk(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq,
    32713321                              PAHCIR3MEMCOPYCALLBACK pfnCopyWorker,
    32723322                              PRTSGBUF pSgBuf, size_t cbSkip, size_t cbCopy)
     
    32913341                                   : RT_ELEMENTS(aPrdtlEntries);
    32923342
    3293         PDMDevHlpPhysRead(pThis->CTX_SUFF(pDevIns), GCPhysPrdtl, &aPrdtlEntries[0],
     3343        PDMDevHlpPhysRead(pDevIns, GCPhysPrdtl, &aPrdtlEntries[0],
    32943344                          cPrdtlEntriesRead * sizeof(SGLEntry));
    32953345
     
    33023352
    33033353            /* Copy into SG entry. */
    3304             pfnCopyWorker(pThis, GCPhysAddrDataBase, pSgBuf, cbThisCopy, &cbSkip);
     3354            pfnCopyWorker(pDevIns, GCPhysAddrDataBase, pSgBuf, cbThisCopy, &cbSkip);
    33053355
    33063356            cbCopy   -= cbThisCopy;
     
    33223372 *
    33233373 * @returns Amount of bytes copied to the PRDTL.
    3324  * @param   pThis          The AHCI controller device instance.
    3325  * @param   pAhciReq       AHCI request structure.
    3326  * @param   pSgBuf         The S/G buffer to copy from.
    3327  * @param   cbSkip         How many bytes to skip in advance before starting to copy.
    3328  * @param   cbCopy         How many bytes to copy.
    3329  */
    3330 static size_t ahciR3CopySgBufToPrdtl(PAHCI pThis, PAHCIREQ pAhciReq, PRTSGBUF pSgBuf,
    3331                                      size_t cbSkip, size_t cbCopy)
    3332 {
    3333     return ahciR3PrdtlWalk(pThis, pAhciReq, ahciR3CopyBufferToGuestWorker,
    3334                            pSgBuf, cbSkip, cbCopy);
     3374 * @param   pDevIns     The device instance.
     3375 * @param   pAhciReq    AHCI request structure.
     3376 * @param   pSgBuf      The S/G buffer to copy from.
     3377 * @param   cbSkip      How many bytes to skip in advance before starting to copy.
     3378 * @param   cbCopy      How many bytes to copy.
     3379 */
     3380static size_t ahciR3CopySgBufToPrdtl(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, PRTSGBUF pSgBuf, size_t cbSkip, size_t cbCopy)
     3381{
     3382    return ahciR3PrdtlWalk(pDevIns, pAhciReq, ahciR3CopyBufferToGuestWorker, pSgBuf, cbSkip, cbCopy);
    33353383}
    33363384
     
    33393387 *
    33403388 * @returns Amount of bytes copied from the PRDTL.
    3341  * @param   pThis          The AHCI controller device instance.
    3342  * @param   pAhciReq       AHCI request structure.
    3343  * @param   pSgBuf         The S/G buffer to copy into.
    3344  * @param   cbSkip         How many bytes to skip in advance before starting to copy.
    3345  * @param   cbCopy         How many bytes to copy.
    3346  */
    3347 static size_t ahciR3CopySgBufFromPrdtl(PAHCI pThis, PAHCIREQ pAhciReq, PRTSGBUF pSgBuf,
    3348                                        size_t cbSkip, size_t cbCopy)
    3349 {
    3350     return ahciR3PrdtlWalk(pThis, pAhciReq, ahciR3CopyBufferFromGuestWorker,
    3351                            pSgBuf, cbSkip, cbCopy);
     3389 * @param   pDevIns     The device instance.
     3390 * @param   pAhciReq    AHCI request structure.
     3391 * @param   pSgBuf      The S/G buffer to copy into.
     3392 * @param   cbSkip      How many bytes to skip in advance before starting to copy.
     3393 * @param   cbCopy      How many bytes to copy.
     3394 */
     3395static size_t ahciR3CopySgBufFromPrdtl(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, PRTSGBUF pSgBuf, size_t cbSkip, size_t cbCopy)
     3396{
     3397    return ahciR3PrdtlWalk(pDevIns, pAhciReq, ahciR3CopyBufferFromGuestWorker, pSgBuf, cbSkip, cbCopy);
    33523398}
    33533399
     
    33563402 *
    33573403 * @returns Amount of bytes copied from the PRDTL.
    3358  * @param   pThis          The AHCI controller device instance.
    3359  * @param   pAhciReq       AHCI request structure.
    3360  * @param   pvSrc          The buffer to copy from.
    3361  * @param   cbSrc          How many bytes to copy.
    3362  * @param   cbSkip         How many bytes to skip initially.
    3363  */
    3364 static size_t ahciR3CopyBufferToPrdtl(PAHCI pThis, PAHCIREQ pAhciReq, const void *pvSrc,
    3365                                       size_t cbSrc, size_t cbSkip)
     3404 * @param   pDevIns     The device instance.
     3405 * @param   pAhciReq    AHCI request structure.
     3406 * @param   pvSrc       The buffer to copy from.
     3407 * @param   cbSrc       How many bytes to copy.
     3408 * @param   cbSkip      How many bytes to skip initially.
     3409 */
     3410static size_t ahciR3CopyBufferToPrdtl(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, const void *pvSrc, size_t cbSrc, size_t cbSkip)
    33663411{
    33673412    RTSGSEG Seg;
     
    33703415    Seg.cbSeg = cbSrc;
    33713416    RTSgBufInit(&SgBuf, &Seg, 1);
    3372     return ahciR3CopySgBufToPrdtl(pThis, pAhciReq, &SgBuf, cbSkip, cbSrc);
     3417    return ahciR3CopySgBufToPrdtl(pDevIns, pAhciReq, &SgBuf, cbSkip, cbSrc);
    33733418}
    33743419
     
    33773422 *
    33783423 * @returns VBox status code.
    3379  * @param   pThis          The AHCI controller device instance.
    3380  * @param   pAhciReq       AHCI request structure.
    3381  * @param   pcbPrdt        Where to store the size of the guest buffer.
    3382  */
    3383 static int ahciR3PrdtQuerySize(PAHCI pThis, PAHCIREQ pAhciReq, size_t *pcbPrdt)
     3424 * @param   pDevIns     The device instance.
     3425 * @param   pThis       The AHCI controller device instance.
     3426 * @param   pAhciReq    AHCI request structure.
     3427 * @param   pcbPrdt     Where to store the size of the guest buffer.
     3428 */
     3429static int ahciR3PrdtQuerySize(PPDMDEVINS pDevIns, PAHCIREQ pAhciReq, size_t *pcbPrdt)
    33843430{
    33853431    RTGCPHYS GCPhysPrdtl = pAhciReq->GCPhysPrdtl;
     
    33903436    {
    33913437        SGLEntry aPrdtlEntries[32];
    3392         uint32_t cPrdtlEntriesRead = cPrdtlEntries < RT_ELEMENTS(aPrdtlEntries)
    3393                                    ? cPrdtlEntries
    3394                                    : RT_ELEMENTS(aPrdtlEntries);
    3395 
    3396         PDMDevHlpPhysRead(pThis->CTX_SUFF(pDevIns), GCPhysPrdtl, &aPrdtlEntries[0],
    3397                           cPrdtlEntriesRead * sizeof(SGLEntry));
     3438        uint32_t const cPrdtlEntriesRead = RT_MIN(cPrdtlEntries,  RT_ELEMENTS(aPrdtlEntries));
     3439
     3440        PDMDevHlpPhysRead(pDevIns, GCPhysPrdtl, &aPrdtlEntries[0], cPrdtlEntriesRead * sizeof(SGLEntry));
    33983441
    33993442        for (uint32_t i = 0; i < cPrdtlEntriesRead; i++)
     
    34123455 *
    34133456 * @returns Whether all active tasks were canceled.
    3414  * @param   pAhciPort        The AHCI port.
    3415  */
    3416 static bool ahciCancelActiveTasks(PAHCIPort pAhciPort)
    3417 {
    3418     if (pAhciPort->pDrvMediaEx)
    3419     {
    3420         int rc = pAhciPort->pDrvMediaEx->pfnIoReqCancelAll(pAhciPort->pDrvMediaEx);
     3457 * @param   pAhciPortR3 The AHCI port, ring-3 bits.
     3458 */
     3459static bool ahciR3CancelActiveTasks(PAHCIPORTR3 pAhciPortR3)
     3460{
     3461    if (pAhciPortR3->pDrvMediaEx)
     3462    {
     3463        int rc = pAhciPortR3->pDrvMediaEx->pfnIoReqCancelAll(pAhciPortR3->pDrvMediaEx);
    34213464        AssertRC(rc);
    34223465    }
     
    34283471 *
    34293472 * @returns VBox status code.
    3430  * @param   pAhciPort     AHCI port state.
    3431  * @param   pAhciReq      The request handling the TRIM request.
    3432  * @param   idxRangeStart Index of the first range to start copying.
    3433  * @param   paRanges      Where to store the ranges.
    3434  * @param   cRanges       Number of ranges fitting into the array.
    3435  * @param   pcRanges      Where to store the amount of ranges actually copied on success.
    3436  */
    3437 static int ahciTrimRangesCreate(PAHCIPort pAhciPort, PAHCIREQ pAhciReq, uint32_t idxRangeStart,
     3473 * @param   pDevIns         The device instance.
     3474 * @param   pAhciPort       AHCI port state.
     3475 * @param   pAhciReq        The request handling the TRIM request.
     3476 * @param   idxRangeStart   Index of the first range to start copying.
     3477 * @param   paRanges        Where to store the ranges.
     3478 * @param   cRanges         Number of ranges fitting into the array.
     3479 * @param   pcRanges        Where to store the amount of ranges actually copied on success.
     3480 */
     3481static int ahciTrimRangesCreate(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort, PAHCIREQ pAhciReq, uint32_t idxRangeStart,
    34383482                                PRTRANGE paRanges, uint32_t cRanges, uint32_t *pcRanges)
    34393483{
     
    34423486    uint32_t cPrdtlEntries = pAhciReq->cPrdtlEntries;
    34433487    RTGCPHYS GCPhysPrdtl   = pAhciReq->GCPhysPrdtl;
    3444     PPDMDEVINS pDevIns     = pAhciPort->CTX_SUFF(pDevIns);
    34453488    int rc = VERR_PDM_MEDIAEX_IOBUF_OVERFLOW;
    34463489    uint32_t idxRange = 0;
     
    35063549 *
    35073550 * @returns A new AHCI request structure or NULL if out of memory.
    3508  * @param   pAhciPort    The AHCI port.
    3509  * @param   uTag         The tag to assign.
    3510  */
    3511 static PAHCIREQ ahciR3ReqAlloc(PAHCIPort pAhciPort, uint32_t uTag)
     3551 * @param   pAhciPortR3 The AHCI port, ring-3 bits.
     3552 * @param   uTag        The tag to assign.
     3553 */
     3554static PAHCIREQ ahciR3ReqAlloc(PAHCIPORTR3 pAhciPortR3, uint32_t uTag)
    35123555{
    35133556    PAHCIREQ pAhciReq = NULL;
    35143557    PDMMEDIAEXIOREQ hIoReq = NULL;
    35153558
    3516     int rc = pAhciPort->pDrvMediaEx->pfnIoReqAlloc(pAhciPort->pDrvMediaEx, &hIoReq, (void **)&pAhciReq,
    3517                                                    uTag, PDMIMEDIAEX_F_SUSPEND_ON_RECOVERABLE_ERR);
     3559    int rc = pAhciPortR3->pDrvMediaEx->pfnIoReqAlloc(pAhciPortR3->pDrvMediaEx, &hIoReq, (void **)&pAhciReq,
     3560                                                     uTag, PDMIMEDIAEX_F_SUSPEND_ON_RECOVERABLE_ERR);
    35183561    if (RT_SUCCESS(rc))
    35193562    {
     
    35303573 *
    35313574 * @returns nothing.
    3532  * @param   pAhciPort    The AHCI port.
    3533  * @param   pAhciReq     The request to free.
    3534  */
    3535 static void ahciR3ReqFree(PAHCIPort pAhciPort, PAHCIREQ pAhciReq)
     3575 * @param   pAhciPort   The AHCI port, shared bits.
     3576 * @param   pAhciPortR3 The AHCI port, ring-3 bits.
     3577 * @param   pAhciReq    The request to free.
     3578 */
     3579static void ahciR3ReqFree(PAHCIPORTR3 pAhciPortR3, PAHCIREQ pAhciReq)
    35363580{
    35373581    if (   pAhciReq
    35383582        && !(pAhciReq->fFlags & AHCI_REQ_IS_ON_STACK))
    35393583    {
    3540         int rc = pAhciPort->pDrvMediaEx->pfnIoReqFree(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq);
     3584        int rc = pAhciPortR3->pDrvMediaEx->pfnIoReqFree(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq);
    35413585        AssertRC(rc);
    35423586    }
     
    35493593 * @returns Flag whether the given request was canceled inbetween;
    35503594 *
    3551  * @param pAhciPort    Pointer to the port where to request completed.
    3552  * @param pAhciReq     Pointer to the task which finished.
    3553  * @param rcReq        IPRT status code of the completed request.
    3554  */
    3555 static bool ahciTransferComplete(PAHCIPort pAhciPort, PAHCIREQ pAhciReq, int rcReq)
     3595 * @param   pDevIns     The device instance.
     3596 * @param   pThis       The shared AHCI state.
     3597 * @param   pThisCC     The ring-3 AHCI state.
     3598 * @param   pAhciPort   Pointer to the port where to request completed, shared bits.
     3599 * @param   pAhciPortR3 Pointer to the port where to request completed, ring-3 bits.
     3600 * @param   pAhciReq    Pointer to the task which finished.
     3601 * @param   rcReq       IPRT status code of the completed request.
     3602 */
     3603static bool ahciR3TransferComplete(PPDMDEVINS pDevIns, PAHCI pThis, PAHCICC pThisCC,
     3604                                   PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3, PAHCIREQ pAhciReq, int rcReq)
    35563605{
    35573606    bool fCanceled = false;
     
    35633612
    35643613    if (pAhciReq->fMapped)
    3565         PDMDevHlpPhysReleasePageMappingLock(pAhciPort->CTX_SUFF(pAhci)->CTX_SUFF(pDevIns),
    3566                                             &pAhciReq->PgLck);
     3614        PDMDevHlpPhysReleasePageMappingLock(pDevIns, &pAhciReq->PgLck);
    35673615
    35683616    if (rcReq != VERR_PDM_MEDIAEX_IOREQ_CANCELED)
     
    35873635                if (pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_FLUSH)
    35883636                    LogRel(("AHCI#%uP%u: Flush returned rc=%Rrc\n",
    3589                             pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN, rcReq));
     3637                            pDevIns->iInstance, pAhciPort->iLUN, rcReq));
    35903638                else if (pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_DISCARD)
    35913639                    LogRel(("AHCI#%uP%u: Trim returned rc=%Rrc\n",
    3592                             pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN, rcReq));
     3640                            pDevIns->iInstance, pAhciPort->iLUN, rcReq));
    35933641                else
    35943642                    LogRel(("AHCI#%uP%u: %s at offset %llu (%zu bytes left) returned rc=%Rrc\n",
    3595                             pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN,
     3643                            pDevIns->iInstance, pAhciPort->iLUN,
    35963644                            pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_READ
    35973645                            ? "Read"
     
    36083656            PAHCIREQ pReqDup = (PAHCIREQ)RTMemDup(pAhciReq, sizeof(AHCIREQ));
    36093657            if (   pReqDup
    3610                 && !ASMAtomicCmpXchgPtr(&pAhciPort->pTaskErr, pReqDup, NULL))
     3658                && !ASMAtomicCmpXchgPtr(&pAhciPortR3->pTaskErr, pReqDup, NULL))
    36113659                RTMemFree(pReqDup);
    36123660        }
     
    36403688            {
    36413689                size_t cbXfer = 0;
    3642                 int rc = pAhciPort->pDrvMediaEx->pfnIoReqQueryXferSize(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq, &cbXfer);
     3690                int rc = pAhciPortR3->pDrvMediaEx->pfnIoReqQueryXferSize(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq, &cbXfer);
    36433691                AssertRC(rc);
    36443692                u32PRDBC = (uint32_t)RT_MIN(cbXfer, pAhciReq->cbTransfer);
     
    36473695                u32PRDBC = (uint32_t)pAhciReq->cbTransfer;
    36483696
    3649             PDMDevHlpPCIPhysWrite(pAhciPort->CTX_SUFF(pDevIns), pAhciReq->GCPhysCmdHdrAddr + RT_UOFFSETOF(CmdHdr, u32PRDBC),
     3697            PDMDevHlpPCIPhysWrite(pDevIns, pAhciReq->GCPhysCmdHdrAddr + RT_UOFFSETOF(CmdHdr, u32PRDBC),
    36503698                                  &u32PRDBC, sizeof(u32PRDBC));
    36513699
     
    36593707                ASMAtomicOrU32(&pAhciPort->regIS, AHCI_PORT_IS_OFS);
    36603708                if (pAhciPort->regIE & AHCI_PORT_IE_OFE)
    3661                     ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     3709                    ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    36623710            }
    36633711        }
     
    36753723        memcpy(&cmdFis[0], &pAhciReq->cmdFis[0], sizeof(cmdFis));
    36763724
    3677         ahciR3ReqFree(pAhciPort, pAhciReq);
     3725        ahciR3ReqFree(pAhciPortR3, pAhciReq);
    36783726
    36793727        /* Post a PIO setup FIS first if this is a PIO command which transfers data. */
    36803728        if (fFlags & AHCI_REQ_PIO_DATA)
    3681             ahciSendPioSetupFis(pAhciPort, cbTransfer, &cmdFis[0], fRead, false /* fInterrupt */);
     3729            ahciSendPioSetupFis(pDevIns, pThis, pAhciPort, cbTransfer, &cmdFis[0], fRead, false /* fInterrupt */);
    36823730
    36833731        if (fFlags & AHCI_REQ_CLEAR_SACT)
    36843732        {
    3685             if (RT_SUCCESS(rcReq) && !ASMAtomicReadPtrT(&pAhciPort->pTaskErr, PAHCIREQ))
     3733            if (RT_SUCCESS(rcReq) && !ASMAtomicReadPtrT(&pAhciPortR3->pTaskErr, PAHCIREQ))
    36863734                ASMAtomicOrU32(&pAhciPort->u32QueuedTasksFinished, RT_BIT_32(uTag));
    36873735        }
     
    36943742             * impact on performance (see @bugref{5071})
    36953743             */
    3696             ahciSendSDBFis(pAhciPort, 0, true);
     3744            ahciSendSDBFis(pDevIns, pThis, pAhciPort, pAhciPortR3, 0, true);
    36973745        }
    36983746        else
    3699             ahciSendD2HFis(pAhciPort, uTag, &cmdFis[0], true);
     3747            ahciSendD2HFis(pDevIns, pThis, pAhciPort, uTag, &cmdFis[0], true);
    37003748    }
    37013749    else
     
    37123760            if (pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_FLUSH)
    37133761                LogRel(("AHCI#%uP%u: Canceled flush returned rc=%Rrc\n",
    3714                         pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN, rcReq));
     3762                        pDevIns->iInstance, pAhciPort->iLUN, rcReq));
    37153763            else if (pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_DISCARD)
    37163764                LogRel(("AHCI#%uP%u: Canceled trim returned rc=%Rrc\n",
    3717                         pAhciPort->CTX_SUFF(pDevIns)->iInstance,pAhciPort->iLUN, rcReq));
     3765                        pDevIns->iInstance,pAhciPort->iLUN, rcReq));
    37183766            else
    37193767                LogRel(("AHCI#%uP%u: Canceled %s at offset %llu (%zu bytes left) returned rc=%Rrc\n",
    3720                         pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN,
     3768                        pDevIns->iInstance, pAhciPort->iLUN,
    37213769                        pAhciReq->enmType == PDMMEDIAEXIOREQTYPE_READ
    37223770                        ? "read"
     
    37263774         }
    37273775
    3728          ahciR3ReqFree(pAhciPort, pAhciReq);
     3776         ahciR3ReqFree(pAhciPortR3, pAhciReq);
    37293777    }
    37303778
     
    37393787    ASMAtomicDecU32(&pAhciPort->cTasksActive);
    37403788
    3741     if (pAhciPort->cTasksActive == 0 && pAhciPort->pAhciR3->fSignalIdle)
    3742         PDMDevHlpAsyncNotificationCompleted(pAhciPort->pDevInsR3);
     3789    if (pAhciPort->cTasksActive == 0 && pThisCC->fSignalIdle)
     3790        PDMDevHlpAsyncNotificationCompleted(pDevIns);
    37433791
    37443792    return fCanceled;
     
    37523800                                                size_t cbCopy)
    37533801{
    3754     RT_NOREF(hIoReq);
    3755     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
     3802    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
    37563803    int rc = VINF_SUCCESS;
    37573804    PAHCIREQ pIoReq = (PAHCIREQ)pvIoReqAlloc;
    3758 
    3759     ahciR3CopySgBufToPrdtl(pAhciPort->CTX_SUFF(pAhci), pIoReq, pSgBuf, offDst, cbCopy);
     3805    RT_NOREF(hIoReq);
     3806
     3807    ahciR3CopySgBufToPrdtl(pAhciPortR3->pDevIns, pIoReq, pSgBuf, offDst, cbCopy);
    37603808
    37613809    if (pIoReq->fFlags & AHCI_REQ_OVERFLOW)
     
    37723820                                              size_t cbCopy)
    37733821{
    3774     RT_NOREF(hIoReq);
    3775     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
     3822    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
    37763823    int rc = VINF_SUCCESS;
    37773824    PAHCIREQ pIoReq = (PAHCIREQ)pvIoReqAlloc;
    3778 
    3779     ahciR3CopySgBufFromPrdtl(pAhciPort->CTX_SUFF(pAhci), pIoReq, pSgBuf, offSrc, cbCopy);
     3825    RT_NOREF(hIoReq);
     3826
     3827    ahciR3CopySgBufFromPrdtl(pAhciPortR3->pDevIns, pIoReq, pSgBuf, offSrc, cbCopy);
    37803828    if (pIoReq->fFlags & AHCI_REQ_OVERFLOW)
    37813829        rc = VERR_PDM_MEDIAEX_IOBUF_UNDERRUN;
     
    37903838                                             void *pvIoReqAlloc, void **ppvBuf, size_t *pcbBuf)
    37913839{
     3840    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
     3841    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
     3842    PAHCIREQ    pIoReq      = (PAHCIREQ)pvIoReqAlloc;
     3843    int         rc          = VERR_NOT_SUPPORTED;
    37923844    RT_NOREF(hIoReq);
    3793     int rc              = VERR_NOT_SUPPORTED;
    3794     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
    3795     PAHCIREQ pIoReq     = (PAHCIREQ)pvIoReqAlloc;
    3796     PAHCI pThis         = pAhciPort->CTX_SUFF(pAhci);
    37973845
    37983846    /* Only allow single 4KB page aligned buffers at the moment. */
     
    38033851        SGLEntry PrdtEntry;
    38043852
    3805         PDMDevHlpPhysRead(pThis->pDevInsR3, GCPhysPrdt, &PrdtEntry, sizeof(SGLEntry));
     3853        PDMDevHlpPhysRead(pDevIns, GCPhysPrdt, &PrdtEntry, sizeof(SGLEntry));
    38063854
    38073855        RTGCPHYS GCPhysAddrDataBase = AHCI_RTGCPHYS_FROM_U32(PrdtEntry.u32DBAUp, PrdtEntry.u32DBA);
     
    38113859            && !(GCPhysAddrDataBase & (_4K - 1)))
    38123860        {
    3813             rc = PDMDevHlpPhysGCPhys2CCPtr(pThis->pDevInsR3, GCPhysAddrDataBase,
    3814                                            0, ppvBuf, &pIoReq->PgLck);
     3861            rc = PDMDevHlpPhysGCPhys2CCPtr(pDevIns, GCPhysAddrDataBase, 0, ppvBuf, &pIoReq->PgLck);
    38153862            if (RT_SUCCESS(rc))
    38163863            {
     
    38343881                                                       uint32_t *pcRanges)
    38353882{
     3883    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
     3884    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
     3885    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     3886    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
     3887    PAHCIREQ    pIoReq      = (PAHCIREQ)pvIoReqAlloc;
    38363888    RT_NOREF(hIoReq);
    3837     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
    3838     PAHCIREQ pIoReq = (PAHCIREQ)pvIoReqAlloc;
    3839 
    3840     return ahciTrimRangesCreate(pAhciPort, pIoReq, idxRangeStart, paRanges, cRanges, pcRanges);
     3889
     3890    return ahciTrimRangesCreate(pDevIns, pAhciPort, pIoReq, idxRangeStart, paRanges, cRanges, pcRanges);
    38413891}
    38423892
     
    38473897                                                   void *pvIoReqAlloc, int rcReq)
    38483898{
     3899    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
     3900    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
     3901    PAHCIR3     pThisCC     = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     3902    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     3903    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
     3904    PAHCIREQ    pIoReq      = (PAHCIREQ)pvIoReqAlloc;
    38493905    RT_NOREF(hIoReq);
    3850     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
    3851     ahciTransferComplete(pAhciPort, (PAHCIREQ)pvIoReqAlloc, rcReq);
     3906
     3907    ahciR3TransferComplete(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3, pIoReq, rcReq);
    38523908    return VINF_SUCCESS;
    38533909}
     
    38593915                                                  void *pvIoReqAlloc, PDMMEDIAEXIOREQSTATE enmState)
    38603916{
     3917    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
     3918    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
     3919    PAHCIR3     pThisCC     = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     3920    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     3921    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
    38613922    RT_NOREF(hIoReq, pvIoReqAlloc);
    3862     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
    38633923
    38643924    switch (enmState)
     
    38683928            /* Make sure the request is not accounted for so the VM can suspend successfully. */
    38693929            uint32_t cTasksActive = ASMAtomicDecU32(&pAhciPort->cTasksActive);
    3870             if (!cTasksActive && pAhciPort->pAhciR3->fSignalIdle)
    3871                 PDMDevHlpAsyncNotificationCompleted(pAhciPort->pDevInsR3);
     3930            if (!cTasksActive && pThisCC->fSignalIdle)
     3931                PDMDevHlpAsyncNotificationCompleted(pDevIns);
    38723932            break;
    38733933        }
     
    38863946static DECLCALLBACK(void) ahciR3MediumEjected(PPDMIMEDIAEXPORT pInterface)
    38873947{
    3888     PAHCIPort pAhciPort = RT_FROM_MEMBER(pInterface, AHCIPort, IMediaExPort);
    3889     PAHCI pThis = pAhciPort->CTX_SUFF(pAhci);
    3890 
    3891     if (pThis->pMediaNotify)
    3892     {
    3893         int rc = VMR3ReqCallNoWait(PDMDevHlpGetVM(pThis->CTX_SUFF(pDevIns)), VMCPUID_ANY,
    3894                                    (PFNRT)pThis->pMediaNotify->pfnEjected, 2,
    3895                                    pThis->pMediaNotify, pAhciPort->iLUN);
     3948    PAHCIPORTR3 pAhciPortR3 = RT_FROM_MEMBER(pInterface, AHCIPORTR3, IMediaExPort);
     3949    PPDMDEVINS  pDevIns     = pAhciPortR3->pDevIns;
     3950    PAHCIR3     pThisCC     = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     3951    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     3952    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
     3953
     3954    if (pThisCC->pMediaNotify)
     3955    {
     3956        int rc = VMR3ReqCallNoWait(PDMDevHlpGetVM(pDevIns), VMCPUID_ANY,
     3957                                   (PFNRT)pThisCC->pMediaNotify->pfnEjected, 2,
     3958                                   pThisCC->pMediaNotify, pAhciPort->iLUN);
    38963959        AssertRC(rc);
    38973960    }
     
    39023965 *
    39033966 * @returns The direction of the data transfer
    3904  * @param   pAhciPort     The AHCI port of the request.
    3905  * @param   pAhciReq      The AHCI request state.
    3906  * @param   pCmdFis       Pointer to the command FIS.
    3907  */
    3908 static PDMMEDIAEXIOREQTYPE ahciProcessCmd(PAHCIPort pAhciPort, PAHCIREQ pAhciReq, uint8_t *pCmdFis)
     3967 * @param   pDevIns         The device instance.
     3968 * @param   pThis           The shared AHCI state.
     3969 * @param   pAhciPort       The AHCI port of the request, shared bits.
     3970 * @param   pAhciPortR3     The AHCI port of the request, ring-3 bits.
     3971 * @param   pAhciReq        The AHCI request state.
     3972 * @param   pCmdFis         Pointer to the command FIS.
     3973 */
     3974static PDMMEDIAEXIOREQTYPE ahciProcessCmd(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3,
     3975                                          PAHCIREQ pAhciReq, uint8_t *pCmdFis)
    39093976{
    39103977    PDMMEDIAEXIOREQTYPE enmType = PDMMEDIAEXIOREQTYPE_INVALID;
     
    39193986        case ATA_IDENTIFY_DEVICE:
    39203987        {
    3921             if (pAhciPort->pDrvMedia && !pAhciPort->fATAPI)
     3988            if (pAhciPortR3->pDrvMedia && !pAhciPort->fATAPI)
    39223989            {
    39233990                uint16_t u16Temp[256];
    39243991
    39253992                /* Fill the buffer. */
    3926                 ahciIdentifySS(pAhciPort, u16Temp);
     3993                ahciIdentifySS(pThis, pAhciPort, pAhciPortR3, u16Temp);
    39273994
    39283995                /* Copy the buffer. */
    3929                 size_t cbCopied = ahciR3CopyBufferToPrdtl(pAhciPort->CTX_SUFF(pAhci), pAhciReq,
    3930                                                           &u16Temp[0], sizeof(u16Temp), 0 /* cbSkip */);
     3996                size_t cbCopied = ahciR3CopyBufferToPrdtl(pDevIns, pAhciReq, &u16Temp[0], sizeof(u16Temp), 0 /* cbSkip */);
    39313997
    39323998                pAhciReq->fFlags |= AHCI_REQ_PIO_DATA;
     
    39864052            {
    39874053                /* Reset the device. */
    3988                 ahciDeviceReset(pAhciPort, pAhciReq);
     4054                ahciDeviceReset(pDevIns, pThis, pAhciPort, pAhciReq);
    39894055            }
    39904056            break;
     
    40064072            {
    40074073                size_t cbData;
    4008                 ahciR3AtapiIdentify(pAhciReq, pAhciPort, 512, &cbData);
     4074                ahciR3AtapiIdentify(pDevIns, pAhciReq, pAhciPort, 512, &cbData);
    40094075
    40104076                pAhciReq->fFlags |= AHCI_REQ_PIO_DATA;
     
    40994165                    {
    41004166                        LogFlow(("Reading error page\n"));
    4101                         PAHCIREQ pTaskErr = ASMAtomicXchgPtrT(&pAhciPort->pTaskErr, NULL, PAHCIREQ);
     4167                        PAHCIREQ pTaskErr = ASMAtomicXchgPtrT(&pAhciPortR3->pTaskErr, NULL, PAHCIREQ);
    41024168                        if (pTaskErr)
    41034169                        {
     
    41324198                         * See SATA2 1.2 spec chapter 4.2.3.4
    41334199                         */
    4134                         bool fAbortedAll = ahciCancelActiveTasks(pAhciPort);
     4200                        bool fAbortedAll = ahciR3CancelActiveTasks(pAhciPortR3);
    41354201                        Assert(fAbortedAll); NOREF(fAbortedAll);
    4136                         ahciSendSDBFis(pAhciPort, 0xffffffff, true);
     4202                        ahciSendSDBFis(pDevIns, pThis, pAhciPort, pAhciPortR3, UINT32_C(0xffffffff), true);
    41374203
    41384204                        break;
     
    41414207
    41424208                /* Copy the buffer. */
    4143                 size_t cbCopied = ahciR3CopyBufferToPrdtl(pAhciPort->CTX_SUFF(pAhci), pAhciReq,
    4144                                                           &aBuf[offLogRead], cbLogRead, 0 /* cbSkip */);
     4209                size_t cbCopied = ahciR3CopyBufferToPrdtl(pDevIns, pAhciReq, &aBuf[offLogRead], cbLogRead, 0 /* cbSkip */);
    41454210
    41464211                pAhciReq->fFlags |= AHCI_REQ_PIO_DATA;
     
    41854250 *
    41864251 * @returns whether the H2D FIS was successfully read from the guest memory.
    4187  * @param pAhciPort    The AHCI port of the request.
    4188  * @param pAhciReq     The state of the actual task.
    4189  */
    4190 static bool ahciPortTaskGetCommandFis(PAHCIPort pAhciPort, PAHCIREQ pAhciReq)
     4252 * @param   pDevIns     The device instance.
     4253 * @param   pThis       The shared AHCI state.
     4254 * @param   pAhciPort   The AHCI port of the request.
     4255 * @param   pAhciReq    The state of the actual task.
     4256 */
     4257static bool ahciPortTaskGetCommandFis(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIREQ pAhciReq)
    41914258{
    41924259    AssertMsgReturn(pAhciPort->GCPhysAddrClb && pAhciPort->GCPhysAddrFb,
     
    42034270    LogFlow(("%s: PDMDevHlpPhysRead GCPhysAddrCmdLst=%RGp cbCmdHdr=%u\n", __FUNCTION__,
    42044271             pAhciReq->GCPhysCmdHdrAddr, sizeof(CmdHdr)));
    4205     PDMDevHlpPhysRead(pAhciPort->CTX_SUFF(pDevIns), pAhciReq->GCPhysCmdHdrAddr, &cmdHdr, sizeof(CmdHdr));
     4272    PDMDevHlpPhysRead(pDevIns, pAhciReq->GCPhysCmdHdrAddr, &cmdHdr, sizeof(CmdHdr));
    42064273
    42074274#ifdef LOG_ENABLED
     
    42184285    /* Read the command Fis. */
    42194286    LogFlow(("%s: PDMDevHlpPhysRead GCPhysAddrCmdTbl=%RGp cbCmdFis=%u\n", __FUNCTION__, GCPhysAddrCmdTbl, AHCI_CMDFIS_TYPE_H2D_SIZE));
    4220     PDMDevHlpPhysRead(pAhciPort->CTX_SUFF(pDevIns), GCPhysAddrCmdTbl, &pAhciReq->cmdFis[0], AHCI_CMDFIS_TYPE_H2D_SIZE);
     4287    PDMDevHlpPhysRead(pDevIns, GCPhysAddrCmdTbl, &pAhciReq->cmdFis[0], AHCI_CMDFIS_TYPE_H2D_SIZE);
    42214288
    42224289    AssertMsgReturn(pAhciReq->cmdFis[AHCI_CMDFIS_TYPE] == AHCI_CMDFIS_TYPE_H2D,
     
    42314298    {
    42324299        GCPhysAddrCmdTbl += AHCI_CMDHDR_ACMD_OFFSET;
    4233         PDMDevHlpPhysRead(pAhciPort->CTX_SUFF(pDevIns), GCPhysAddrCmdTbl, &pAhciReq->aATAPICmd[0], ATAPI_PACKET_SIZE);
     4300        PDMDevHlpPhysRead(pDevIns, GCPhysAddrCmdTbl, &pAhciReq->aATAPICmd[0], ATAPI_PACKET_SIZE);
    42344301    }
    42354302
     
    42414308         * but this FIS does not assert an interrupt
    42424309         */
    4243         ahciSendD2HFis(pAhciPort, pAhciReq->uTag, pAhciReq->cmdFis, false);
     4310        ahciSendD2HFis(pDevIns, pThis, pAhciPort, pAhciReq->uTag, pAhciReq->cmdFis, false);
    42444311        pAhciPort->regTFD &= ~AHCI_PORT_TFD_BSY;
    42454312    }
     
    42614328
    42624329        ahciLog(("Entry %u at address %RGp\n", i, GCPhysPrdtl));
    4263         PDMDevHlpPhysRead(pAhciPort->CTX_SUFF(pDevIns), GCPhysPrdtl, &SGEntry, sizeof(SGLEntry));
     4330        PDMDevHlpPhysRead(pDevIns, GCPhysPrdtl, &SGEntry, sizeof(SGLEntry));
    42644331
    42654332        RTGCPHYS GCPhysDataAddr = AHCI_RTGCPHYS_FROM_U32(SGEntry.u32DBAUp, SGEntry.u32DBA);
     
    42774344 *
    42784345 * @returns Flag whether the request was canceled inbetween.
    4279  * @param   pAhciPort    The port the request is for.
    4280  * @param   pAhciReq     The request to submit.
     4346 * @param   pDevIns     The device instance.
     4347 * @param   pThis       The shared AHCI state.
     4348 * @param   pThisCC     The ring-3 AHCI state.
     4349 * @param   pAhciPort   The port the request is for.
     4350 * @param   pAhciReq    The request to submit.
    42814351 * @param   enmType     The request type.
    42824352 */
    4283 static bool ahciR3ReqSubmit(PAHCIPort pAhciPort, PAHCIREQ pAhciReq, PDMMEDIAEXIOREQTYPE enmType)
     4353static bool ahciR3ReqSubmit(PPDMDEVINS pDevIns, PAHCI pThis, PAHCICC pThisCC, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3,
     4354                            PAHCIREQ pAhciReq, PDMMEDIAEXIOREQTYPE enmType)
    42844355{
    42854356    int rc = VINF_SUCCESS;
     
    42894360
    42904361    if (enmType == PDMMEDIAEXIOREQTYPE_FLUSH)
    4291         rc = pAhciPort->pDrvMediaEx->pfnIoReqFlush(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq);
     4362        rc = pAhciPortR3->pDrvMediaEx->pfnIoReqFlush(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq);
    42924363    else if (enmType == PDMMEDIAEXIOREQTYPE_DISCARD)
    42934364    {
     
    43014372
    43024373        pAhciPort->Led.Asserted.s.fWriting = pAhciPort->Led.Actual.s.fWriting = 1;
    4303         rc = pAhciPort->pDrvMediaEx->pfnIoReqDiscard(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq,
     4374        rc = pAhciPortR3->pDrvMediaEx->pfnIoReqDiscard(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq,
    43044375                                                     cRangesMax);
    43054376    }
     
    43074378    {
    43084379        pAhciPort->Led.Asserted.s.fReading = pAhciPort->Led.Actual.s.fReading = 1;
    4309         rc = pAhciPort->pDrvMediaEx->pfnIoReqRead(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq,
     4380        rc = pAhciPortR3->pDrvMediaEx->pfnIoReqRead(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq,
    43104381                                                  pAhciReq->uOffset, pAhciReq->cbTransfer);
    43114382    }
     
    43134384    {
    43144385        pAhciPort->Led.Asserted.s.fWriting = pAhciPort->Led.Actual.s.fWriting = 1;
    4315         rc = pAhciPort->pDrvMediaEx->pfnIoReqWrite(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq,
     4386        rc = pAhciPortR3->pDrvMediaEx->pfnIoReqWrite(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq,
    43164387                                                   pAhciReq->uOffset, pAhciReq->cbTransfer);
    43174388    }
     
    43214392
    43224393        if (pAhciReq->cPrdtlEntries)
    4323             rc = ahciR3PrdtQuerySize(pAhciPort->CTX_SUFF(pAhci), pAhciReq, &cbBuf);
     4394            rc = ahciR3PrdtQuerySize(pDevIns, pAhciReq, &cbBuf);
    43244395        pAhciReq->cbTransfer = cbBuf;
    43254396        if (RT_SUCCESS(rc))
     
    43294400            else if (cbBuf)
    43304401                pAhciPort->Led.Asserted.s.fWriting = pAhciPort->Led.Actual.s.fWriting = 1;
    4331             rc = pAhciPort->pDrvMediaEx->pfnIoReqSendScsiCmd(pAhciPort->pDrvMediaEx, pAhciReq->hIoReq,
     4402            rc = pAhciPortR3->pDrvMediaEx->pfnIoReqSendScsiCmd(pAhciPortR3->pDrvMediaEx, pAhciReq->hIoReq,
    43324403                                                             0, &pAhciReq->aATAPICmd[0], ATAPI_PACKET_SIZE,
    43334404                                                             PDMMEDIAEXIOREQSCSITXDIR_UNKNOWN, NULL, cbBuf,
     
    43384409
    43394410    if (rc == VINF_SUCCESS)
    4340         fReqCanceled = ahciTransferComplete(pAhciPort, pAhciReq, VINF_SUCCESS);
     4411        fReqCanceled = ahciR3TransferComplete(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3, pAhciReq, VINF_SUCCESS);
    43414412    else if (rc != VINF_PDM_MEDIAEX_IOREQ_IN_PROGRESS)
    4342         fReqCanceled = ahciTransferComplete(pAhciPort, pAhciReq, rc);
     4413        fReqCanceled = ahciR3TransferComplete(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3, pAhciReq, rc);
    43434414
    43444415    return fReqCanceled;
     
    43514422 * @returns Whether the command was successfully fetched from guest memory and
    43524423 *          can be continued.
    4353  * @param   pAhciPort    The AHCI port the request is for.
    4354  * @param   pAhciReq     Request structure to copy the command to.
    4355  */
    4356 static bool ahciR3CmdPrepare(PAHCIPort pAhciPort, PAHCIREQ pAhciReq)
     4424 * @param   pDevIns     The device instance.
     4425 * @param   pThis       The shared AHCI state.
     4426 * @param   pAhciPort   The AHCI port the request is for.
     4427 * @param   pAhciReq    Request structure to copy the command to.
     4428 */
     4429static bool ahciR3CmdPrepare(PPDMDEVINS pDevIns, PAHCI pThis, PAHCIPORT pAhciPort, PAHCIREQ pAhciReq)
    43574430{
    43584431    /* Set current command slot */
    43594432    ASMAtomicWriteU32(&pAhciPort->u32CurrentCommandSlot, pAhciReq->uTag);
    43604433
    4361     bool fContinue = ahciPortTaskGetCommandFis(pAhciPort, pAhciReq);
     4434    bool fContinue = ahciPortTaskGetCommandFis(pDevIns, pThis, pAhciPort, pAhciReq);
    43624435    if (fContinue)
    43634436    {
     
    43804453            AssertLogRelMsg(ASMAtomicReadU32(&pAhciPort->cTasksActive) <= AHCI_NR_COMMAND_SLOTS,
    43814454                            ("AHCI#%uP%u: There are more than %u (+1) requests active",
    4382                              pAhciPort->CTX_SUFF(pDevIns)->iInstance, pAhciPort->iLUN,
     4455                             pDevIns->iInstance, pAhciPort->iLUN,
    43834456                             AHCI_NR_COMMAND_SLOTS));
    43844457            ASMAtomicIncU32(&pAhciPort->cTasksActive);
     
    43914464                ahciLog(("%s: Setting device into reset state\n", __FUNCTION__));
    43924465                pAhciPort->fResetDevice = true;
    4393                 ahciSendD2HFis(pAhciPort, pAhciReq->uTag, pAhciReq->cmdFis, true);
     4466                ahciSendD2HFis(pDevIns, pThis, pAhciPort, pAhciReq->uTag, pAhciReq->cmdFis, true);
    43944467            }
    43954468            else if (pAhciPort->fResetDevice) /* The bit is not set and we are in a reset state. */
    4396                 ahciFinishStorageDeviceReset(pAhciPort, pAhciReq);
     4469                ahciFinishStorageDeviceReset(pDevIns, pThis, pAhciPort, pAhciReq);
    43974470            else /* We are not in a reset state update the control registers. */
    43984471                AssertMsgFailed(("%s: Update the control register\n", __FUNCTION__));
     
    44224495static DECLCALLBACK(int) ahciAsyncIOLoop(PPDMDEVINS pDevIns, PPDMTHREAD pThread)
    44234496{
    4424     RT_NOREF(pDevIns);
    4425     PAHCIPort pAhciPort = (PAHCIPort)pThread->pvUser;
    4426     PAHCI     pThis     = pAhciPort->CTX_SUFF(pAhci);
    4427     int       rc        = VINF_SUCCESS;
     4497    PAHCIPORTR3 pAhciPortR3 = (PAHCIPORTR3)pThread->pvUser;
     4498    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     4499    PAHCIR3     pThisCC     = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     4500    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
     4501    int         rc          = VINF_SUCCESS;
    44284502
    44294503    ahciLog(("%s: Port %d entering async IO loop.\n", __FUNCTION__, pAhciPort->iLUN));
     
    44554529
    44564530        /* Check whether the thread should be suspended. */
    4457         if (pThis->fSignalIdle)
     4531        if (pThisCC->fSignalIdle)
    44584532        {
    44594533            if (!ASMAtomicDecU32(&pThis->cThreadsActive))
    4460                 PDMDevHlpAsyncNotificationCompleted(pAhciPort->pDevInsR3);
     4534                PDMDevHlpAsyncNotificationCompleted(pDevIns);
    44614535            continue;
    44624536        }
     
    44704544            && !ASMAtomicDecU32(&pThis->cThreadsActive))
    44714545        {
    4472             ahciHBAReset(pThis);
    4473             if (pThis->fSignalIdle)
    4474                 PDMDevHlpAsyncNotificationCompleted(pAhciPort->pDevInsR3);
     4546            ahciR3HBAReset(pDevIns, pThis, pThisCC);
     4547            if (pThisCC->fSignalIdle)
     4548                PDMDevHlpAsyncNotificationCompleted(pDevIns);
    44754549            continue;
    44764550        }
     
    44864560            ahciLog(("%s: Processing command at slot %d\n", __FUNCTION__, idx));
    44874561
    4488             PAHCIREQ pAhciReq = ahciR3ReqAlloc(pAhciPort, idx);
     4562            PAHCIREQ pAhciReq = ahciR3ReqAlloc(pAhciPortR3, idx);
    44894563            if (RT_LIKELY(pAhciReq))
    44904564            {
     
    44924566                pAhciReq->fFlags        = 0;
    44934567
    4494                 bool fContinue = ahciR3CmdPrepare(pAhciPort, pAhciReq);
     4568                bool fContinue = ahciR3CmdPrepare(pDevIns, pThis, pAhciPort, pAhciReq);
    44954569                if (fContinue)
    44964570                {
    4497                     PDMMEDIAEXIOREQTYPE enmType = ahciProcessCmd(pAhciPort, pAhciReq, pAhciReq->cmdFis);
     4571                    PDMMEDIAEXIOREQTYPE enmType = ahciProcessCmd(pDevIns, pThis, pAhciPort, pAhciPortR3,
     4572                                                                 pAhciReq, pAhciReq->cmdFis);
    44984573                    pAhciReq->enmType = enmType;
    44994574
    45004575                    if (enmType != PDMMEDIAEXIOREQTYPE_INVALID)
    4501                         fReqCanceled = ahciR3ReqSubmit(pAhciPort, pAhciReq, enmType);
     4576                        fReqCanceled = ahciR3ReqSubmit(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3, pAhciReq, enmType);
    45024577                    else
    4503                         fReqCanceled = ahciTransferComplete(pAhciPort, pAhciReq, VINF_SUCCESS);
     4578                        fReqCanceled = ahciR3TransferComplete(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3,
     4579                                                              pAhciReq, VINF_SUCCESS);
    45044580                } /* Command */
    45054581                else
    4506                     ahciR3ReqFree(pAhciPort, pAhciReq);
     4582                    ahciR3ReqFree(pAhciPortR3, pAhciReq);
    45074583            }
    45084584            else /* !Request allocated, use on stack variant to signal the error. */
     
    45164592                Req.enmType    = PDMMEDIAEXIOREQTYPE_INVALID;
    45174593
    4518                 bool fContinue = ahciR3CmdPrepare(pAhciPort, &Req);
     4594                bool fContinue = ahciR3CmdPrepare(pDevIns, pThis, pAhciPort, &Req);
    45194595                if (fContinue)
    4520                     fReqCanceled = ahciTransferComplete(pAhciPort, &Req, VERR_NO_MEMORY);
     4596                    fReqCanceled = ahciR3TransferComplete(pDevIns, pThis, pThisCC, pAhciPort, pAhciPortR3, &Req, VERR_NO_MEMORY);
    45214597            }
    45224598
     
    45354611        if (   ASMAtomicReadBool(&pAhciPort->fPortReset)
    45364612            && (pAhciPort->regSCTL & AHCI_PORT_SCTL_DET) == AHCI_PORT_SCTL_DET_NINIT)
    4537             ahciPortResetFinish(pAhciPort);
     4613            ahciPortResetFinish(pDevIns, pThis, pAhciPort, pAhciPortR3);
    45384614
    45394615        /*
     
    45454621        if (   (u32RegHbaCtrl & AHCI_HBA_CTRL_HR)
    45464622            && !cThreadsActive)
    4547             ahciHBAReset(pThis);
    4548 
    4549         if (!cThreadsActive && pThis->fSignalIdle)
    4550             PDMDevHlpAsyncNotificationCompleted(pAhciPort->pDevInsR3);
     4623            ahciR3HBAReset(pDevIns, pThis, pThisCC);
     4624
     4625        if (!cThreadsActive && pThisCC->fSignalIdle)
     4626            PDMDevHlpAsyncNotificationCompleted(pDevIns);
    45514627    } /* While running */
    45524628
     
    45604636static DECLCALLBACK(int) ahciAsyncIOLoopWakeUp(PPDMDEVINS pDevIns, PPDMTHREAD pThread)
    45614637{
    4562     PAHCIPort pAhciPort = (PAHCIPort)pThread->pvUser;
     4638    PAHCIPORTR3 pAhciPortR3 = (PAHCIPORTR3)pThread->pvUser;
     4639    PAHCI       pThis       = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     4640    PAHCIPORT   pAhciPort   = &RT_SAFE_SUBSCRIPT(pThis->ahciPort, pAhciPortR3->iLUN);
    45634641    return PDMDevHlpSUPSemEventSignal(pDevIns, pAhciPort->hEvtProcess);
    45644642}
     
    46054683     * Per port data.
    46064684     */
    4607     for (unsigned i = 0; i < pThis->cPortsImpl; i++)
    4608     {
    4609         PAHCIPort pThisPort = &pThis->ahciPort[i];
    4610 
    4611         pHlp->pfnPrintf(pHlp, "Port %d: device-attached=%RTbool\n",
    4612                         pThisPort->iLUN, pThisPort->pDrvBase != NULL);
     4685    uint32_t const cPortsImpl = RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort));
     4686    for (unsigned i = 0; i < cPortsImpl; i++)
     4687    {
     4688        PAHCIPORT pThisPort = &pThis->ahciPort[i];
     4689
     4690        pHlp->pfnPrintf(pHlp, "Port %d: device-attached=%RTbool\n", pThisPort->iLUN, pThisPort->fPresent);
    46134691        pHlp->pfnPrintf(pHlp, "PortClb=%#x\n", pThisPort->regCLB);
    46144692        pHlp->pfnPrintf(pHlp, "PortClbU=%#x\n", pThisPort->regCLBU);
     
    46594737    for (uint32_t i = 0; i < RT_ELEMENTS(pThis->ahciPort); i++)
    46604738    {
    4661         PAHCIPort pThisPort = &pThis->ahciPort[i];
    4662         if (pThisPort->pDrvBase)
     4739        PAHCIPORT pThisPort = &pThis->ahciPort[i];
     4740        if (pThisPort->fPresent)
    46634741        {
    46644742            if (   (pThisPort->cTasksActive != 0)
     
    47054783    for (uint32_t i = 0; i < AHCI_MAX_NR_PORTS_IMPL; i++)
    47064784    {
    4707         pHlp->pfnSSMPutBool(pSSM, pThis->ahciPort[i].pDrvBase != NULL);
     4785        pHlp->pfnSSMPutBool(pSSM, pThis->ahciPort[i].fPresent);
    47084786        pHlp->pfnSSMPutBool(pSSM, pThis->ahciPort[i].fHotpluggable);
    47094787        pHlp->pfnSSMPutStrZ(pSSM, pThis->ahciPort[i].szSerialNumber);
     
    49094987            rc = pHlp->pfnSSMGetBool(pSSM, &fInUse);
    49104988            AssertRCReturn(rc, rc);
    4911             if (fInUse != (pThis->ahciPort[i].pDrvBase != NULL))
     4989            if (fInUse != pThis->ahciPort[i].fPresent)
    49124990                return pHlp->pfnSSMSetCfgError(pSSM, RT_SRC_POS,
    49134991                                               N_("The %s VM is missing a device on port %u. Please make sure the source and target VMs have compatible storage configurations"),
     
    49955073        for (uint32_t i = 0; i < AHCI_MAX_NR_PORTS_IMPL; i++)
    49965074        {
    4997             PAHCIPort pAhciPort = &pThis->ahciPort[i];
     5075            PAHCIPORT pAhciPort = &pThis->ahciPort[i];
    49985076
    49995077            pHlp->pfnSSMGetU32(pSSM, &pThis->ahciPort[i].regCLB);
     
    50875165/* -=-=-=-=- device PDM interface -=-=-=-=- */
    50885166
    5089 static DECLCALLBACK(void) ahciR3Relocate(PPDMDEVINS pDevIns, RTGCINTPTR offDelta)
    5090 {
    5091     uint32_t i;
    5092     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5093 
    5094     pThis->pDevInsRC += offDelta;
    5095 
    5096     /* Relocate every port. */
    5097     for (i = 0; i < RT_ELEMENTS(pThis->ahciPort); i++)
    5098     {
    5099         PAHCIPort pAhciPort = &pThis->ahciPort[i];
    5100         pAhciPort->pAhciRC += offDelta;
    5101         pAhciPort->pDevInsRC += offDelta;
    5102     }
    5103 }
    5104 
    51055167/**
    51065168 * Configure the attached device for a port.
     
    51105172 * @returns VBox status code
    51115173 * @param   pDevIns     The device instance data.
    5112  * @param   pAhciPort   The port for which the device is to be configured.
    5113  */
    5114 static int ahciR3ConfigureLUN(PPDMDEVINS pDevIns, PAHCIPort pAhciPort)
     5174 * @param   pAhciPort   The port for which the device is to be configured, shared bits.
     5175 * @param   pAhciPortR3 The port for which the device is to be configured, ring-3 bits.
     5176 */
     5177static int ahciR3ConfigureLUN(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3)
    51155178{
    51165179    /* Query the media interface. */
    5117     pAhciPort->pDrvMedia = PDMIBASE_QUERY_INTERFACE(pAhciPort->pDrvBase, PDMIMEDIA);
    5118     AssertMsgReturn(VALID_PTR(pAhciPort->pDrvMedia),
     5180    pAhciPortR3->pDrvMedia = PDMIBASE_QUERY_INTERFACE(pAhciPortR3->pDrvBase, PDMIMEDIA);
     5181    AssertMsgReturn(VALID_PTR(pAhciPortR3->pDrvMedia),
    51195182                    ("AHCI configuration error: LUN#%d misses the basic media interface!\n", pAhciPort->iLUN),
    51205183                    VERR_PDM_MISSING_INTERFACE);
    51215184
    51225185    /* Get the extended media interface. */
    5123     pAhciPort->pDrvMediaEx = PDMIBASE_QUERY_INTERFACE(pAhciPort->pDrvBase, PDMIMEDIAEX);
    5124     AssertMsgReturn(VALID_PTR(pAhciPort->pDrvMediaEx),
     5186    pAhciPortR3->pDrvMediaEx = PDMIBASE_QUERY_INTERFACE(pAhciPortR3->pDrvBase, PDMIMEDIAEX);
     5187    AssertMsgReturn(VALID_PTR(pAhciPortR3->pDrvMediaEx),
    51255188                    ("AHCI configuration error: LUN#%d misses the extended media interface!\n", pAhciPort->iLUN),
    51265189                    VERR_PDM_MISSING_INTERFACE);
     
    51295192     * Validate type.
    51305193     */
    5131     PDMMEDIATYPE enmType = pAhciPort->pDrvMedia->pfnGetType(pAhciPort->pDrvMedia);
     5194    PDMMEDIATYPE enmType = pAhciPortR3->pDrvMedia->pfnGetType(pAhciPortR3->pDrvMedia);
    51325195    AssertMsgReturn(enmType == PDMMEDIATYPE_HARD_DISK || enmType == PDMMEDIATYPE_CDROM || enmType == PDMMEDIATYPE_DVD,
    51335196                    ("AHCI configuration error: LUN#%d isn't a disk or cd/dvd. enmType=%u\n", pAhciPort->iLUN, enmType),
    51345197                    VERR_PDM_UNSUPPORTED_BLOCK_TYPE);
    51355198
    5136     int rc = pAhciPort->pDrvMediaEx->pfnIoReqAllocSizeSet(pAhciPort->pDrvMediaEx, sizeof(AHCIREQ));
     5199    int rc = pAhciPortR3->pDrvMediaEx->pfnIoReqAllocSizeSet(pAhciPortR3->pDrvMediaEx, sizeof(AHCIREQ));
    51375200    if (RT_FAILURE(rc))
    51385201        return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
     
    51415204
    51425205    uint32_t fFeatures = 0;
    5143     rc = pAhciPort->pDrvMediaEx->pfnQueryFeatures(pAhciPort->pDrvMediaEx, &fFeatures);
     5206    rc = pAhciPortR3->pDrvMediaEx->pfnQueryFeatures(pAhciPortR3->pDrvMediaEx, &fFeatures);
    51445207    if (RT_FAILURE(rc))
    51455208        return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
     
    51505213        pAhciPort->fTrimEnabled = true;
    51515214
     5215    pAhciPort->fPresent = true;
     5216
    51525217    pAhciPort->fATAPI =    (enmType == PDMMEDIATYPE_CDROM || enmType == PDMMEDIATYPE_DVD)
    51535218                        && RT_BOOL(fFeatures & PDMIMEDIAEX_FEATURE_F_RAWSCSICMD);
     
    51615226    else
    51625227    {
    5163         pAhciPort->cbSector = pAhciPort->pDrvMedia->pfnGetSectorSize(pAhciPort->pDrvMedia);
    5164         pAhciPort->cTotalSectors = pAhciPort->pDrvMedia->pfnGetSize(pAhciPort->pDrvMedia) / pAhciPort->cbSector;
    5165         rc = pAhciPort->pDrvMedia->pfnBiosGetPCHSGeometry(pAhciPort->pDrvMedia, &pAhciPort->PCHSGeometry);
     5228        pAhciPort->cbSector = pAhciPortR3->pDrvMedia->pfnGetSectorSize(pAhciPortR3->pDrvMedia);
     5229        pAhciPort->cTotalSectors = pAhciPortR3->pDrvMedia->pfnGetSize(pAhciPortR3->pDrvMedia) / pAhciPort->cbSector;
     5230        rc = pAhciPortR3->pDrvMedia->pfnBiosGetPCHSGeometry(pAhciPortR3->pDrvMedia, &pAhciPort->PCHSGeometry);
    51665231        if (rc == VERR_PDM_MEDIA_NOT_MOUNTED)
    51675232        {
     
    51865251            pAhciPort->PCHSGeometry.cSectors = 63;
    51875252            /* Set the disk geometry information. Ignore errors. */
    5188             pAhciPort->pDrvMedia->pfnBiosSetPCHSGeometry(pAhciPort->pDrvMedia, &pAhciPort->PCHSGeometry);
     5253            pAhciPortR3->pDrvMedia->pfnBiosSetPCHSGeometry(pAhciPortR3->pDrvMedia, &pAhciPort->PCHSGeometry);
    51895254            rc = VINF_SUCCESS;
    51905255        }
     
    52105275        return false;
    52115276
    5212     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5213     ASMAtomicWriteBool(&pThis->fSignalIdle, false);
     5277    PAHCIR3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5278    ASMAtomicWriteBool(&pThisCC->fSignalIdle, false);
    52145279    return true;
    52155280}
     
    52205285static void ahciR3SuspendOrPowerOff(PPDMDEVINS pDevIns)
    52215286{
    5222     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5223 
    5224     ASMAtomicWriteBool(&pThis->fSignalIdle, true);
     5287    PAHCIR3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5288
     5289    ASMAtomicWriteBool(&pThisCC->fSignalIdle, true);
    52255290    if (!ahciR3AllAsyncIOIsFinished(pDevIns))
    52265291        PDMDevHlpSetAsyncNotification(pDevIns, ahciR3IsAsyncSuspendOrPowerOffDone);
    52275292    else
    5228         ASMAtomicWriteBool(&pThis->fSignalIdle, false);
    5229 
    5230     for (uint32_t i = 0; i < RT_ELEMENTS(pThis->ahciPort); i++)
    5231     {
    5232         PAHCIPort pThisPort = &pThis->ahciPort[i];
     5293        ASMAtomicWriteBool(&pThisCC->fSignalIdle, false);
     5294
     5295    for (uint32_t i = 0; i < RT_ELEMENTS(pThisCC->aPorts); i++)
     5296    {
     5297        PAHCIPORTR3 pThisPort = &pThisCC->aPorts[i];
    52335298        if (pThisPort->pDrvMediaEx)
    52345299            pThisPort->pDrvMediaEx->pfnNotifySuspend(pThisPort->pDrvMediaEx);
     
    52625327    for (unsigned i = 0; i < RT_ELEMENTS(pThis->ahciPort); i++)
    52635328    {
    5264         PAHCIPort pAhciPort = &pThis->ahciPort[i];
     5329        PAHCIPORT pAhciPort = &pThis->ahciPort[i];
    52655330
    52665331        if (pAhciPort->u32TasksRedo)
     
    52855350 *
    52865351 * @returns VBox status code.
    5287  * @param   pDevIns      The device instance.
    5288  * @param   pAhciPort    The attached device.
    5289  * @param   pszName      Name of the port to get the CFGM node.
    5290  */
    5291 static int ahciR3VpdInit(PPDMDEVINS pDevIns, PAHCIPort pAhciPort, const char *pszName)
     5352 * @param   pDevIns         The device instance.
     5353 * @param   pAhciPort       The attached device, shared bits.
     5354 * @param   pAhciPortR3     The attached device, ring-3 bits.
     5355 * @param   pszName         Name of the port to get the CFGM node.
     5356 */
     5357static int ahciR3VpdInit(PPDMDEVINS pDevIns, PAHCIPORT pAhciPort, PAHCIPORTR3 pAhciPortR3, const char *pszName)
    52925358{
    52935359    PCPDMDEVHLPR3   pHlp = pDevIns->pHlpR3;
     
    52985364
    52995365    int rc = VINF_SUCCESS;
    5300     if (pAhciPort->pDrvMedia)
    5301         rc = pAhciPort->pDrvMedia->pfnGetUuid(pAhciPort->pDrvMedia, &Uuid);
     5366    if (pAhciPortR3->pDrvMedia)
     5367        rc = pAhciPortR3->pDrvMedia->pfnGetUuid(pAhciPortR3->pDrvMedia, &Uuid);
    53025368    else
    53035369        RTUuidClear(&Uuid);
     
    54015467static DECLCALLBACK(void) ahciR3Detach(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags)
    54025468{
    5403     PAHCI           pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5404     PAHCIPort       pAhciPort = &pThis->ahciPort[iLUN];
    5405     int             rc = VINF_SUCCESS;
     5469    PAHCI       pThis  = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5470    PAHCIR3     pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5471    int         rc = VINF_SUCCESS;
    54065472
    54075473    Log(("%s:\n", __FUNCTION__));
    54085474
    5409     AssertMsg(iLUN < pThis->cPortsImpl, ("iLUN=%u", iLUN));
     5475    AssertMsgReturnVoid(iLUN < RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThisCC->aPorts)), ("iLUN=%u", iLUN));
     5476    PAHCIPORT   pAhciPort   = &pThis->ahciPort[iLUN];
     5477    PAHCIPORTR3 pAhciPortR3 = &pThisCC->aPorts[iLUN];
    54105478    AssertMsgReturnVoid(   pAhciPort->fHotpluggable
    54115479                        || (fFlags & PDM_TACH_FLAGS_NOT_HOT_PLUG),
     
    54135481
    54145482
    5415     if (pAhciPort->pAsyncIOThread)
     5483    if (pAhciPortR3->pAsyncIOThread)
    54165484    {
    54175485        int rcThread;
    54185486        /* Destroy the thread. */
    5419         rc = PDMDevHlpThreadDestroy(pDevIns, pAhciPort->pAsyncIOThread, &rcThread);
     5487        rc = PDMDevHlpThreadDestroy(pDevIns, pAhciPortR3->pAsyncIOThread, &rcThread);
    54205488        if (RT_FAILURE(rc) || RT_FAILURE(rcThread))
    54215489            AssertMsgFailed(("%s Failed to destroy async IO thread rc=%Rrc rcThread=%Rrc\n", __FUNCTION__, rc, rcThread));
    54225490
    5423         pAhciPort->pAsyncIOThread = NULL;
     5491        pAhciPortR3->pAsyncIOThread = NULL;
    54245492        pAhciPort->fWrkThreadSleeping = true;
    54255493    }
     
    54405508        ASMAtomicOrU32(&pAhciPort->regSERR, AHCI_PORT_SERR_X | AHCI_PORT_SERR_N);
    54415509        if (pAhciPort->regIE & (AHCI_PORT_IE_CPDE | AHCI_PORT_IE_PCE | AHCI_PORT_IE_PRCE))
    5442             ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     5510            ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    54435511    }
    54445512
     
    54465514     * Zero some important members.
    54475515     */
    5448     pAhciPort->pDrvBase = NULL;
    5449     pAhciPort->pDrvMedia = NULL;
    5450     pAhciPort->pDrvMediaEx = NULL;
     5516    pAhciPortR3->pDrvBase    = NULL;
     5517    pAhciPortR3->pDrvMedia   = NULL;
     5518    pAhciPortR3->pDrvMediaEx = NULL;
     5519    pAhciPort->fPresent      = false;
    54515520}
    54525521
     
    54645533static DECLCALLBACK(int)  ahciR3Attach(PPDMDEVINS pDevIns, unsigned iLUN, uint32_t fFlags)
    54655534{
    5466     PAHCI       pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5467     PAHCIPort   pAhciPort = &pThis->ahciPort[iLUN];
     5535    PAHCI       pThis     = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5536    PAHCIR3     pThisCC   = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
    54685537    int         rc;
    54695538
     
    54715540
    54725541    /* the usual paranoia */
    5473     AssertMsg(iLUN < pThis->cPortsImpl, ("iLUN=%u", iLUN));
    5474     AssertRelease(!pAhciPort->pDrvBase);
    5475     AssertRelease(!pAhciPort->pDrvMedia);
    5476     AssertRelease(!pAhciPort->pDrvMediaEx);
     5542    AssertMsgReturn(iLUN < RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThisCC->aPorts)), ("iLUN=%u", iLUN), VERR_PDM_LUN_NOT_FOUND);
     5543    PAHCIPORT   pAhciPort   = &pThis->ahciPort[iLUN];
     5544    PAHCIPORTR3 pAhciPortR3 = &pThisCC->aPorts[iLUN];
     5545    AssertRelease(!pAhciPortR3->pDrvBase);
     5546    AssertRelease(!pAhciPortR3->pDrvMedia);
     5547    AssertRelease(!pAhciPortR3->pDrvMediaEx);
    54775548    Assert(pAhciPort->iLUN == iLUN);
     5549    Assert(pAhciPortR3->iLUN == iLUN);
    54785550
    54795551    AssertMsgReturn(   pAhciPort->fHotpluggable
     
    54865558     * required as well as optional.
    54875559     */
    5488     rc = PDMDevHlpDriverAttach(pDevIns, pAhciPort->iLUN, &pAhciPort->IBase, &pAhciPort->pDrvBase, pAhciPort->pszDesc);
     5560    rc = PDMDevHlpDriverAttach(pDevIns, pAhciPort->iLUN, &pAhciPortR3->IBase, &pAhciPortR3->pDrvBase, pAhciPortR3->szDesc);
    54895561    if (RT_SUCCESS(rc))
    5490         rc = ahciR3ConfigureLUN(pDevIns, pAhciPort);
     5562        rc = ahciR3ConfigureLUN(pDevIns, pAhciPort, pAhciPortR3);
    54915563    else
    54925564        AssertMsgFailed(("Failed to attach LUN#%d. rc=%Rrc\n", pAhciPort->iLUN, rc));
     
    54945566    if (RT_FAILURE(rc))
    54955567    {
    5496         pAhciPort->pDrvBase = NULL;
    5497         pAhciPort->pDrvMedia = NULL;
     5568        pAhciPortR3->pDrvBase    = NULL;
     5569        pAhciPortR3->pDrvMedia   = NULL;
     5570        pAhciPortR3->pDrvMediaEx = NULL;
     5571        pAhciPort->fPresent      = false;
    54985572    }
    54995573    else
     
    55055579
    55065580        /* Create the async IO thread. */
    5507         rc = PDMDevHlpThreadCreate(pDevIns, &pAhciPort->pAsyncIOThread, pAhciPort, ahciAsyncIOLoop, ahciAsyncIOLoopWakeUp, 0,
    5508                                    RTTHREADTYPE_IO, pAhciPort->pszDesc);
     5581        rc = PDMDevHlpThreadCreate(pDevIns, &pAhciPortR3->pAsyncIOThread, pAhciPortR3, ahciAsyncIOLoop,
     5582                                   ahciAsyncIOLoopWakeUp, 0, RTTHREADTYPE_IO, pAhciPortR3->szDesc);
    55095583        if (RT_FAILURE(rc))
    55105584            return rc;
     
    55145588         */
    55155589        if (RT_SUCCESS(rc))
    5516             rc = ahciR3VpdInit(pDevIns, pAhciPort, pAhciPort->pszDesc);
     5590            rc = ahciR3VpdInit(pDevIns, pAhciPort, pAhciPortR3, pAhciPortR3->szDesc);
    55175591
    55185592        /* Inform the guest about the added device in case of hotplugging. */
     
    55425616                || (pAhciPort->regIE & AHCI_PORT_IE_PCE)
    55435617                || (pAhciPort->regIE & AHCI_PORT_IE_PRCE))
    5544                 ahciHbaSetInterrupt(pAhciPort->CTX_SUFF(pAhci), pAhciPort->iLUN, VERR_IGNORED);
     5618                ahciHbaSetInterrupt(pDevIns, pThis, pAhciPort->iLUN, VERR_IGNORED);
    55455619        }
    55465620
     
    55575631static int ahciR3ResetCommon(PPDMDEVINS pDevIns)
    55585632{
    5559     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5560 
    5561     ahciHBAReset(pThis);
     5633    PAHCI   pThis  = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5634    PAHCIR3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5635    ahciR3HBAReset(pDevIns, pThis, pThisCC);
    55625636
    55635637    /* Hardware reset for the ports. */
     
    55755649static DECLCALLBACK(bool) ahciR3IsAsyncResetDone(PPDMDEVINS pDevIns)
    55765650{
    5577     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5651    PAHCIR3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
    55785652
    55795653    if (!ahciR3AllAsyncIOIsFinished(pDevIns))
    55805654        return false;
    5581     ASMAtomicWriteBool(&pThis->fSignalIdle, false);
     5655    ASMAtomicWriteBool(&pThisCC->fSignalIdle, false);
    55825656
    55835657    ahciR3ResetCommon(pDevIns);
     
    55925666static DECLCALLBACK(void) ahciR3Reset(PPDMDEVINS pDevIns)
    55935667{
    5594     PAHCI pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5595 
    5596     ASMAtomicWriteBool(&pThis->fSignalIdle, true);
     5668    PAHCIR3 pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5669
     5670    ASMAtomicWriteBool(&pThisCC->fSignalIdle, true);
    55975671    if (!ahciR3AllAsyncIOIsFinished(pDevIns))
    55985672        PDMDevHlpSetAsyncNotification(pDevIns, ahciR3IsAsyncResetDone);
    55995673    else
    56005674    {
    5601         ASMAtomicWriteBool(&pThis->fSignalIdle, false);
     5675        ASMAtomicWriteBool(&pThisCC->fSignalIdle, false);
    56025676        ahciR3ResetCommon(pDevIns);
    56035677    }
     
    56265700{
    56275701    PDMDEV_CHECK_VERSIONS_RETURN_QUIET(pDevIns);
    5628     PAHCI       pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5629     int         rc    = VINF_SUCCESS;
     5702    PAHCI   pThis  = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5703    int     rc      = VINF_SUCCESS;
    56305704
    56315705    /*
     
    56405714
    56415715        Log(("%s: Destruct every port\n", __FUNCTION__));
    5642         for (unsigned iActPort = 0; iActPort < pThis->cPortsImpl; iActPort++)
    5643         {
    5644             PAHCIPort pAhciPort = &pThis->ahciPort[iActPort];
     5716        uint32_t const cPortsImpl = RT_MIN(pThis->cPortsImpl, RT_ELEMENTS(pThis->ahciPort));
     5717        for (unsigned iActPort = 0; iActPort < cPortsImpl; iActPort++)
     5718        {
     5719            PAHCIPORT pAhciPort = &pThis->ahciPort[iActPort];
    56455720
    56465721            if (pAhciPort->hEvtProcess != NIL_SUPSEMEVENT)
     
    56495724                pAhciPort->hEvtProcess = NIL_SUPSEMEVENT;
    56505725            }
    5651 
    5652             if (pAhciPort->pszDesc)
    5653                 RTStrFree(pAhciPort->pszDesc);
    56545726        }
    56555727
     
    56665738{
    56675739    PDMDEV_CHECK_VERSIONS_RETURN(pDevIns);
    5668     PAHCI           pThis = PDMDEVINS_2_DATA(pDevIns, PAHCI);
    5669     PCPDMDEVHLPR3   pHlp  = pDevIns->pHlpR3;
     5740    PAHCI           pThis   = PDMDEVINS_2_DATA(pDevIns, PAHCI);
     5741    PAHCIR3         pThisCC = PDMDEVINS_2_DATA_CC(pDevIns, PAHCICC);
     5742    PCPDMDEVHLPR3   pHlp    = pDevIns->pHlpR3;
    56705743    PPDMIBASE       pBase;
    5671     int             rc = VINF_SUCCESS;
    5672     unsigned        i = 0;
    5673     uint32_t        cbTotalBufferSize = 0;
     5744    int             rc;
     5745    unsigned        i;
     5746    uint32_t        cbTotalBufferSize = 0; /** @todo r=bird: cbTotalBufferSize isn't ever set. */
    56745747
    56755748    LogFlowFunc(("pThis=%#p\n", pThis));
     5749    /*
     5750     * Initialize the instance data (everything touched by the destructor need
     5751     * to be initialized here!).
     5752     */
     5753    PPDMPCIDEV pPciDev = pDevIns->apPciDevs[0];
     5754    PDMPCIDEV_ASSERT_VALID(pDevIns, pPciDev);
     5755
     5756    PDMPciDevSetVendorId(pPciDev,          0x8086); /* Intel */
     5757    PDMPciDevSetDeviceId(pPciDev,          0x2829); /* ICH-8M */
     5758    PDMPciDevSetCommand(pPciDev,           0x0000);
     5759#ifdef VBOX_WITH_MSI_DEVICES
     5760    PDMPciDevSetStatus(pPciDev,            VBOX_PCI_STATUS_CAP_LIST);
     5761    PDMPciDevSetCapabilityList(pPciDev,    0x80);
     5762#else
     5763    PDMPciDevSetCapabilityList(pPciDev,    0x70);
     5764#endif
     5765    PDMPciDevSetRevisionId(pPciDev,        0x02);
     5766    PDMPciDevSetClassProg(pPciDev,         0x01);
     5767    PDMPciDevSetClassSub(pPciDev,          0x06);
     5768    PDMPciDevSetClassBase(pPciDev,         0x01);
     5769    PDMPciDevSetBaseAddress(pPciDev, 5, false, false, false, 0x00000000);
     5770
     5771    PDMPciDevSetInterruptLine(pPciDev,     0x00);
     5772    PDMPciDevSetInterruptPin(pPciDev,      0x01);
     5773
     5774    PDMPciDevSetByte(pPciDev,  0x70,       VBOX_PCI_CAP_ID_PM); /* Capability ID: PCI Power Management Interface */
     5775    PDMPciDevSetByte(pPciDev,  0x71,       0xa8); /* next */
     5776    PDMPciDevSetByte(pPciDev,  0x72,       0x03); /* version ? */
     5777
     5778    PDMPciDevSetByte(pPciDev,  0x90,       0x40); /* AHCI mode. */
     5779    PDMPciDevSetByte(pPciDev,  0x92,       0x3f);
     5780    PDMPciDevSetByte(pPciDev,  0x94,       0x80);
     5781    PDMPciDevSetByte(pPciDev,  0x95,       0x01);
     5782    PDMPciDevSetByte(pPciDev,  0x97,       0x78);
     5783
     5784    PDMPciDevSetByte(pPciDev,  0xa8,       0x12);              /* SATACR capability */
     5785    PDMPciDevSetByte(pPciDev,  0xa9,       0x00);              /* next */
     5786    PDMPciDevSetWord(pPciDev,  0xaa,       0x0010);      /* Revision */
     5787    PDMPciDevSetDWord(pPciDev, 0xac,       0x00000028); /* SATA Capability Register 1 */
     5788
     5789    pThis->cThreadsActive = 0;
     5790
     5791    pThisCC->pDevIns                 = pDevIns;
     5792    pThisCC->IBase.pfnQueryInterface = ahciR3Status_QueryInterface;
     5793    pThisCC->ILeds.pfnQueryStatusLed = ahciR3Status_QueryStatusLed;
     5794
     5795    /* Initialize port members. */
     5796    for (i = 0; i < AHCI_MAX_NR_PORTS_IMPL; i++)
     5797    {
     5798        PAHCIPORT   pAhciPort           = &pThis->ahciPort[i];
     5799        PAHCIPORTR3 pAhciPortR3         = &pThisCC->aPorts[i];
     5800        pAhciPortR3->pDevIns            = pDevIns;
     5801        pAhciPort->iLUN                 = i;
     5802        pAhciPortR3->iLUN               = i;
     5803        pAhciPort->Led.u32Magic         = PDMLED_MAGIC;
     5804        pAhciPortR3->pDrvBase           = NULL;
     5805        pAhciPortR3->pAsyncIOThread     = NULL;
     5806        pAhciPort->hEvtProcess          = NIL_SUPSEMEVENT;
     5807        pAhciPort->fHotpluggable        = true;
     5808    }
     5809
     5810    /*
     5811     * Init locks, using explicit locking where necessary.
     5812     */
     5813    rc = PDMDevHlpSetDeviceCritSect(pDevIns, PDMDevHlpCritSectGetNop(pDevIns));
     5814    AssertRCReturn(rc, rc);
     5815
     5816    rc = PDMDevHlpCritSectInit(pDevIns, &pThis->lock, RT_SRC_POS, "AHCI#%u", iInstance);
     5817    if (RT_FAILURE(rc))
     5818    {
     5819        Log(("%s: Failed to create critical section.\n", __FUNCTION__));
     5820        return rc;
     5821    }
    56765822
    56775823    /*
     
    57185864        return PDMDEV_SET_ERROR(pDevIns, rc, N_("AHCI configuration error: failed to read TigerHack as boolean"));
    57195865
    5720     /*
    5721      * Initialize the instance data (everything touched by the destructor need
    5722      * to be initialized here!).
    5723      */
    5724     pThis->pDevInsR3 = pDevIns;
    5725     pThis->pDevInsR0 = PDMDEVINS_2_R0PTR(pDevIns);
    5726     pThis->pDevInsRC = PDMDEVINS_2_RCPTR(pDevIns);
    5727 
    5728     PPDMPCIDEV pPciDev = pDevIns->apPciDevs[0];
    5729     PDMPCIDEV_ASSERT_VALID(pDevIns, pPciDev);
    5730 
    5731     PDMPciDevSetVendorId(pPciDev,          0x8086); /* Intel */
    5732     PDMPciDevSetDeviceId(pPciDev,          0x2829); /* ICH-8M */
    5733     PDMPciDevSetCommand(pPciDev,           0x0000);
    5734 #ifdef VBOX_WITH_MSI_DEVICES
    5735     PDMPciDevSetStatus(pPciDev,            VBOX_PCI_STATUS_CAP_LIST);
    5736     PDMPciDevSetCapabilityList(pPciDev,    0x80);
    5737 #else
    5738     PDMPciDevSetCapabilityList(pPciDev,    0x70);
    5739 #endif
    5740     PDMPciDevSetRevisionId(pPciDev,        0x02);
    5741     PDMPciDevSetClassProg(pPciDev,         0x01);
    5742     PDMPciDevSetClassSub(pPciDev,          0x06);
    5743     PDMPciDevSetClassBase(pPciDev,         0x01);
    5744     PDMPciDevSetBaseAddress(pPciDev, 5, false, false, false, 0x00000000);
    5745 
    5746     PDMPciDevSetInterruptLine(pPciDev,     0x00);
    5747     PDMPciDevSetInterruptPin(pPciDev,      0x01);
    5748 
    5749     PDMPciDevSetByte(pPciDev,  0x70,       VBOX_PCI_CAP_ID_PM); /* Capability ID: PCI Power Management Interface */
    5750     PDMPciDevSetByte(pPciDev,  0x71,       0xa8); /* next */
    5751     PDMPciDevSetByte(pPciDev,  0x72,       0x03); /* version ? */
    5752 
    5753     PDMPciDevSetByte(pPciDev,  0x90,       0x40); /* AHCI mode. */
    5754     PDMPciDevSetByte(pPciDev,  0x92,       0x3f);
    5755     PDMPciDevSetByte(pPciDev,  0x94,       0x80);
    5756     PDMPciDevSetByte(pPciDev,  0x95,       0x01);
    5757     PDMPciDevSetByte(pPciDev,  0x97,       0x78);
    5758 
    5759     PDMPciDevSetByte(pPciDev,  0xa8,       0x12);              /* SATACR capability */
    5760     PDMPciDevSetByte(pPciDev,  0xa9,       0x00);              /* next */
    5761     PDMPciDevSetWord(pPciDev,  0xaa,       0x0010);      /* Revision */
    5762     PDMPciDevSetDWord(pPciDev, 0xac,       0x00000028); /* SATA Capability Register 1 */
    5763 
    5764     pThis->cThreadsActive = 0;
    5765 
    5766     pThis->IBase.pfnQueryInterface = ahciR3Status_QueryInterface;
    5767     pThis->ILeds.pfnQueryStatusLed = ahciR3Status_QueryStatusLed;
    5768 
    5769     /* Initialize port members. */
    5770     for (i = 0; i < AHCI_MAX_NR_PORTS_IMPL; i++)
    5771     {
    5772         PAHCIPort pAhciPort             = &pThis->ahciPort[i];
    5773         pAhciPort->pDevInsR3            = pDevIns;
    5774         pAhciPort->pDevInsR0            = PDMDEVINS_2_R0PTR(pDevIns);
    5775         pAhciPort->pDevInsRC            = PDMDEVINS_2_RCPTR(pDevIns);
    5776         pAhciPort->iLUN                 = i;
    5777         pAhciPort->pAhciR3              = pThis;
    5778         pAhciPort->pAhciR0              = PDMINS_2_DATA_R0PTR(pDevIns);
    5779         pAhciPort->pAhciRC              = PDMINS_2_DATA_RCPTR(pDevIns);
    5780         pAhciPort->Led.u32Magic         = PDMLED_MAGIC;
    5781         pAhciPort->pDrvBase             = NULL;
    5782         pAhciPort->pAsyncIOThread       = NULL;
    5783         pAhciPort->hEvtProcess          = NIL_SUPSEMEVENT;
    5784         pAhciPort->fHotpluggable        = true;
    5785     }
    5786 
    5787     /*
    5788      * Init locks, using explicit locking where necessary.
    5789      */
    5790     rc = PDMDevHlpSetDeviceCritSect(pDevIns, PDMDevHlpCritSectGetNop(pDevIns));
    5791     AssertRCReturn(rc, rc);
    5792 
    5793     rc = PDMDevHlpCritSectInit(pDevIns, &pThis->lock, RT_SRC_POS, "AHCI#%u", iInstance);
    5794     if (RT_FAILURE(rc))
    5795     {
    5796         Log(("%s: Failed to create critical section.\n", __FUNCTION__));
    5797         return rc;
    5798     }
    57995866
    58005867    /*
     
    58855952    for (i = 0; i < pThis->cPortsImpl; i++)
    58865953    {
    5887         PAHCIPort pAhciPort      = &pThis->ahciPort[i];
    5888 
    5889         if (RTStrAPrintf(&pAhciPort->pszDesc, "Port%u", i) <= 0)
    5890             AssertLogRelFailedReturn(VERR_NO_MEMORY);
     5954        PAHCIPORT   pAhciPort   = &pThis->ahciPort[i];
     5955        PAHCIPORTR3 pAhciPortR3 = &pThisCC->aPorts[i];
     5956
     5957        RTStrPrintf(pAhciPortR3->szDesc, sizeof(pAhciPortR3->szDesc), "Port%u", i);
    58915958
    58925959        /*
    58935960         * Init interfaces.
    58945961         */
    5895         pAhciPort->IBase.pfnQueryInterface                 = ahciR3PortQueryInterface;
    5896         pAhciPort->IMediaExPort.pfnIoReqCompleteNotify     = ahciR3IoReqCompleteNotify;
    5897         pAhciPort->IMediaExPort.pfnIoReqCopyFromBuf        = ahciR3IoReqCopyFromBuf;
    5898         pAhciPort->IMediaExPort.pfnIoReqCopyToBuf          = ahciR3IoReqCopyToBuf;
    5899         pAhciPort->IMediaExPort.pfnIoReqQueryBuf           = ahciR3IoReqQueryBuf;
    5900         pAhciPort->IMediaExPort.pfnIoReqQueryDiscardRanges = ahciR3IoReqQueryDiscardRanges;
    5901         pAhciPort->IMediaExPort.pfnIoReqStateChanged       = ahciR3IoReqStateChanged;
    5902         pAhciPort->IMediaExPort.pfnMediumEjected           = ahciR3MediumEjected;
    5903         pAhciPort->IPort.pfnQueryDeviceLocation            = ahciR3PortQueryDeviceLocation;
    5904         pAhciPort->IPort.pfnQueryScsiInqStrings            = ahciR3PortQueryScsiInqStrings;
    5905         pAhciPort->fWrkThreadSleeping                      = true;
     5962        pAhciPortR3->IBase.pfnQueryInterface                 = ahciR3PortQueryInterface;
     5963        pAhciPortR3->IMediaExPort.pfnIoReqCompleteNotify     = ahciR3IoReqCompleteNotify;
     5964        pAhciPortR3->IMediaExPort.pfnIoReqCopyFromBuf        = ahciR3IoReqCopyFromBuf;
     5965        pAhciPortR3->IMediaExPort.pfnIoReqCopyToBuf          = ahciR3IoReqCopyToBuf;
     5966        pAhciPortR3->IMediaExPort.pfnIoReqQueryBuf           = ahciR3IoReqQueryBuf;
     5967        pAhciPortR3->IMediaExPort.pfnIoReqQueryDiscardRanges = ahciR3IoReqQueryDiscardRanges;
     5968        pAhciPortR3->IMediaExPort.pfnIoReqStateChanged       = ahciR3IoReqStateChanged;
     5969        pAhciPortR3->IMediaExPort.pfnMediumEjected           = ahciR3MediumEjected;
     5970        pAhciPortR3->IPort.pfnQueryDeviceLocation            = ahciR3PortQueryDeviceLocation;
     5971        pAhciPortR3->IPort.pfnQueryScsiInqStrings            = ahciR3PortQueryScsiInqStrings;
     5972        pAhciPort->fWrkThreadSleeping                        = true;
    59065973
    59075974        /* Query per port configuration options if available. */
    5908         PCFGMNODE pCfgPort = pHlp->pfnCFGMGetChild(pDevIns->pCfg, pAhciPort->pszDesc);
     5975        PCFGMNODE pCfgPort = pHlp->pfnCFGMGetChild(pDevIns->pCfg, pAhciPortR3->szDesc);
    59095976        if (pCfgPort)
    59105977        {
     
    59175984         * Attach the block driver
    59185985         */
    5919         rc = PDMDevHlpDriverAttach(pDevIns, pAhciPort->iLUN, &pAhciPort->IBase, &pAhciPort->pDrvBase, pAhciPort->pszDesc);
     5986        rc = PDMDevHlpDriverAttach(pDevIns, pAhciPort->iLUN, &pAhciPortR3->IBase, &pAhciPortR3->pDrvBase, pAhciPortR3->szDesc);
    59205987        if (RT_SUCCESS(rc))
    59215988        {
    5922             rc = ahciR3ConfigureLUN(pDevIns, pAhciPort);
     5989            rc = ahciR3ConfigureLUN(pDevIns, pAhciPort, pAhciPortR3);
    59235990            if (RT_FAILURE(rc))
    59245991            {
    5925                 Log(("%s: Failed to configure the %s.\n", __FUNCTION__, pAhciPort->pszDesc));
     5992                Log(("%s: Failed to configure the %s.\n", __FUNCTION__, pAhciPortR3->szDesc));
    59265993                return rc;
    59275994            }
     
    59346001             * Init vendor product data.
    59356002             */
    5936             rc = ahciR3VpdInit(pDevIns, pAhciPort, pAhciPort->pszDesc);
     6003            rc = ahciR3VpdInit(pDevIns, pAhciPort, pAhciPortR3, pAhciPortR3->szDesc);
    59376004            if (RT_FAILURE(rc))
    59386005                return rc;
     
    59436010                                           N_("AHCI: Failed to create SUP event semaphore"));
    59446011
    5945             rc = PDMDevHlpThreadCreate(pDevIns, &pAhciPort->pAsyncIOThread, pAhciPort, ahciAsyncIOLoop,
    5946                                        ahciAsyncIOLoopWakeUp, 0, RTTHREADTYPE_IO, pAhciPort->pszDesc);
     6012            rc = PDMDevHlpThreadCreate(pDevIns, &pAhciPortR3->pAsyncIOThread, pAhciPortR3, ahciAsyncIOLoop,
     6013                                       ahciAsyncIOLoopWakeUp, 0, RTTHREADTYPE_IO, pAhciPortR3->szDesc);
    59476014            if (RT_FAILURE(rc))
    59486015                return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
    5949                                            N_("AHCI: Failed to create worker thread %s"), pAhciPort->pszDesc);
     6016                                           N_("AHCI: Failed to create worker thread %s"), pAhciPortR3->szDesc);
    59506017        }
    59516018        else if (rc == VERR_PDM_NO_ATTACHED_DRIVER)
    59526019        {
    5953             pAhciPort->pDrvBase = NULL;
     6020            pAhciPortR3->pDrvBase = NULL;
     6021            pAhciPort->fPresent   = false;
    59546022            rc = VINF_SUCCESS;
    5955             LogRel(("AHCI: %s: No driver attached\n", pAhciPort->pszDesc));
     6023            LogRel(("AHCI: %s: No driver attached\n", pAhciPortR3->szDesc));
    59566024        }
    59576025        else
    59586026            return PDMDevHlpVMSetError(pDevIns, rc, RT_SRC_POS,
    5959                                        N_("AHCI: Failed to attach drive to %s"), pAhciPort->pszDesc);
     6027                                       N_("AHCI: Failed to attach drive to %s"), pAhciPortR3->szDesc);
    59606028    }
    59616029
     
    59636031     * Attach status driver (optional).
    59646032     */
    5965     rc = PDMDevHlpDriverAttach(pDevIns, PDM_STATUS_LUN, &pThis->IBase, &pBase, "Status Port");
     6033    rc = PDMDevHlpDriverAttach(pDevIns, PDM_STATUS_LUN, &pThisCC->IBase, &pBase, "Status Port");
    59666034    if (RT_SUCCESS(rc))
    59676035    {
    5968         pThis->pLedsConnector = PDMIBASE_QUERY_INTERFACE(pBase, PDMILEDCONNECTORS);
    5969         pThis->pMediaNotify = PDMIBASE_QUERY_INTERFACE(pBase, PDMIMEDIANOTIFY);
     6036        pThisCC->pLedsConnector = PDMIBASE_QUERY_INTERFACE(pBase, PDMILEDCONNECTORS);
     6037        pThisCC->pMediaNotify  = PDMIBASE_QUERY_INTERFACE(pBase, PDMIMEDIANOTIFY);
    59706038    }
    59716039    else
     
    60346102    /* .uReserved0 = */             0,
    60356103    /* .szName = */                 "ahci",
    6036     /* .fFlags = */                 PDM_DEVREG_FLAGS_DEFAULT_BITS | PDM_DEVREG_FLAGS_RZ |
    6037                                     PDM_DEVREG_FLAGS_FIRST_SUSPEND_NOTIFICATION | PDM_DEVREG_FLAGS_FIRST_POWEROFF_NOTIFICATION |
    6038                                     PDM_DEVREG_FLAGS_FIRST_RESET_NOTIFICATION,
     6104    /* .fFlags = */                 PDM_DEVREG_FLAGS_DEFAULT_BITS | PDM_DEVREG_FLAGS_RZ | PDM_DEVREG_FLAGS_NEW_STYLE
     6105                                    | PDM_DEVREG_FLAGS_FIRST_SUSPEND_NOTIFICATION | PDM_DEVREG_FLAGS_FIRST_POWEROFF_NOTIFICATION
     6106                                    | PDM_DEVREG_FLAGS_FIRST_RESET_NOTIFICATION,
    60396107    /* .fClass = */                 PDM_DEVREG_CLASS_STORAGE,
    60406108    /* .cMaxInstances = */          ~0U,
    60416109    /* .uSharedVersion = */         42,
    60426110    /* .cbInstanceShared = */       sizeof(AHCI),
    6043     /* .cbInstanceCC = */           0,
    6044     /* .cbInstanceRC = */           0,
     6111    /* .cbInstanceCC = */           sizeof(AHCICC),
     6112    /* .cbInstanceRC = */           sizeof(AHCIRC),
    60456113    /* .cMaxPciDevices = */         1,
    60466114    /* .cMaxMsixVectors = */        0,
     
    60516119    /* .pfnConstruct = */           ahciR3Construct,
    60526120    /* .pfnDestruct = */            ahciR3Destruct,
    6053     /* .pfnRelocate = */            ahciR3Relocate,
     6121    /* .pfnRelocate = */            NULL,
    60546122    /* .pfnMemSetup = */            NULL,
    60556123    /* .pfnPowerOn = */             NULL,
Note: See TracChangeset for help on using the changeset viewer.

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