VirtualBox

Changeset 85109 in vbox for trunk/src/VBox/Devices/VirtIO


Ignore:
Timestamp:
Jul 8, 2020 2:03:45 PM (5 years ago)
Author:
vboxsync
Message:

Resolved other part of xtracker #9766. Rearranged structs, arrays and pointers to improve cache locality (impacts: Network/DevVirtioNet.cpp, DevVirtioNet_1_0.cpp, and VirtIO/VirtioCore.*)

Location:
trunk/src/VBox/Devices/VirtIO
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/VirtIO/VirtioCore.cpp

    r85054 r85109  
    4343*********************************************************************************************************************************/
    4444#define INSTANCE(a_pVirtio)                 ((a_pVirtio)->szInstance)
    45 #define VIRTQNAME(a_pVirtio, a_uVirtqNbr)   ((a_pVirtio)->aVirtqState[(a_uVirtqNbr)].szVirtqName)
     45#define VIRTQNAME(a_pVirtio, a_uVirtq)      ((a_pVirtio)->aVirtqueues[(a_uVirtq)].szName)
     46
    4647#define IS_DRIVER_OK(a_pVirtio)             ((a_pVirtio)->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK)
    47 #define IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtqState) \
    48             (virtioCoreVirtqAvailBufCount(pDevIns, pVirtio, pVirtqState) == 0)
     48#define IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtq) \
     49            (virtioCoreVirtqAvailBufCount_inline(pDevIns, pVirtio, pVirtq) == 0)
    4950
    5051/**
     
    5354 * @a a_LocCapData.
    5455 *
    55  *
    56  *
    5756 * @param[in]  a_offAccess      Input:  The offset into the MMIO bar of the access.
    5857 * @param[in]  a_cbAccess       Input:  The access size.
     
    7877/** @name virtq related flags
    7978 * @{ */
    80 #define VIRTQ_DESC_F_NEXT                               1        /**< Indicates this descriptor chains to next  */
    81 #define VIRTQ_DESC_F_WRITE                              2        /**< Marks buffer as write-only (default ro)   */
    82 #define VIRTQ_DESC_F_INDIRECT                           4        /**< Buffer is list of buffer descriptors      */
    83 
    84 #define VIRTQ_USED_F_NO_NOTIFY                          1        /**< Dev to Drv: Don't notify when buf added   */
    85 #define VIRTQ_AVAIL_F_NO_INTERRUPT                      1        /**< Drv to Dev: Don't notify when buf eaten   */
     79#define VIRTQUEUE_DESC_F_NEXT                               1        /**< Indicates this descriptor chains to next  */
     80#define VIRTQUEUE_DESC_F_WRITE                              2        /**< Marks buffer as write-only (default ro)   */
     81#define VIRTQUEUE_DESC_F_INDIRECT                           4        /**< Buffer is list of buffer descriptors      */
     82
     83#define VIRTQUEUE_USED_F_NO_NOTIFY                          1        /**< Dev to Drv: Don't notify when buf added   */
     84#define VIRTQUEUE_AVAIL_F_NO_INTERRUPT                      1        /**< Drv to Dev: Don't notify when buf eaten   */
    8685/** @} */
    8786
     
    9695    uint16_t  fFlags;                                            /**< flags      Buffer specific flags          */
    9796    uint16_t  uDescIdxNext;                                      /**< next       Idx set if VIRTIO_DESC_F_NEXT  */
    98 } VIRTQ_DESC_T, *PVIRTQ_DESC_T;
     97} VIRTQUEUE_DESC_T, *PVIRTQUEUE_DESC_T;
    9998
    10099typedef struct virtq_avail
     
    104103    RT_FLEXIBLE_ARRAY_EXTENSION
    105104    uint16_t  auRing[RT_FLEXIBLE_ARRAY];                         /**< ring       Ring: avail drv to dev bufs    */
    106     //uint16_t  uUsedEventIdx;                                   /**< used_event (if VIRTQ_USED_F_EVENT_IDX)    */
    107 } VIRTQ_AVAIL_T, *PVIRTQ_AVAIL_T;
     105    //uint16_t  uUsedEventIdx;                                   /**< used_event (if VIRTQUEUE_USED_F_EVENT_IDX)    */
     106} VIRTQUEUE_AVAIL_T, *PVIRTQUEUE_AVAIL_T;
    108107
    109108typedef struct virtq_used_elem
     
    111110    uint32_t  uDescIdx;                                          /**< idx         Start of used desc chain      */
    112111    uint32_t  cbElem;                                            /**< len         Total len of used desc chain  */
    113 } VIRTQ_USED_ELEM_T;
     112} VIRTQUEUE_USED_ELEM_T;
    114113
    115114typedef struct virt_used
     
    118117    uint16_t  uIdx;                                              /**< idx         Index of next ring slot       */
    119118    RT_FLEXIBLE_ARRAY_EXTENSION
    120     VIRTQ_USED_ELEM_T aRing[RT_FLEXIBLE_ARRAY];                  /**< ring        Ring: used dev to drv bufs    */
    121     //uint16_t  uAvailEventIdx;                                  /**< avail_event if (VIRTQ_USED_F_EVENT_IDX)   */
    122 } VIRTQ_USED_T, *PVIRTQ_USED_T;
     119    VIRTQUEUE_USED_ELEM_T aRing[RT_FLEXIBLE_ARRAY];                  /**< ring        Ring: used dev to drv bufs    */
     120    //uint16_t  uAvailEventIdx;                                  /**< avail_event if (VIRTQUEUE_USED_F_EVENT_IDX)   */
     121} VIRTQUEUE_USED_T, *PVIRTQUEUE_USED_T;
    123122
    124123
     
    137136/* Internal Functions */
    138137
    139 static void virtioCoreNotifyGuestDriver(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr);
     138static void virtioCoreNotifyGuestDriver(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq);
    140139static int  virtioKick(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint8_t uCause, uint16_t uVec);
    141140
     
    147146 */
    148147#ifdef IN_RING3
    149 DECLINLINE(void) virtioReadDesc(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr,
    150                                 uint32_t idxDesc, PVIRTQ_DESC_T pDesc)
     148DECLINLINE(void) virtioReadDesc(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq,
     149                                uint32_t idxDesc, PVIRTQUEUE_DESC_T pDesc)
    151150{
    152151    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
    153     uint16_t const cVirtqItems = RT_MAX(pVirtio->uVirtqSize[uVirtqNbr], 1); /* Make sure to avoid div-by-zero. */
     152    RT_NOREF(pVirtio);
     153    uint16_t const cVirtqItems = RT_MAX(pVirtq->uSize, 1); /* Make sure to avoid div-by-zero. */
    154154    PDMDevHlpPCIPhysRead(pDevIns,
    155                       pVirtio->aGCPhysVirtqDesc[uVirtqNbr] + sizeof(VIRTQ_DESC_T) * (idxDesc % cVirtqItems),
    156                       pDesc, sizeof(VIRTQ_DESC_T));
     155                      pVirtq->GCPhysVirtqDesc + sizeof(VIRTQUEUE_DESC_T) * (idxDesc % cVirtqItems),
     156                      pDesc, sizeof(VIRTQUEUE_DESC_T));
    157157}
    158158#endif
     
    162162 */
    163163#ifdef IN_RING3
    164 DECLINLINE(uint16_t) virtioReadAvailDescIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, uint32_t availIdx)
     164DECLINLINE(uint16_t) virtioReadAvailDescIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq, uint32_t availIdx)
    165165{
    166166    uint16_t uDescIdx;
    167167    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
    168     uint16_t const cVirtqItems = RT_MAX(pVirtio->uVirtqSize[uVirtqNbr], 1); /* Make sure to avoid div-by-zero. */
     168    RT_NOREF(pVirtio);
     169    uint16_t const cVirtqItems = RT_MAX(pVirtq->uSize, 1); /* Make sure to avoid div-by-zero. */
    169170    PDMDevHlpPCIPhysRead(pDevIns,
    170                         pVirtio->aGCPhysVirtqAvail[uVirtqNbr]
    171                       + RT_UOFFSETOF_DYN(VIRTQ_AVAIL_T, auRing[availIdx % cVirtqItems]),
    172                       &uDescIdx, sizeof(uDescIdx));
     171                         pVirtq->GCPhysVirtqAvail + RT_UOFFSETOF_DYN(VIRTQUEUE_AVAIL_T, auRing[availIdx % cVirtqItems]),
     172                         &uDescIdx, sizeof(uDescIdx));
    173173    return uDescIdx;
    174174}
    175175
    176 DECLINLINE(uint16_t) virtioReadAvailUsedEvent(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
     176DECLINLINE(uint16_t) virtioReadAvailUsedEvent(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
    177177{
    178178    uint16_t uUsedEventIdx;
    179179    /* VirtIO 1.0 uUsedEventIdx (used_event) immediately follows ring */
    180180    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     181    RT_NOREF(pVirtio);
    181182    PDMDevHlpPCIPhysRead(pDevIns,
    182                       pVirtio->aGCPhysVirtqAvail[uVirtqNbr] + RT_UOFFSETOF_DYN(VIRTQ_AVAIL_T, auRing[pVirtio->uVirtqSize[uVirtqNbr]]),
    183                       &uUsedEventIdx, sizeof(uUsedEventIdx));
     183                         pVirtq->GCPhysVirtqAvail + RT_UOFFSETOF_DYN(VIRTQUEUE_AVAIL_T, auRing[pVirtq->uSize]),
     184                         &uUsedEventIdx, sizeof(uUsedEventIdx));
    184185    return uUsedEventIdx;
    185186}
    186187#endif
    187188
    188 DECLINLINE(uint16_t) virtioReadAvailRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
     189DECLINLINE(uint16_t) virtioReadAvailRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
    189190{
    190191    uint16_t uIdx = 0;
    191192    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     193    RT_NOREF(pVirtio);
    192194    PDMDevHlpPCIPhysRead(pDevIns,
    193                       pVirtio->aGCPhysVirtqAvail[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_AVAIL_T, uIdx),
    194                       &uIdx, sizeof(uIdx));
     195                         pVirtq->GCPhysVirtqAvail + RT_UOFFSETOF(VIRTQUEUE_AVAIL_T, uIdx),
     196                         &uIdx, sizeof(uIdx));
    195197    return uIdx;
    196198}
    197199
    198 DECLINLINE(uint16_t) virtioReadAvailRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
     200DECLINLINE(uint16_t) virtioReadAvailRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
    199201{
    200202    uint16_t fFlags = 0;
    201203    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     204    RT_NOREF(pVirtio);
    202205    PDMDevHlpPCIPhysRead(pDevIns,
    203                       pVirtio->aGCPhysVirtqAvail[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_AVAIL_T, fFlags),
    204                       &fFlags, sizeof(fFlags));
     206                         pVirtq->GCPhysVirtqAvail + RT_UOFFSETOF(VIRTQUEUE_AVAIL_T, fFlags),
     207                         &fFlags, sizeof(fFlags));
    205208    return fFlags;
    206209}
     
    213216
    214217#ifdef IN_RING3
    215 DECLINLINE(void) virtioWriteUsedElem(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr,
     218DECLINLINE(void) virtioWriteUsedElem(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq,
    216219                                     uint32_t usedIdx, uint32_t uDescIdx, uint32_t uLen)
    217220{
    218     VIRTQ_USED_ELEM_T elem = { uDescIdx,  uLen };
     221    VIRTQUEUE_USED_ELEM_T elem = { uDescIdx,  uLen };
    219222    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
    220     uint16_t const cVirtqItems = RT_MAX(pVirtio->uVirtqSize[uVirtqNbr], 1); /* Make sure to avoid div-by-zero. */
     223    RT_NOREF(pVirtio);
     224    uint16_t const cVirtqItems = RT_MAX(pVirtq->uSize, 1); /* Make sure to avoid div-by-zero. */
    221225    PDMDevHlpPCIPhysWrite(pDevIns,
    222                           pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF_DYN(VIRTQ_USED_T, aRing[usedIdx % cVirtqItems]),
     226                          pVirtq->GCPhysVirtqUsed
     227                        + RT_UOFFSETOF_DYN(VIRTQUEUE_USED_T, aRing[usedIdx % cVirtqItems]),
    223228                          &elem, sizeof(elem));
    224229}
    225230
    226 DECLINLINE(void) virtioWriteUsedRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, uint16_t fFlags)
     231DECLINLINE(void) virtioWriteUsedRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq, uint16_t fFlags)
    227232{
    228233    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     234    RT_NOREF(pVirtio);
    229235    RT_UNTRUSTED_VALIDATED_FENCE(); /* VirtIO 1.0, Section 3.2.1.4.1 */
    230236    PDMDevHlpPCIPhysWrite(pDevIns,
    231                           pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_USED_T, fFlags),
     237                          pVirtq->GCPhysVirtqUsed + RT_UOFFSETOF(VIRTQUEUE_USED_T, fFlags),
    232238                          &fFlags, sizeof(fFlags));
    233239}
    234240#endif
    235241
    236 DECLINLINE(void) virtioWriteUsedRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, uint16_t uIdx)
     242DECLINLINE(void) virtioWriteUsedRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq, uint16_t uIdx)
    237243{
    238244    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     245    RT_NOREF(pVirtio);
    239246    PDMDevHlpPCIPhysWrite(pDevIns,
    240                           pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_USED_T, uIdx),
     247                          pVirtq->GCPhysVirtqUsed + RT_UOFFSETOF(VIRTQUEUE_USED_T, uIdx),
    241248                          &uIdx, sizeof(uIdx));
    242249}
     
    244251
    245252#ifdef IN_RING3
    246 DECLINLINE(uint16_t) virtioReadUsedRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
     253DECLINLINE(uint16_t) virtioReadUsedRingIdx(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
    247254{
    248255    uint16_t uIdx = 0;
    249256    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     257    RT_NOREF(pVirtio);
    250258    PDMDevHlpPCIPhysRead(pDevIns,
    251                       pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_USED_T, uIdx),
    252                       &uIdx, sizeof(uIdx));
     259                         pVirtq->GCPhysVirtqUsed + RT_UOFFSETOF(VIRTQUEUE_USED_T, uIdx),
     260                         &uIdx, sizeof(uIdx));
    253261    return uIdx;
    254262}
    255263
    256 DECLINLINE(uint16_t) virtioReadUsedRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
     264DECLINLINE(uint16_t) virtioReadUsedRingFlags(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
    257265{
    258266    uint16_t fFlags = 0;
    259267    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     268    RT_NOREF(pVirtio);
    260269    PDMDevHlpPCIPhysRead(pDevIns,
    261                       pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF(VIRTQ_USED_T, fFlags),
    262                       &fFlags, sizeof(fFlags));
     270                         pVirtq->GCPhysVirtqUsed + RT_UOFFSETOF(VIRTQUEUE_USED_T, fFlags),
     271                         &fFlags, sizeof(fFlags));
    263272    return fFlags;
    264273}
    265274
    266 DECLINLINE(void) virtioWriteUsedAvailEvent(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, uint32_t uAvailEventIdx)
     275DECLINLINE(void) virtioWriteUsedAvailEvent(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq, uint32_t uAvailEventIdx)
    267276{
    268277    /** VirtIO 1.0 uAvailEventIdx (avail_event) immediately follows ring */
    269278    AssertMsg(pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK, ("Called with guest driver not ready\n"));
     279    RT_NOREF(pVirtio);
    270280    PDMDevHlpPCIPhysWrite(pDevIns,
    271                           pVirtio->aGCPhysVirtqUsed[uVirtqNbr] + RT_UOFFSETOF_DYN(VIRTQ_USED_T, aRing[pVirtio->uVirtqSize[uVirtqNbr]]),
     281                          pVirtq->GCPhysVirtqUsed
     282                        + RT_UOFFSETOF_DYN(VIRTQUEUE_USED_T, aRing[pVirtq->uSize]),
    272283                          &uAvailEventIdx, sizeof(uAvailEventIdx));
    273284}
    274285#endif
    275286
    276 DECLINLINE(uint16_t) virtioCoreVirtqAvailBufCount(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQSTATE pVirtqState)
    277 {
    278     uint16_t uIdx    = virtioReadAvailRingIdx(pDevIns, pVirtio, pVirtqState->uVirtqNbr);
    279     uint16_t uShadow = pVirtqState->uAvailIdxShadow;
     287DECLINLINE(uint16_t) virtioCoreVirtqAvailBufCount_inline(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, PVIRTQUEUE pVirtq)
     288{
     289    uint16_t uIdx    = virtioReadAvailRingIdx(pDevIns, pVirtio, pVirtq);
     290    uint16_t uShadow = pVirtq->uAvailIdxShadow;
    280291
    281292    uint16_t uDelta;
     
    286297
    287298    LogFunc(("%s has %u %s (idx=%u shadow=%u)\n",
    288         VIRTQNAME(pVirtio, pVirtqState->uVirtqNbr), uDelta, uDelta == 1 ? "entry" : "entries",
     299        pVirtq->szName, uDelta, uDelta == 1 ? "entry" : "entries",
    289300        uIdx, uShadow));
    290301
     
    296307 * @param   pDevIns     The device instance.
    297308 * @param   pVirtio     Pointer to the shared virtio state.
    298  * @param   uVirtqNbr   Virtq number
     309 * @param   uVirtq      Virtq number
    299310 *
    300311 * @returns how many entries have been added to ring as a delta of the consumer's
    301312 *          avail index and the queue's guest-side current avail index.
    302313 */
    303 uint16_t virtioCoreVirtqAvailBufCount(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    304 {
    305     if (!IS_DRIVER_OK(pVirtio) || !pVirtio->uVirtqEnable[uVirtqNbr])
     314uint16_t virtioCoreVirtqAvailBufCount(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq)
     315{
     316    AssertMsgReturn(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues), ("uVirtq out of range"), 0);
     317    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     318    if (!IS_DRIVER_OK(pVirtio) || !pVirtq->uEnable)
    306319    {
    307320        LogRelFunc(("Driver not ready or queue not enabled\n"));
    308321        return 0;
    309322    }
    310     return virtioCoreVirtqAvailBufCount(pDevIns, pVirtio, &pVirtio->aVirtqState[uVirtqNbr]);
     323
     324    return virtioCoreVirtqAvailBufCount_inline(pDevIns, pVirtio, pVirtq);
    311325}
    312326
     
    444458    } const s_aFeatures[] =
    445459    {
    446         { VIRTIO_F_RING_INDIRECT_DESC,      "   RING_INDIRECT_DESC   Driver can use descriptors with VIRTQ_DESC_F_INDIRECT flag set\n" },
     460        { VIRTIO_F_RING_INDIRECT_DESC,      "   RING_INDIRECT_DESC   Driver can use descriptors with VIRTQUEUE_DESC_F_INDIRECT flag set\n" },
    447461        { VIRTIO_F_RING_EVENT_IDX,          "   RING_EVENT_IDX       Enables use_event and avail_event fields described in 2.4.7, 2.4.8\n" },
    448462        { VIRTIO_F_VERSION_1,               "   VERSION              Used to detect legacy drivers.\n" },
     
    659673#ifdef IN_RING3
    660674
    661 int virtioCoreR3VirtqAttach(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, const char *pcszName)
     675int virtioCoreR3VirtqAttach(PVIRTIOCORE pVirtio, uint16_t uVirtq, const char *pcszName)
    662676{
    663677    LogFunc(("%s\n", pcszName));
    664     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    665     pVirtqState->uVirtqNbr = uVirtqNbr;
    666     pVirtqState->uAvailIdxShadow = 0;
    667     pVirtqState->uUsedIdxShadow  = 0;
    668     pVirtqState->fVirtqRingEventThreshold = false;
    669     RTStrCopy(pVirtqState->szVirtqName, sizeof(pVirtqState->szVirtqName), pcszName);
     678    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     679    pVirtq->uVirtq = uVirtq;
     680    pVirtq->uAvailIdxShadow = 0;
     681    pVirtq->uUsedIdxShadow  = 0;
     682    pVirtq->fUsedRingEvent = false;
     683    RTStrCopy(pVirtq->szName, sizeof(pVirtq->szName), pcszName);
    670684    return VINF_SUCCESS;
    671685}
    672686
    673687/** API Fuunction: See header file */
    674 void virtioCoreR3VirtqInfo(PPDMDEVINS pDevIns, PCDBGFINFOHLP pHlp, const char *pszArgs, int uVirtqNbr)
     688void virtioCoreR3VirtqInfo(PPDMDEVINS pDevIns, PCDBGFINFOHLP pHlp, const char *pszArgs, int uVirtq)
    675689{
    676690    RT_NOREF(pszArgs);
    677691    PVIRTIOCORE pVirtio = PDMDEVINS_2_DATA(pDevIns, PVIRTIOCORE);
    678     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
     692    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
    679693
    680694    /** @todo add ability to dump physical contents described by any descriptor (using existing VirtIO core API function) */
    681695//    bool fDump      = pszArgs && (*pszArgs == 'd' || *pszArgs == 'D'); /* "dump" (avail phys descriptor)"
    682696
    683     uint16_t uAvailIdx       = virtioReadAvailRingIdx(pDevIns, pVirtio, uVirtqNbr);
    684     uint16_t uAvailIdxShadow = pVirtqState->uAvailIdxShadow;
    685 
    686     uint16_t uUsedIdx        = virtioReadUsedRingIdx(pDevIns, pVirtio, uVirtqNbr);
    687     uint16_t uUsedIdxShadow  = pVirtqState->uUsedIdxShadow;
     697    uint16_t uAvailIdx       = virtioReadAvailRingIdx(pDevIns, pVirtio, pVirtq);
     698    uint16_t uAvailIdxShadow = pVirtq->uAvailIdxShadow;
     699
     700    uint16_t uUsedIdx        = virtioReadUsedRingIdx(pDevIns, pVirtio, pVirtq);
     701    uint16_t uUsedIdxShadow  = pVirtq->uUsedIdxShadow;
    688702
    689703    PVIRTQBUF pVirtqBuf = NULL;
    690704
    691     bool fEmpty = IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtqState);
    692 
    693     LogFunc(("%s, empty = %s\n", VIRTQNAME(pVirtio, uVirtqNbr), fEmpty ? "true" : "false"));
     705    bool fEmpty = IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtq);
     706
     707    LogFunc(("%s, empty = %s\n", pVirtq->szName, fEmpty ? "true" : "false"));
    694708
    695709    int cSendSegs = 0, cReturnSegs = 0;
    696710    if (!fEmpty)
    697711    {
    698         virtioCoreR3VirtqAvailBufPeek(pDevIns,  pVirtio, uVirtqNbr, &pVirtqBuf);
     712        virtioCoreR3VirtqAvailBufPeek(pDevIns,  pVirtio, uVirtq, &pVirtqBuf);
    699713        cSendSegs   = pVirtqBuf->pSgPhysSend ? pVirtqBuf->pSgPhysSend->cSegs : 0;
    700714        cReturnSegs = pVirtqBuf->pSgPhysReturn ? pVirtqBuf->pSgPhysReturn->cSegs : 0;
    701715    }
    702716
    703     bool fAvailNoInterrupt   = virtioReadAvailRingFlags(pDevIns, pVirtio, uVirtqNbr) & VIRTQ_AVAIL_F_NO_INTERRUPT;
    704     bool fUsedNoNotify       = virtioReadUsedRingFlags(pDevIns, pVirtio, uVirtqNbr) & VIRTQ_USED_F_NO_NOTIFY;
    705 
    706 
    707     pHlp->pfnPrintf(pHlp, "       queue enabled: ........... %s\n", pVirtio->uVirtqEnable[uVirtqNbr] ? "true" : "false");
    708     pHlp->pfnPrintf(pHlp, "       size: .................... %d\n", pVirtio->uVirtqSize[uVirtqNbr]);
    709     pHlp->pfnPrintf(pHlp, "       notify offset: ........... %d\n", pVirtio->uVirtqNotifyOff[uVirtqNbr]);
     717    bool fAvailNoInterrupt   = virtioReadAvailRingFlags(pDevIns, pVirtio, pVirtq) & VIRTQUEUE_AVAIL_F_NO_INTERRUPT;
     718    bool fUsedNoNotify       = virtioReadUsedRingFlags(pDevIns, pVirtio, pVirtq) & VIRTQUEUE_USED_F_NO_NOTIFY;
     719
     720
     721    pHlp->pfnPrintf(pHlp, "       queue enabled: ........... %s\n", pVirtq->uEnable ? "true" : "false");
     722    pHlp->pfnPrintf(pHlp, "       size: .................... %d\n", pVirtq->uSize);
     723    pHlp->pfnPrintf(pHlp, "       notify offset: ........... %d\n", pVirtq->uNotifyOffset);
    710724    if (pVirtio->fMsiSupport)
    711         pHlp->pfnPrintf(pHlp, "       MSIX vector: ....... %4.4x\n", pVirtio->uVirtqMsixVector[uVirtqNbr]);
     725        pHlp->pfnPrintf(pHlp, "       MSIX vector: ....... %4.4x\n", pVirtq->uMsix);
    712726    pHlp->pfnPrintf(pHlp, "\n");
    713727    pHlp->pfnPrintf(pHlp, "       avail ring (%d entries):\n", uAvailIdx - uAvailIdxShadow);
     
    750764
    751765/** API Function: See header file */
    752 int virtioCoreR3VirtqAvailBufGet(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr,
     766int virtioCoreR3VirtqAvailBufGet(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq,
    753767                             uint16_t uHeadIdx, PPVIRTQBUF ppVirtqBuf)
    754768{
     
    756770    *ppVirtqBuf = NULL;
    757771
    758     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    759 
    760     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    761 
    762     AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtio->uVirtqEnable[uVirtqNbr],
     772    AssertMsgReturn(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues),
     773                        ("uVirtq out of range"), VERR_INVALID_PARAMETER);
     774    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     775
     776    if (!IS_DRIVER_OK(pVirtio) || !pVirtq->uEnable)
     777    {
     778        LogRelFunc(("Driver not ready or queue not enabled\n"));
     779        return 0;
     780    }
     781
     782    AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtq->uEnable,
    763783                    ("Guest driver not in ready state.\n"), VERR_INVALID_STATE);
    764784
    765785    uint16_t uDescIdx = uHeadIdx;
    766786
    767     Log6Func(("%s DESC CHAIN: (head) desc_idx=%u\n", pVirtqState->szVirtqName, uHeadIdx));
    768     RT_NOREF(pVirtqState);
     787    Log6Func(("%s DESC CHAIN: (head) desc_idx=%u\n", pVirtq->szName, uHeadIdx));
    769788
    770789    /*
     
    773792    PVIRTQBUF pVirtqBuf = (PVIRTQBUF)RTMemAllocZ(sizeof(VIRTQBUF_T));
    774793    AssertReturn(pVirtqBuf, VERR_NO_MEMORY);
    775     pVirtqBuf->u32Magic = VIRTQBUF_MAGIC;
    776     pVirtqBuf->cRefs    = 1;
    777     pVirtqBuf->uHeadIdx = uHeadIdx;
    778     pVirtqBuf->uVirtqNbr = uVirtqNbr;
     794    pVirtqBuf->u32Magic  = VIRTQBUF_MAGIC;
     795    pVirtqBuf->cRefs     = 1;
     796    pVirtqBuf->uHeadIdx  = uHeadIdx;
     797    pVirtqBuf->uVirtq = uVirtq;
    779798    *ppVirtqBuf = pVirtqBuf;
    780799
     
    782801     * Gather segments.
    783802     */
    784     VIRTQ_DESC_T desc;
     803    VIRTQUEUE_DESC_T desc;
    785804
    786805    uint32_t cbIn = 0;
     
    816835        RT_UNTRUSTED_VALIDATED_FENCE();
    817836
    818         virtioReadDesc(pDevIns, pVirtio, uVirtqNbr, uDescIdx, &desc);
    819 
    820         if (desc.fFlags & VIRTQ_DESC_F_WRITE)
    821         {
    822             Log6Func(("%s IN  desc_idx=%u seg=%u addr=%RGp cb=%u\n", VIRTQNAME(pVirtio, uVirtqNbr), uDescIdx, cSegsIn, desc.GCPhysBuf, desc.cb));
     837        virtioReadDesc(pDevIns, pVirtio, pVirtq, uDescIdx, &desc);
     838
     839        if (desc.fFlags & VIRTQUEUE_DESC_F_WRITE)
     840        {
     841            Log6Func(("%s IN  desc_idx=%u seg=%u addr=%RGp cb=%u\n", pVirtq->szName, uDescIdx, cSegsIn, desc.GCPhysBuf, desc.cb));
    823842            cbIn += desc.cb;
    824843            pSeg = &paSegsIn[cSegsIn++];
     
    826845        else
    827846        {
    828             Log6Func(("%s OUT desc_idx=%u seg=%u addr=%RGp cb=%u\n", VIRTQNAME(pVirtio, uVirtqNbr), uDescIdx, cSegsOut, desc.GCPhysBuf, desc.cb));
     847            Log6Func(("%s OUT desc_idx=%u seg=%u addr=%RGp cb=%u\n", pVirtq->szName, uDescIdx, cSegsOut, desc.GCPhysBuf, desc.cb));
    829848            cbOut += desc.cb;
    830849            pSeg = &paSegsOut[cSegsOut++];
     
    840859
    841860        uDescIdx = desc.uDescIdxNext;
    842     } while (desc.fFlags & VIRTQ_DESC_F_NEXT);
     861    } while (desc.fFlags & VIRTQUEUE_DESC_F_NEXT);
    843862
    844863    /*
     
    862881
    863882    STAM_REL_COUNTER_INC(&pVirtio->StatDescChainsAllocated);
    864     Log6Func(("%s -- segs OUT: %u (%u bytes)   IN: %u (%u bytes) --\n", pVirtqState->szVirtqName, cSegsOut, cbOut, cSegsIn, cbIn));
     883    Log6Func(("%s -- segs OUT: %u (%u bytes)   IN: %u (%u bytes) --\n",
     884        pVirtq->szName, cSegsOut, cbOut, cSegsIn, cbIn));
    865885
    866886    return VINF_SUCCESS;
     
    903923}
    904924
    905 void virtioCoreVirtqEnableNotify(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, bool fEnable)
    906 {
     925/** API Function: See header file */
     926void virtioCoreVirtqEnableNotify(PVIRTIOCORE pVirtio, uint16_t uVirtq, bool fEnable)
     927{
     928
     929    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     930    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     931
    907932    if (pVirtio->fDeviceStatus & VIRTIO_STATUS_DRIVER_OK)
    908933    {
    909         uint16_t fFlags = virtioReadUsedRingFlags(pVirtio->pDevInsR3, pVirtio, uVirtqNbr);
     934        uint16_t fFlags = virtioReadUsedRingFlags(pVirtio->pDevInsR3, pVirtio, pVirtq);
    910935
    911936        if (fEnable)
    912             fFlags &= ~ VIRTQ_USED_F_NO_NOTIFY;
     937            fFlags &= ~ VIRTQUEUE_USED_F_NO_NOTIFY;
    913938        else
    914             fFlags |= VIRTQ_USED_F_NO_NOTIFY;
    915 
    916         virtioWriteUsedRingFlags(pVirtio->pDevInsR3, pVirtio, uVirtqNbr, fFlags);
     939            fFlags |= VIRTQUEUE_USED_F_NO_NOTIFY;
     940
     941        virtioWriteUsedRingFlags(pVirtio->pDevInsR3, pVirtio, pVirtq, fFlags);
    917942    }
    918943}
     
    931956
    932957/** API function: See Header file  */
    933 int virtioCoreR3VirtqAvailBufPeek(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr,
     958int virtioCoreR3VirtqAvailBufPeek(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq,
    934959                         PPVIRTQBUF ppVirtqBuf)
    935960{
    936     return virtioCoreR3VirtqAvailBufGet(pDevIns, pVirtio, uVirtqNbr, ppVirtqBuf, false);
     961    return virtioCoreR3VirtqAvailBufGet(pDevIns, pVirtio, uVirtq, ppVirtqBuf, false);
    937962}
    938963
    939964/** API function: See Header file  */
    940 int virtioCoreR3VirtqAvailBufNext(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    941 {
    942     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    943     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    944 
    945     AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtio->uVirtqEnable[uVirtqNbr],
     965int virtioCoreR3VirtqAvailBufNext(PVIRTIOCORE pVirtio, uint16_t uVirtq)
     966{
     967    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     968    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     969
     970    AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtq->uEnable,
    946971                    ("Guest driver not in ready state.\n"), VERR_INVALID_STATE);
    947972
    948     if (IS_VIRTQ_EMPTY(pVirtio->pDevInsR3, pVirtio, pVirtqState))
     973    if (IS_VIRTQ_EMPTY(pVirtio->pDevInsR3, pVirtio, pVirtq))
    949974        return VERR_NOT_AVAILABLE;
    950975
    951     Log6Func(("%s avail shadow idx: %u\n", pVirtqState->szVirtqName, pVirtqState->uAvailIdxShadow));
    952     pVirtqState->uAvailIdxShadow++;
     976    Log6Func(("%s avail shadow idx: %u\n", pVirtq->szName, pVirtq->uAvailIdxShadow));
     977    pVirtq->uAvailIdxShadow++;
    953978
    954979    return VINF_SUCCESS;
     
    956981
    957982/** API function: See Header file  */
    958 int virtioCoreR3VirtqAvailBufGet(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr,
     983int virtioCoreR3VirtqAvailBufGet(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq,
    959984                         PPVIRTQBUF ppVirtqBuf, bool fRemove)
    960985{
    961     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    962 
    963     if (IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtqState))
     986    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     987    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     988
     989    if (IS_VIRTQ_EMPTY(pDevIns, pVirtio, pVirtq))
    964990        return VERR_NOT_AVAILABLE;
    965991
    966     uint16_t uHeadIdx = virtioReadAvailDescIdx(pDevIns, pVirtio, uVirtqNbr, pVirtqState->uAvailIdxShadow);
     992    uint16_t uHeadIdx = virtioReadAvailDescIdx(pDevIns, pVirtio, pVirtq, pVirtq->uAvailIdxShadow);
    967993
    968994    if (pVirtio->uDriverFeatures & VIRTIO_F_EVENT_IDX)
    969         virtioWriteUsedAvailEvent(pDevIns,pVirtio, uVirtqNbr, pVirtqState->uAvailIdxShadow + 1);
     995        virtioWriteUsedAvailEvent(pDevIns,pVirtio, pVirtq, pVirtq->uAvailIdxShadow + 1);
    970996
    971997    if (fRemove)
    972         pVirtqState->uAvailIdxShadow++;
    973 
    974     int rc = virtioCoreR3VirtqAvailBufGet(pDevIns, pVirtio, uVirtqNbr, uHeadIdx, ppVirtqBuf);
     998        pVirtq->uAvailIdxShadow++;
     999
     1000    int rc = virtioCoreR3VirtqAvailBufGet(pDevIns, pVirtio, uVirtq, uHeadIdx, ppVirtqBuf);
    9751001    return rc;
    9761002}
    9771003
    9781004/** API function: See Header file  */
    979 int virtioCoreR3VirtqUsedBufPut(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, PRTSGBUF pSgVirtReturn,
     1005int virtioCoreR3VirtqUsedBufPut(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq, PRTSGBUF pSgVirtReturn,
    9801006                            PVIRTQBUF pVirtqBuf, bool fFence)
    9811007{
    982     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    983     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
     1008    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     1009    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     1010
    9841011    PVIRTIOSGBUF pSgPhysReturn = pVirtqBuf->pSgPhysReturn;
    9851012
     
    9901017
    9911018    Log6Func(("Copying client data to %s, desc chain (head desc_idx %d)\n",
    992               VIRTQNAME(pVirtio, uVirtqNbr), virtioReadUsedRingIdx(pDevIns, pVirtio, uVirtqNbr)));
     1019              VIRTQNAME(pVirtio, uVirtq), virtioReadUsedRingIdx(pDevIns, pVirtio, pVirtq)));
    9931020
    9941021    /* Copy s/g buf (virtual memory) to guest phys mem (IN direction). */
     
    10201047    /* If this write-ahead crosses threshold where the driver wants to get an event flag it */
    10211048    if (pVirtio->uDriverFeatures & VIRTIO_F_EVENT_IDX)
    1022         if (pVirtqState->uUsedIdxShadow == virtioReadAvailUsedEvent(pDevIns, pVirtio, uVirtqNbr))
    1023             pVirtqState->fVirtqRingEventThreshold = true;
     1049        if (pVirtq->uUsedIdxShadow == virtioReadAvailUsedEvent(pDevIns, pVirtio, pVirtq))
     1050            pVirtq->fUsedRingEvent = true;
    10241051
    10251052    /*
    10261053     * Place used buffer's descriptor in used ring but don't update used ring's slot index.
    10271054     * That will be done with a subsequent client call to virtioCoreVirtqSyncUsedRing() */
    1028     virtioWriteUsedElem(pDevIns, pVirtio, uVirtqNbr, pVirtqState->uUsedIdxShadow++, pVirtqBuf->uHeadIdx, (uint32_t)cbTotal);
     1055    virtioWriteUsedElem(pDevIns, pVirtio, pVirtq, pVirtq->uUsedIdxShadow++, pVirtqBuf->uHeadIdx, (uint32_t)cbTotal);
    10291056
    10301057    if (pSgVirtReturn)
     
    10331060
    10341061    Log6Func(("Write ahead used_idx=%u, %s used_idx=%u\n",
    1035               pVirtqState->uUsedIdxShadow, VIRTQNAME(pVirtio, uVirtqNbr), virtioReadUsedRingIdx(pDevIns, pVirtio, uVirtqNbr)));
     1062              pVirtq->uUsedIdxShadow, VIRTQNAME(pVirtio, uVirtq), virtioReadUsedRingIdx(pDevIns, pVirtio, pVirtq)));
    10361063
    10371064    return VINF_SUCCESS;
     
    10531080    }
    10541081    LogFunc(("Added %d/%d bytes to %s buffer, head idx: %u (%d bytes remain)\n",
    1055              cb - cbLim, cb, VIRTQNAME(pVirtio, pVirtqBuf->uVirtqNbr),
     1082             cb - cbLim, cb, VIRTQNAME(pVirtio, pVirtqBuf->uVirtq),
    10561083             pVirtqBuf->uHeadIdx, pVirtqBuf->cbPhysReturn));
    10571084}
     
    10731100    }
    10741101    LogFunc(("Drained %d/%d bytes from %s buffer, head idx: %u (%d bytes left)\n",
    1075              cb - cbLim, cb, VIRTQNAME(pVirtio, pVirtqBuf->uVirtqNbr),
     1102             cb - cbLim, cb, VIRTQNAME(pVirtio, pVirtqBuf->uVirtq),
    10761103             pVirtqBuf->uHeadIdx, pVirtqBuf->cbPhysSend));
    10771104}
     
    10801107
    10811108/** API function: See Header file  */
    1082 int virtioCoreVirtqSyncUsedRing(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    1083 {
    1084     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    1085     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    1086 
    1087     AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtio->uVirtqEnable[uVirtqNbr],
     1109int virtioCoreVirtqSyncUsedRing(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq)
     1110{
     1111    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     1112    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     1113
     1114    AssertMsgReturn(IS_DRIVER_OK(pVirtio) && pVirtq->uEnable,
    10881115                    ("Guest driver not in ready state.\n"), VERR_INVALID_STATE);
    10891116
    1090     Log6Func(("Updating %s used_idx to %u\n",
    1091               VIRTQNAME(pVirtio, uVirtqNbr), pVirtqState->uUsedIdxShadow));
    1092 
    1093     virtioWriteUsedRingIdx(pDevIns, pVirtio, uVirtqNbr, pVirtqState->uUsedIdxShadow);
    1094     virtioCoreNotifyGuestDriver(pDevIns, pVirtio, uVirtqNbr);
     1117    Log6Func(("Updating %s used_idx to %u\n", pVirtq->szName, pVirtq->uUsedIdxShadow));
     1118
     1119    virtioWriteUsedRingIdx(pDevIns, pVirtio, pVirtq, pVirtq->uUsedIdxShadow);
     1120    virtioCoreNotifyGuestDriver(pDevIns, pVirtio, uVirtq);
    10951121
    10961122    return VINF_SUCCESS;
     
    11041130 * @param   pDevIns     The device instance.
    11051131 * @param   pVirtio     Pointer to the shared virtio state.
    1106  * @param   uVirtqNbr   Virtq to check for guest interrupt handling preference
     1132 * @param   uVirtq      Virtq to check for guest interrupt handling preference
    11071133 * @param   uNotifyIdx  Notification index
    11081134 */
    1109 static void virtioCoreVirtqNotified(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr, uint16_t uNotifyIdx)
     1135static void virtioCoreVirtqNotified(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq, uint16_t uNotifyIdx)
    11101136{
    11111137    PVIRTIOCORECC pVirtioCC = PDMDEVINS_2_DATA_CC(pDevIns, PVIRTIOCORECC);
    11121138
    1113     /* See VirtIO 1.0, section 4.1.5.2 It implies that uVirtqNbr and uNotifyIdx should match.
     1139    /* See VirtIO 1.0, section 4.1.5.2 It implies that uVirtq and uNotifyIdx should match.
    11141140     * Disregarding this notification may cause throughput to stop, however there's no way to know
    11151141     * which was queue was intended for wake-up if the two parameters disagree. */
    11161142
    1117     AssertMsg(uNotifyIdx == uVirtqNbr,
    1118                     ("Guest kicked virtq %d's notify addr w/non-corresponding virtq idx %d\n",
    1119                      uVirtqNbr, uNotifyIdx));
     1143    AssertMsg(uNotifyIdx == uVirtq,
     1144              ("Guest kicked virtq %d's notify addr w/non-corresponding virtq idx %d\n",
     1145              uVirtq, uNotifyIdx));
    11201146    RT_NOREF(uNotifyIdx);
    11211147
    1122     AssertReturnVoid(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    1123     Log6Func(("%s (desc chains: %u)\n",
    1124         pVirtio->aVirtqState[uVirtqNbr].szVirtqName,
    1125         virtioCoreVirtqAvailBufCount(pDevIns, pVirtio, uVirtqNbr)));
     1148    AssertReturnVoid(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     1149    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     1150
     1151    Log6Func(("%s (desc chains: %u)\n", pVirtq->szName,
     1152        virtioCoreVirtqAvailBufCount_inline(pDevIns, pVirtio, pVirtq)));
    11261153
    11271154    /* Inform client */
    1128     pVirtioCC->pfnVirtqNotified(pDevIns, pVirtio, uVirtqNbr);
     1155    pVirtioCC->pfnVirtqNotified(pDevIns, pVirtio, uVirtq);
     1156    RT_NOREF2(pVirtio, pVirtq);
    11291157}
    11301158
     
    11381166 * @param   pDevIns     The device instance.
    11391167 * @param   pVirtio     Pointer to the shared virtio state.
    1140  * @param   uVirtqNbr   Virtq to check for guest interrupt handling preference
    1141  */
    1142 static void virtioCoreNotifyGuestDriver(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    1143 {
    1144     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    1145     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
     1168 * @param   uVirtq      Virtq to check for guest interrupt handling preference
     1169 */
     1170static void virtioCoreNotifyGuestDriver(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint16_t uVirtq)
     1171{
     1172    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     1173    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
    11461174
    11471175    if (!IS_DRIVER_OK(pVirtio))
     
    11531181    if (pVirtio->uDriverFeatures & VIRTIO_F_EVENT_IDX)
    11541182    {
    1155         if (pVirtqState->fVirtqRingEventThreshold)
     1183        if (pVirtq->fUsedRingEvent)
    11561184        {
    11571185#ifdef IN_RING3
    11581186            Log6Func(("...kicking guest %s, VIRTIO_F_EVENT_IDX set and threshold (%d) reached\n",
    1159                    VIRTQNAME(pVirtio, uVirtqNbr), (uint16_t)virtioReadAvailUsedEvent(pDevIns, pVirtio, uVirtqNbr)));
     1187                   pVirtq->szName, (uint16_t)virtioReadAvailUsedEvent(pDevIns, pVirtio, pVirtq)));
    11601188#endif
    1161             virtioKick(pDevIns, pVirtio, VIRTIO_ISR_VIRTQ_INTERRUPT, pVirtio->uVirtqMsixVector[uVirtqNbr]);
    1162             pVirtqState->fVirtqRingEventThreshold = false;
     1189            virtioKick(pDevIns, pVirtio, VIRTIO_ISR_VIRTQ_INTERRUPT, pVirtq->uMsix);
     1190            pVirtq->fUsedRingEvent = false;
    11631191            return;
    11641192        }
    11651193#ifdef IN_RING3
    11661194        Log6Func(("...skip interrupt %s, VIRTIO_F_EVENT_IDX set but threshold (%d) not reached (%d)\n",
    1167                    VIRTQNAME(pVirtio, uVirtqNbr),(uint16_t)virtioReadAvailUsedEvent(pDevIns, pVirtio, uVirtqNbr), pVirtqState->uUsedIdxShadow));
     1195                   pVirtq->szName,(uint16_t)virtioReadAvailUsedEvent(pDevIns, pVirtio, pVirtq), pVirtq->uUsedIdxShadow));
    11681196#endif
    11691197    }
     
    11711199    {
    11721200        /** If guest driver hasn't suppressed interrupts, interrupt  */
    1173         if (!(virtioReadAvailRingFlags(pDevIns, pVirtio, uVirtqNbr) & VIRTQ_AVAIL_F_NO_INTERRUPT))
    1174         {
    1175             virtioKick(pDevIns, pVirtio, VIRTIO_ISR_VIRTQ_INTERRUPT, pVirtio->uVirtqMsixVector[uVirtqNbr]);
     1201        if (!(virtioReadAvailRingFlags(pDevIns, pVirtio, pVirtq) & VIRTQUEUE_AVAIL_F_NO_INTERRUPT))
     1202        {
     1203            virtioKick(pDevIns, pVirtio, VIRTIO_ISR_VIRTQ_INTERRUPT, pVirtq->uMsix);
    11761204            return;
    11771205        }
    1178         Log6Func(("...skipping interrupt for %s (guest set VIRTQ_AVAIL_F_NO_INTERRUPT)\n",
    1179                      VIRTQNAME(pVirtio, uVirtqNbr)));
     1206        Log6Func(("...skipping interrupt for %s (guest set VIRTQUEUE_AVAIL_F_NO_INTERRUPT)\n", pVirtq->szName));
    11801207    }
    11811208}
     
    11891216 * @param   uVec        MSI-X vector, if enabled
    11901217 */
    1191 static int virtioKick(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint8_t uCause, uint16_t uMsixVector)
     1218static int virtioKick(PPDMDEVINS pDevIns, PVIRTIOCORE pVirtio, uint8_t uCause, uint16_t uMsixtor)
    11921219{
    11931220    if (uCause == VIRTIO_ISR_VIRTQ_INTERRUPT)
     
    12021229        PDMDevHlpPCISetIrq(pDevIns, 0, PDM_IRQ_LEVEL_HIGH);
    12031230    }
    1204     else if (uMsixVector != VIRTIO_MSI_NO_VECTOR)
    1205         PDMDevHlpPCISetIrq(pDevIns, uMsixVector, 1);
     1231    else if (uMsixtor != VIRTIO_MSI_NO_VECTOR)
     1232        PDMDevHlpPCISetIrq(pDevIns, uMsixtor, 1);
    12061233    return VINF_SUCCESS;
    12071234}
     
    12121239 * @param   pDevIns     The device instance.
    12131240 */
    1214 static void virtioLowerInterrupt(PPDMDEVINS pDevIns, uint16_t uMsixVector)
     1241static void virtioLowerInterrupt(PPDMDEVINS pDevIns, uint16_t uMsixtor)
    12151242{
    12161243    PVIRTIOCORE pVirtio = PDMINS_2_DATA(pDevIns, PVIRTIOCORE);
    12171244    if (!pVirtio->fMsiSupport)
    12181245        PDMDevHlpPCISetIrq(pDevIns, 0, PDM_IRQ_LEVEL_LOW);
    1219     else if (uMsixVector != VIRTIO_MSI_NO_VECTOR)
     1246    else if (uMsixtor != VIRTIO_MSI_NO_VECTOR)
    12201247        PDMDevHlpPCISetIrq(pDevIns, pVirtio->uMsixConfig, PDM_IRQ_LEVEL_LOW);
    12211248}
    12221249
    12231250#ifdef IN_RING3
    1224 static void virtioResetVirtq(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    1225 {
    1226     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    1227     PVIRTQSTATE pVirtqState = &pVirtio->aVirtqState[uVirtqNbr];
    1228     pVirtqState->uAvailIdxShadow = 0;
    1229     pVirtqState->uUsedIdxShadow  = 0;
    1230     pVirtqState->fVirtqRingEventThreshold = false;
    1231     pVirtio->uVirtqEnable[uVirtqNbr] = false;
    1232     pVirtio->uVirtqSize[uVirtqNbr] = VIRTQ_MAX_ENTRIES;
    1233     pVirtio->uVirtqNotifyOff[uVirtqNbr] = uVirtqNbr;
    1234     pVirtio->uVirtqMsixVector[uVirtqNbr] = uVirtqNbr + 2;
     1251static void virtioResetVirtq(PVIRTIOCORE pVirtio, uint16_t uVirtq)
     1252{
     1253    Assert(uVirtq < RT_ELEMENTS(pVirtio->aVirtqueues));
     1254    PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[uVirtq];
     1255
     1256    pVirtq->uAvailIdxShadow  = 0;
     1257    pVirtq->uUsedIdxShadow   = 0;
     1258    pVirtq->uEnable     = false;
     1259    pVirtq->uSize       = VIRTQ_MAX_ENTRIES;
     1260    pVirtq->uNotifyOffset  = uVirtq;
     1261    pVirtq->uMsix = uVirtq + 2;
     1262    pVirtq->fUsedRingEvent = false;
     1263
    12351264    if (!pVirtio->fMsiSupport) /* VirtIO 1.0, 4.1.4.3 and 4.1.5.1.2 */
    1236         pVirtio->uVirtqMsixVector[uVirtqNbr] = VIRTIO_MSI_NO_VECTOR;
    1237 
    1238     virtioLowerInterrupt(pVirtio->pDevInsR3, pVirtio->uVirtqMsixVector[uVirtqNbr]);
     1265        pVirtq->uMsix = VIRTIO_MSI_NO_VECTOR;
     1266
     1267    virtioLowerInterrupt(pVirtio->pDevInsR3, pVirtq->uMsix);
    12391268}
    12401269
     
    12531282    {
    12541283        virtioLowerInterrupt(pDevIns, pVirtio->uMsixConfig);
    1255         for (int i = 0; i < VIRTQ_MAX_CNT; i++)
    1256         {
    1257             virtioLowerInterrupt(pDevIns, pVirtio->uVirtqMsixVector[i]);
    1258             pVirtio->uVirtqMsixVector[i];
    1259         }
     1284        for (int i = 0; i < VIRTQ_MAX_COUNT; i++)
     1285            virtioLowerInterrupt(pDevIns, pVirtio->aVirtqueues[i].uMsix);
    12601286    }
    12611287
     
    12631289        pVirtio->uMsixConfig = VIRTIO_MSI_NO_VECTOR;
    12641290
    1265     for (uint16_t uVirtqNbr = 0; uVirtqNbr < VIRTQ_MAX_CNT; uVirtqNbr++)
    1266         virtioResetVirtq(pVirtio, uVirtqNbr);
     1291    for (uint16_t uVirtq = 0; uVirtq < VIRTQ_MAX_COUNT; uVirtq++)
     1292        virtioResetVirtq(pVirtio, uVirtq);
    12671293}
    12681294
     
    12971323                                   int fWrite, uint32_t uOffsetOfAccess, unsigned cb, void *pv)
    12981324{
    1299     uint16_t uVirtqNbr = pVirtio->uVirtqSelect;
     1325    uint16_t uVirtq = pVirtio->uVirtqSelect;
    13001326    int rc = VINF_SUCCESS;
    13011327    uint64_t val;
     
    13811407            return VINF_SUCCESS;
    13821408        }
    1383         *(uint16_t *)pv = VIRTQ_MAX_CNT;
     1409        *(uint16_t *)pv = VIRTQ_MAX_COUNT;
    13841410        VIRTIO_DEV_CONFIG_LOG_ACCESS(uNumVirtqs, VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess);
    13851411    }
     
    14391465    }
    14401466    else
    1441     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uMsixConfig,                   VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1442         VIRTIO_DEV_CONFIG_ACCESS(         uMsixConfig,                   VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1443     else
    1444     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uDeviceFeaturesSelect,         VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1445         VIRTIO_DEV_CONFIG_ACCESS(         uDeviceFeaturesSelect,         VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1446     else
    1447     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uDriverFeaturesSelect,         VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1448         VIRTIO_DEV_CONFIG_ACCESS(         uDriverFeaturesSelect,         VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1449     else
    1450     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uConfigGeneration,             VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1451         VIRTIO_DEV_CONFIG_ACCESS(         uConfigGeneration,             VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1452     else
    1453     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqSelect,                  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1454         VIRTIO_DEV_CONFIG_ACCESS(         uVirtqSelect,                  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1455     else
    1456     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqSize,                    VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1457         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uVirtqSize,        uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1458     else
    1459     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqMsixVector,              VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1460         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uVirtqMsixVector,  uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1461     else
    1462     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqEnable,                  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1463         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uVirtqEnable,      uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1464     else
    1465     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqNotifyOff,               VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1466         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uVirtqNotifyOff,   uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1467     else
    1468     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   aGCPhysVirtqDesc,              VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1469         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( aGCPhysVirtqDesc,  uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1470     else
    1471     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   aGCPhysVirtqAvail,             VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1472         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( aGCPhysVirtqAvail, uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
    1473     else
    1474     if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   aGCPhysVirtqUsed,              VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
    1475         VIRTIO_DEV_CONFIG_ACCESS_INDEXED( aGCPhysVirtqUsed,  uVirtqNbr,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1467    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uMsixConfig,                VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1468        VIRTIO_DEV_CONFIG_ACCESS(         uMsixConfig,                VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1469    else
     1470    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uDeviceFeaturesSelect,      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1471        VIRTIO_DEV_CONFIG_ACCESS(         uDeviceFeaturesSelect,      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1472    else
     1473    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uDriverFeaturesSelect,      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1474        VIRTIO_DEV_CONFIG_ACCESS(         uDriverFeaturesSelect,      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1475    else
     1476    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uConfigGeneration,          VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1477        VIRTIO_DEV_CONFIG_ACCESS(         uConfigGeneration,          VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1478    else
     1479    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uVirtqSelect,               VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1480        VIRTIO_DEV_CONFIG_ACCESS(         uVirtqSelect,               VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio);
     1481    else
     1482    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   GCPhysVirtqDesc,            VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1483        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( GCPhysVirtqDesc,   uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1484    else
     1485    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   GCPhysVirtqAvail,           VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1486        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( GCPhysVirtqAvail,  uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1487    else
     1488    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   GCPhysVirtqUsed,            VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1489        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( GCPhysVirtqUsed,   uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1490    else
     1491    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uSize,                      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1492        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uSize,             uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1493    else
     1494    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uEnable,                    VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1495        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uEnable,           uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1496    else
     1497    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uNotifyOffset,              VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1498        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uNotifyOffset,     uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
     1499    else
     1500    if (VIRTIO_DEV_CONFIG_MATCH_MEMBER(   uMsix,                      VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess))
     1501        VIRTIO_DEV_CONFIG_ACCESS_INDEXED( uMsix,             uVirtq,  VIRTIO_PCI_COMMON_CFG_T, uOffsetOfAccess, pVirtio->aVirtqueues);
    14761502    else
    14771503    {
     
    17061732    pHlp->pfnSSMPutU32(pSSM, VIRTIO_SAVEDSTATE_VERSION);
    17071733
    1708     pHlp->pfnSSMPutBool(pSSM,   pVirtio->fGenUpdatePending);
    1709     pHlp->pfnSSMPutU8(pSSM,     pVirtio->fDeviceStatus);
    1710     pHlp->pfnSSMPutU8(pSSM,     pVirtio->uConfigGeneration);
    1711     pHlp->pfnSSMPutU8(pSSM,     pVirtio->uPciCfgDataOff);
    1712     pHlp->pfnSSMPutU8(pSSM,     pVirtio->uISR);
    1713     pHlp->pfnSSMPutU16(pSSM,    pVirtio->uVirtqSelect);
    1714     pHlp->pfnSSMPutU32(pSSM,    pVirtio->uDeviceFeaturesSelect);
    1715     pHlp->pfnSSMPutU32(pSSM,    pVirtio->uDriverFeaturesSelect);
    1716     pHlp->pfnSSMPutU64(pSSM,    pVirtio->uDriverFeatures);
    1717 
    1718     for (uint32_t i = 0; i < VIRTQ_MAX_CNT; i++)
    1719     {
    1720         pHlp->pfnSSMPutGCPhys64(pSSM, pVirtio->aGCPhysVirtqDesc[i]);
    1721         pHlp->pfnSSMPutGCPhys64(pSSM, pVirtio->aGCPhysVirtqAvail[i]);
    1722         pHlp->pfnSSMPutGCPhys64(pSSM, pVirtio->aGCPhysVirtqUsed[i]);
    1723         pHlp->pfnSSMPutU16(pSSM,      pVirtio->uVirtqNotifyOff[i]);
    1724         pHlp->pfnSSMPutU16(pSSM,      pVirtio->uVirtqMsixVector[i]);
    1725         pHlp->pfnSSMPutU16(pSSM,      pVirtio->uVirtqEnable[i]);
    1726         pHlp->pfnSSMPutU16(pSSM,      pVirtio->uVirtqSize[i]);
    1727         pHlp->pfnSSMPutU16(pSSM,      pVirtio->aVirtqState[i].uAvailIdxShadow);
    1728         pHlp->pfnSSMPutU16(pSSM,      pVirtio->aVirtqState[i].uUsedIdxShadow);
    1729         int rc = pHlp->pfnSSMPutMem(pSSM, pVirtio->aVirtqState[i].szVirtqName, 32);
     1734    pHlp->pfnSSMPutBool(pSSM, pVirtio->fGenUpdatePending);
     1735    pHlp->pfnSSMPutU8(  pSSM, pVirtio->fDeviceStatus);
     1736    pHlp->pfnSSMPutU8(  pSSM, pVirtio->uConfigGeneration);
     1737    pHlp->pfnSSMPutU8(  pSSM, pVirtio->uPciCfgDataOff);
     1738    pHlp->pfnSSMPutU8(  pSSM, pVirtio->uISR);
     1739    pHlp->pfnSSMPutU16( pSSM, pVirtio->uVirtqSelect);
     1740    pHlp->pfnSSMPutU32( pSSM, pVirtio->uDeviceFeaturesSelect);
     1741    pHlp->pfnSSMPutU32( pSSM, pVirtio->uDriverFeaturesSelect);
     1742    pHlp->pfnSSMPutU64( pSSM, pVirtio->uDriverFeatures);
     1743
     1744    for (uint32_t i = 0; i < VIRTQ_MAX_COUNT; i++)
     1745    {
     1746        PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[i];
     1747
     1748        pHlp->pfnSSMPutGCPhys64( pSSM, pVirtq->GCPhysVirtqDesc);
     1749        pHlp->pfnSSMPutGCPhys64( pSSM, pVirtq->GCPhysVirtqAvail);
     1750        pHlp->pfnSSMPutGCPhys64( pSSM, pVirtq->GCPhysVirtqUsed);
     1751        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uNotifyOffset);
     1752        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uMsix);
     1753        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uEnable);
     1754        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uSize);
     1755        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uAvailIdxShadow);
     1756        pHlp->pfnSSMPutU16(      pSSM, pVirtq->uUsedIdxShadow);
     1757        int rc = pHlp->pfnSSMPutMem(pSSM, pVirtq->szName, 32);
    17301758        AssertRCReturn(rc, rc);
    17311759    }
     
    17641792     * Load the state.
    17651793     */
    1766     pHlp->pfnSSMGetBool(pSSM, &pVirtio->fGenUpdatePending);
    1767     pHlp->pfnSSMGetU8(pSSM,   &pVirtio->fDeviceStatus);
    1768     pHlp->pfnSSMGetU8(pSSM,   &pVirtio->uConfigGeneration);
    1769     pHlp->pfnSSMGetU8(pSSM,   &pVirtio->uPciCfgDataOff);
    1770     pHlp->pfnSSMGetU8(pSSM,   &pVirtio->uISR);
    1771     pHlp->pfnSSMGetU16(pSSM,  &pVirtio->uVirtqSelect);
    1772     pHlp->pfnSSMGetU32(pSSM,  &pVirtio->uDeviceFeaturesSelect);
    1773     pHlp->pfnSSMGetU32(pSSM,  &pVirtio->uDriverFeaturesSelect);
    1774     pHlp->pfnSSMGetU64(pSSM,  &pVirtio->uDriverFeatures);
    1775 
    1776     for (uint32_t i = 0; i < VIRTQ_MAX_CNT; i++)
    1777     {
    1778         pHlp->pfnSSMGetGCPhys64(pSSM, &pVirtio->aGCPhysVirtqDesc[i]);
    1779         pHlp->pfnSSMGetGCPhys64(pSSM, &pVirtio->aGCPhysVirtqAvail[i]);
    1780         pHlp->pfnSSMGetGCPhys64(pSSM, &pVirtio->aGCPhysVirtqUsed[i]);
    1781         pHlp->pfnSSMGetU16(pSSM, &pVirtio->uVirtqNotifyOff[i]);
    1782         pHlp->pfnSSMGetU16(pSSM, &pVirtio->uVirtqMsixVector[i]);
    1783         pHlp->pfnSSMGetU16(pSSM, &pVirtio->uVirtqEnable[i]);
    1784         pHlp->pfnSSMGetU16(pSSM, &pVirtio->uVirtqSize[i]);
    1785         pHlp->pfnSSMGetU16(pSSM, &pVirtio->aVirtqState[i].uAvailIdxShadow);
    1786         pHlp->pfnSSMGetU16(pSSM, &pVirtio->aVirtqState[i].uUsedIdxShadow);
    1787         rc = pHlp->pfnSSMGetMem(pSSM, pVirtio->aVirtqState[i].szVirtqName,
    1788                                 sizeof(pVirtio->aVirtqState[i].szVirtqName));
     1794    pHlp->pfnSSMGetBool( pSSM, &pVirtio->fGenUpdatePending);
     1795    pHlp->pfnSSMGetU8(   pSSM, &pVirtio->fDeviceStatus);
     1796    pHlp->pfnSSMGetU8(   pSSM, &pVirtio->uConfigGeneration);
     1797    pHlp->pfnSSMGetU8(   pSSM, &pVirtio->uPciCfgDataOff);
     1798    pHlp->pfnSSMGetU8(   pSSM, &pVirtio->uISR);
     1799    pHlp->pfnSSMGetU16(  pSSM, &pVirtio->uVirtqSelect);
     1800    pHlp->pfnSSMGetU32(  pSSM, &pVirtio->uDeviceFeaturesSelect);
     1801    pHlp->pfnSSMGetU32(  pSSM, &pVirtio->uDriverFeaturesSelect);
     1802    pHlp->pfnSSMGetU64(  pSSM, &pVirtio->uDriverFeatures);
     1803
     1804    for (uint32_t i = 0; i < VIRTQ_MAX_COUNT; i++)
     1805    {
     1806        PVIRTQUEUE pVirtq = &pVirtio->aVirtqueues[i];
     1807
     1808        pHlp->pfnSSMGetGCPhys64( pSSM, &pVirtq->GCPhysVirtqDesc);
     1809        pHlp->pfnSSMGetGCPhys64( pSSM, &pVirtq->GCPhysVirtqAvail);
     1810        pHlp->pfnSSMGetGCPhys64( pSSM, &pVirtq->GCPhysVirtqUsed);
     1811        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uNotifyOffset);
     1812        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uMsix);
     1813        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uEnable);
     1814        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uSize);
     1815        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uAvailIdxShadow);
     1816        pHlp->pfnSSMGetU16(      pSSM, &pVirtq->uUsedIdxShadow);
     1817        rc = pHlp->pfnSSMGetMem( pSSM, pVirtq->szName,  sizeof(pVirtq->szName));
    17891818        AssertRCReturn(rc, rc);
    17901819    }
     
    18211850            break;
    18221851        case kvirtIoVmStateChangedResume:
    1823             virtioCoreNotifyGuestDriver(pVirtio->pDevInsR3, pVirtio, 0 /* uVirtqNbr */);
     1852            virtioCoreNotifyGuestDriver(pVirtio->pDevInsR3, pVirtio, 0 /* uVirtq */);
    18241853            break;
    18251854        default:
     
    18461875}
    18471876
    1848 
    1849 /**rr
     1877/**
    18501878 * Setup PCI device controller and Virtio state
    18511879 *
     
    19601988    /*
    19611989     * Notify capability (VirtIO 1.0 spec, section 4.1.4.4). Note: uLength is based on the choice
    1962      * of this implementation to make each queue's uVirtqNotifyOff equal to (VirtqSelect) ordinal
     1990     * of this implementation to make each queue's uNotifyOffset equal to (VirtqSelect) ordinal
    19631991     * value of the queue (different strategies are possible according to spec).
    19641992     */
     
    19711999    pCfg->uOffset  = pVirtioCC->pCommonCfgCap->uOffset + pVirtioCC->pCommonCfgCap->uLength;
    19722000    pCfg->uOffset  = RT_ALIGN_32(pCfg->uOffset, 4);
    1973     pCfg->uLength  = VIRTQ_MAX_CNT * VIRTIO_NOTIFY_OFFSET_MULTIPLIER + 2;  /* will change in VirtIO 1.1 */
     2001    pCfg->uLength  = VIRTQ_MAX_COUNT * VIRTIO_NOTIFY_OFFSET_MULTIPLIER + 2;  /* will change in VirtIO 1.1 */
    19742002    cbRegion += pCfg->uLength;
    19752003    SET_PCI_CAP_LOC(pPciDev, pCfg, pVirtio->LocNotifyCap, 1);
  • trunk/src/VBox/Devices/VirtIO/VirtioCore.h

    r85045 r85109  
    4949#define VIRTIO_MAX_VIRTQ_NAME_SIZE          32                   /**< Maximum length of a queue name           */
    5050#define VIRTQ_MAX_ENTRIES                   1024                 /**< Max size (# desc elements) of a virtq    */
    51 #define VIRTQ_MAX_CNT                       24                   /**< Max queues we allow guest to create      */
     51#define VIRTQ_MAX_COUNT                     24                   /**< Max queues we allow guest to create      */
    5252#define VIRTIO_NOTIFY_OFFSET_MULTIPLIER     2                    /**< VirtIO Notify Cap. MMIO config param     */
    5353#define VIRTIO_REGION_PCI_CAP               2                    /**< BAR for VirtIO Cap. MMIO (impl specific) */
     
    9292{
    9393    uint32_t            u32Magic;                                /**< Magic value, VIRTQBUF_MAGIC.             */
    94     uint16_t            uVirtqNbr;                               /**< VirtIO index of associated virtq         */
     94    uint16_t            uVirtq;                                  /**< VirtIO index of associated virtq         */
    9595    uint16_t            pad;
    9696    uint32_t volatile   cRefs;                                   /**< Reference counter.                       */
     
    188188
    189189/**
    190  * Local implementation's usage context of a queue (e.g. not part of VirtIO specification)
    191  */
    192 typedef struct VIRTQSTATE
    193 {
    194     uint16_t  uVirtqNbr;                                         /**< Index of this queue                       */
    195     char      szVirtqName[32];                                   /**< Dev-specific name of queue                */
    196     uint16_t  uAvailIdxShadow;                                   /**< Consumer's position in avail ring         */
    197     uint16_t  uUsedIdxShadow;                                    /**< Consumer's position in used ring          */
    198     bool      fVirtqRingEventThreshold;                          /**< Don't lose track while queueing ahead     */
    199 } VIRTQSTATE, *PVIRTQSTATE;
    200 
    201 /**
    202190 * VirtIO 1.0 Capabilities' related MMIO-mapped structs:
    203191 *
     
    218206    /* Virtq-specific fields (values reflect (via MMIO) info related to queue indicated by uVirtqSelect. */
    219207    uint16_t  uVirtqSelect;                                      /**< RW (selects queue focus for these fields) */
    220     uint16_t  uVirtqSize;                                        /**< RW (queue size, 0 - 2^n)                  */
    221     uint16_t  uVirtqMsixVector;                                  /**< RW (driver selects MSI-X queue vector)    */
    222     uint16_t  uVirtqEnable;                                      /**< RW (driver controls usability of queue)   */
    223     uint16_t  uVirtqNotifyOff;                                   /**< RO (offset into virtqueue; see spec)      */
    224     uint64_t  aGCPhysVirtqDesc;                                  /**< RW (driver writes desc table phys addr)   */
    225     uint64_t  aGCPhysVirtqAvail;                                 /**< RW (driver writes avail ring phys addr)   */
    226     uint64_t  aGCPhysVirtqUsed;                                  /**< RW (driver writes used ring  phys addr)   */
     208    uint16_t  uSize;                                             /**< RW (queue size, 0 - 2^n)                  */
     209    uint16_t  uMsix;                                             /**< RW (driver selects MSI-X queue vector)    */
     210    uint16_t  uEnable;                                           /**< RW (driver controls usability of queue)   */
     211    uint16_t  uNotifyOffset;                                     /**< RO (offset into virtqueue; see spec)      */
     212    uint64_t  GCPhysVirtqDesc;                                   /**< RW (driver writes desc table phys addr)   */
     213    uint64_t  GCPhysVirtqAvail;                                  /**< RW (driver writes avail ring phys addr)   */
     214    uint64_t  GCPhysVirtqUsed;                                   /**< RW (driver writes used ring  phys addr)   */
    227215} VIRTIO_PCI_COMMON_CFG_T, *PVIRTIO_PCI_COMMON_CFG_T;
    228216
     
    250238} VIRTIO_PCI_CAP_LOCATIONS_T;
    251239
     240typedef struct VIRTQUEUE
     241{
     242    RTGCPHYS                    GCPhysVirtqDesc;                  /**< (MMIO) PhysAdr per-Q desc structs   GUEST */
     243    RTGCPHYS                    GCPhysVirtqAvail;                 /**< (MMIO) PhysAdr per-Q avail structs  GUEST */
     244    RTGCPHYS                    GCPhysVirtqUsed;                  /**< (MMIO) PhysAdr per-Q used structs   GUEST */
     245    uint16_t                    uNotifyOffset;                    /**< (MMIO) per-Q notify offset           HOST */
     246    uint16_t                    uMsix;                            /**< (MMIO) Per-queue vector for MSI-X   GUEST */
     247    uint16_t                    uEnable;                          /**< (MMIO) Per-queue enable             GUEST */
     248    uint16_t                    uSize;                            /**< (MMIO) Per-queue size          HOST/GUEST */
     249    uint16_t                    uAvailIdxShadow;                  /**< Consumer's position in avail ring         */
     250    uint16_t                    uUsedIdxShadow;                   /**< Consumer's position in used ring          */
     251    bool                        fUsedRingEvent;                   /**< Flags if used idx to notify guest reached */
     252    uint16_t                    uVirtq;                           /**< Index of this queue                       */
     253    char                        szName[32];                       /**< Dev-specific name of queue                */
     254    uint8_t                     padding[3];
     255} VIRTQUEUE, *PVIRTQUEUE;
     256
    252257/**
    253258 * The core/common state of the VirtIO PCI devices, shared edition.
     
    255260typedef struct VIRTIOCORE
    256261{
    257     char                        szInstance[16];                    /**< Instance name, e.g. "VIRTIOSCSI0"         */
    258     PPDMDEVINS                  pDevInsR0;                         /**< Client device instance                    */
    259     PPDMDEVINS                  pDevInsR3;                         /**< Client device instance                    */
    260     RTGCPHYS                    aGCPhysVirtqDesc[VIRTQ_MAX_CNT];   /**< (MMIO) PhysAdr per-Q desc structs   GUEST */
    261     RTGCPHYS                    aGCPhysVirtqAvail[VIRTQ_MAX_CNT];  /**< (MMIO) PhysAdr per-Q avail structs  GUEST */
    262     RTGCPHYS                    aGCPhysVirtqUsed[VIRTQ_MAX_CNT];   /**< (MMIO) PhysAdr per-Q used structs   GUEST */
    263     uint16_t                    uVirtqNotifyOff[VIRTQ_MAX_CNT];    /**< (MMIO) per-Q notify offset           HOST */
    264     uint16_t                    uVirtqMsixVector[VIRTQ_MAX_CNT];   /**< (MMIO) Per-queue vector for MSI-X   GUEST */
    265     uint16_t                    uVirtqEnable[VIRTQ_MAX_CNT];       /**< (MMIO) Per-queue enable             GUEST */
    266     uint16_t                    uVirtqSize[VIRTQ_MAX_CNT];         /**< (MMIO) Per-queue size          HOST/GUEST */
    267     uint16_t                    uVirtqSelect;                      /**< (MMIO) queue selector               GUEST */
    268     uint16_t                    padding;
    269     uint64_t                    uDeviceFeatures;                   /**< (MMIO) Host features offered         HOST */
    270     uint64_t                    uDriverFeatures;                   /**< (MMIO) Host features accepted       GUEST */
    271     uint32_t                    uDeviceFeaturesSelect;             /**< (MMIO) hi/lo select uDeviceFeatures GUEST */
    272     uint32_t                    uDriverFeaturesSelect;             /**< (MMIO) hi/lo select uDriverFeatures GUEST */
    273     uint32_t                    uMsixConfig;                       /**< (MMIO) MSI-X vector                 GUEST */
    274     uint8_t                     fDeviceStatus;                     /**< (MMIO) Device Status                GUEST */
    275     uint8_t                     uPrevDeviceStatus;                 /**< (MMIO) Prev Device Status           GUEST */
    276     uint8_t                     uConfigGeneration;                 /**< (MMIO) Device config sequencer       HOST */
    277     VIRTQSTATE                  aVirtqState[VIRTQ_MAX_CNT];        /**< Local impl-specific queue context         */
     262    char                        szInstance[16];                   /**< Instance name, e.g. "VIRTIOSCSI0"         */
     263    PPDMDEVINS                  pDevInsR0;                        /**< Client device instance                    */
     264    PPDMDEVINS                  pDevInsR3;                        /**< Client device instance                    */
     265    VIRTQUEUE                   aVirtqueues[VIRTQ_MAX_COUNT];     /**< (MMIO) VirtIO contexts for queues         */
     266    uint64_t                    uDeviceFeatures;                  /**< (MMIO) Host features offered         HOST */
     267    uint64_t                    uDriverFeatures;                  /**< (MMIO) Host features accepted       GUEST */
     268    uint32_t                    uDeviceFeaturesSelect;            /**< (MMIO) hi/lo select uDeviceFeatures GUEST */
     269    uint32_t                    uDriverFeaturesSelect;            /**< (MMIO) hi/lo select uDriverFeatures GUEST */
     270    uint32_t                    uMsixConfig;                      /**< (MMIO) MSI-X vector                 GUEST */
     271    uint8_t                     fDeviceStatus;                    /**< (MMIO) Device Status                GUEST */
     272    uint8_t                     uPrevDeviceStatus;                /**< (MMIO) Prev Device Status           GUEST */
     273    uint8_t                     uConfigGeneration;                /**< (MMIO) Device config sequencer       HOST */
    278274
    279275    /** @name The locations of the capability structures in PCI config space and the BAR.
    280276     * @{ */
    281     VIRTIO_PCI_CAP_LOCATIONS_T  LocPciCfgCap;                      /**< VIRTIO_PCI_CFG_CAP_T                      */
    282     VIRTIO_PCI_CAP_LOCATIONS_T  LocNotifyCap;                      /**< VIRTIO_PCI_NOTIFY_CAP_T                   */
    283     VIRTIO_PCI_CAP_LOCATIONS_T  LocCommonCfgCap;                   /**< VIRTIO_PCI_CAP_T                          */
    284     VIRTIO_PCI_CAP_LOCATIONS_T  LocIsrCap;                         /**< VIRTIO_PCI_CAP_T                          */
    285     VIRTIO_PCI_CAP_LOCATIONS_T  LocDeviceCap;                      /**< VIRTIO_PCI_CAP_T + custom data.           */
     277    VIRTIO_PCI_CAP_LOCATIONS_T  LocPciCfgCap;                     /**< VIRTIO_PCI_CFG_CAP_T                      */
     278    VIRTIO_PCI_CAP_LOCATIONS_T  LocNotifyCap;                     /**< VIRTIO_PCI_NOTIFY_CAP_T                   */
     279    VIRTIO_PCI_CAP_LOCATIONS_T  LocCommonCfgCap;                  /**< VIRTIO_PCI_CAP_T                          */
     280    VIRTIO_PCI_CAP_LOCATIONS_T  LocIsrCap;                        /**< VIRTIO_PCI_CAP_T                          */
     281    VIRTIO_PCI_CAP_LOCATIONS_T  LocDeviceCap;                     /**< VIRTIO_PCI_CAP_T + custom data.           */
    286282    /** @} */
    287283
    288     bool                        fGenUpdatePending;                 /**< If set, update cfg gen after driver reads */
    289     uint8_t                     uPciCfgDataOff;                    /**< Offset to PCI configuration data area     */
    290     uint8_t                     uISR;                              /**< Interrupt Status Register.                */
    291     uint8_t                     fMsiSupport;                       /**< Flag set if using MSI instead of ISR      */
     284    uint16_t                    uVirtqSelect;                     /**< (MMIO) queue selector               GUEST */
     285    bool                        fGenUpdatePending;                /**< If set, update cfg gen after driver reads */
     286    uint8_t                     uPciCfgDataOff;                   /**< Offset to PCI configuration data area     */
     287    uint8_t                     uISR;                             /**< Interrupt Status Register.                */
     288    uint8_t                     fMsiSupport;                      /**< Flag set if using MSI instead of ISR      */
    292289    /** The MMIO handle for the PCI capability region (\#2). */
    293290    IOMMMIOHANDLE               hMmioPciCap;
     
    416413 * queue management, informing the core of the name of the queue associated spec-defined
    417414 * device specific queue number (which also happens to be the index into VirtIO's array
    418  * of queue structs].
     415 * of queue structs].  uVirtqNbr is used as the 'handle' for virt queues in this API.
     416 * They are unambiguous (the VirtIO specification defines how virtq numbers are assigned
     417 * for each device type), and it helps prevent muddying of the core state by devices
     418 * and vice versa by eliminating direct access to otherwise private structs.
    419419 *
    420420 * @param   pVirtio     Pointer to the shared virtio state.
     
    477477 * using the command: "VboxManage debugvm <VM name or id> info <device name> [args]"
    478478 *
    479  * Example:  VBoxManage debugvm myVnetVm info "virtio-net" all
     479 * Example:  VBoxManage debugvm myVnetVm info "virtio-net" help
    480480 *
    481481 * This is implemented currently to be invoked by the inheriting device-specific code
     
    505505 * operation if virtioCoreR3VirtqAvailRingNext() is called to consume the buffer from the avail ring,
    506506 * at which point virtioCoreR3VirtqUsedBufPut() must be called to complete the roundtrip
    507  * transaction putting the descriptor on the used ring.
     507 * transaction by putting the descriptor on the used ring.
    508508 *
    509509 *
     
    579579 * intervening a roundtrip transaction, wherein I/O transactions are always initiated by
    580580 * the guest and completed by the host. In other words, for the host to send any data to the
    581  * guest, the guest must provide buffers for the host to fill to the avail ring of the
     581 * guest, the guest must provide buffers, for the host to fill, via the avail ring of the
    582582 * virtq.
    583583 *
     
    697697DECLINLINE(bool) virtioCoreIsVirtqEnabled(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    698698{
    699     Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    700     return pVirtio->uVirtqEnable[uVirtqNbr] != 0;
     699    Assert(uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqueues));
     700    return pVirtio->aVirtqueues[uVirtqNbr].uEnable != 0;
    701701}
    702702
     
    711711DECLINLINE(const char *) virtioCoreVirtqGetName(PVIRTIOCORE pVirtio, uint16_t uVirtqNbr)
    712712{
    713     Assert((size_t)uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqState));
    714     return pVirtio->aVirtqState[uVirtqNbr].szVirtqName;
     713    Assert((size_t)uVirtqNbr < RT_ELEMENTS(pVirtio->aVirtqueues));
     714    return pVirtio->aVirtqueues[uVirtqNbr].szName;
    715715}
    716716
     
    813813RTGCPHYS virtioCoreGCPhysChainGetNextSeg(PVIRTIOSGBUF pGcSgBuf, size_t *pcbSeg);
    814814RTGCPHYS virtioCoreGCPhysChainAdvance(PVIRTIOSGBUF pGcSgBuf, size_t cbAdvance);
    815 void     virtioCoreGCPhysChainInit(PVIRTIOSGBUF pSgBuf, PVIRTIOSGSEG paSegs, size_t cSegs);
    816815size_t   virtioCoreGCPhysChainCalcBufSize(PCVIRTIOSGBUF pGcSgBuf);
    817816
     
    928927        uint32_t uOffsetInMember = uOffsetOfAccess - RT_UOFFSETOF(tCfgStruct, member); \
    929928        if (fWrite) \
    930             memcpy(((char *)&(pCfgStruct)->member[uIdx]) + uOffsetInMember, pv, cb); \
     929            memcpy(((char *)&(pCfgStruct[uIdx].member)) + uOffsetInMember, pv, cb); \
    931930        else \
    932             memcpy(pv, ((const char *)&(pCfgStruct)->member[uIdx]) + uOffsetInMember, cb); \
     931            memcpy(pv, ((const char *)&(pCfgStruct[uIdx].member)) + uOffsetInMember, cb); \
    933932        VIRTIO_DEV_CONFIG_LOG_INDEXED_ACCESS(member, tCfgStruct, uOffsetOfAccess, uIdx); \
    934933    } while(0)
     
    948947        else \
    949948        { \
    950             memcpy(pv, ((const char *)&(pCfgStruct)->member[uIdx]) + uOffsetInMember, cb); \
     949            memcpy(pv, ((const char *)&(pCfgStruct[uIdx].member)) + uOffsetInMember, cb); \
    951950            VIRTIO_DEV_CONFIG_LOG_INDEXED_ACCESS(member, tCfgStruct, uOffsetOfAccess, uIdx); \
    952951        } \
Note: See TracChangeset for help on using the changeset viewer.

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