VirtualBox

Changeset 61384 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Jun 1, 2016 6:33:47 PM (9 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
107695
Message:

VMMDev/Testing: Added a 64-byte readback register with two access areas (same context / always ring-3). Extended the NOP register handling to include odd access so we can read the whole 32-bit width in two 16-bit accesses (useful for 16-bit C code).

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

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/VMMDev/VMMDevState.h

    r58164 r61384  
    2424#ifndef VBOX_WITHOUT_TESTING_FEATURES
    2525# include <iprt/test.h>
     26# include <VBox/VMMDevTesting.h>
    2627#endif
    2728
     
    350351            char        szName[1024 - 8 - 4];
    351352        } Value;
     353
     354        /** The read back register (VMMDEV_TESTING_MMIO_OFF_READBACK,
     355         *  VMMDEV_TESTING_MMIO_OFF_READBACK_R3). */
     356        uint8_t         abReadBack[VMMDEV_TESTING_READBACK_SIZE];
    352357    } TestingData;
    353358    /** The XML output file name (can be a named pipe, doesn't matter to us). */
  • trunk/src/VBox/Devices/VMMDev/VMMDevTesting.cpp

    r60440 r61384  
    5555    {
    5656        case VMMDEV_TESTING_MMIO_NOP:
     57        case VMMDEV_TESTING_MMIO_NOP_R3:
     58#ifdef IN_RING3
     59            return VINF_IOM_R3_MMIO_WRITE;
     60#else
     61            return VINF_SUCCESS;
     62#endif
     63
     64        default:
     65        {
     66            /*
     67             * Readback register (64 bytes wide).
     68             */
     69            uint32_t off = GCPhysAddr - VMMDEV_TESTING_MMIO_BASE;
     70            if (   (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK
     71                    && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK + VMMDEV_TESTING_READBACK_SIZE)
     72#ifndef IN_RING3
     73                || (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK_R3
     74                    && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK_R3 + VMMDEV_TESTING_READBACK_SIZE)
     75#endif
     76                    )
     77            {
     78                VMMDevState *pThis = PDMINS_2_DATA(pDevIns, VMMDevState *);
     79                off &= VMMDEV_TESTING_READBACK_SIZE - 1;
     80                switch (cb)
     81                {
     82                    case 8: *(uint64_t *)&pThis->TestingData.abReadBack[off] = *(uint64_t const *)pv; break;
     83                    case 4: *(uint32_t *)&pThis->TestingData.abReadBack[off] = *(uint32_t const *)pv; break;
     84                    case 2: *(uint16_t *)&pThis->TestingData.abReadBack[off] = *(uint16_t const *)pv; break;
     85                    case 1: *(uint8_t  *)&pThis->TestingData.abReadBack[off] = *(uint8_t  const *)pv; break;
     86                    default: memcpy(&pThis->TestingData.abReadBack[off], pv, cb); break;
     87                }
     88                return VINF_SUCCESS;
     89            }
     90#ifndef IN_RING3
     91            if (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK_R3
     92                && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK_R3 + 64)
     93                return VINF_IOM_R3_MMIO_WRITE;
     94#endif
     95
     96            break;
     97        }
     98
     99        /*
     100         * Odd NOP accesses.
     101         */
     102        case VMMDEV_TESTING_MMIO_NOP_R3 + 1:
     103        case VMMDEV_TESTING_MMIO_NOP_R3 + 2:
     104        case VMMDEV_TESTING_MMIO_NOP_R3 + 3:
     105        case VMMDEV_TESTING_MMIO_NOP_R3 + 4:
     106        case VMMDEV_TESTING_MMIO_NOP_R3 + 5:
     107        case VMMDEV_TESTING_MMIO_NOP_R3 + 6:
     108        case VMMDEV_TESTING_MMIO_NOP_R3 + 7:
     109#ifndef IN_RING3
     110            return VINF_IOM_R3_MMIO_WRITE;
     111#endif
     112        case VMMDEV_TESTING_MMIO_NOP    + 1:
     113        case VMMDEV_TESTING_MMIO_NOP    + 2:
     114        case VMMDEV_TESTING_MMIO_NOP    + 3:
     115        case VMMDEV_TESTING_MMIO_NOP    + 4:
     116        case VMMDEV_TESTING_MMIO_NOP    + 5:
     117        case VMMDEV_TESTING_MMIO_NOP    + 6:
     118        case VMMDEV_TESTING_MMIO_NOP    + 7:
     119            return VINF_SUCCESS;
     120    }
     121    return VINF_SUCCESS;
     122}
     123
     124
     125/**
     126 * @callback_method_impl{FNIOMMMIOREAD}
     127 */
     128PDMBOTHCBDECL(int) vmmdevTestingMmioRead(PPDMDEVINS pDevIns, void *pvUser, RTGCPHYS GCPhysAddr, void *pv, unsigned cb)
     129{
     130    switch (GCPhysAddr)
     131    {
     132        case VMMDEV_TESTING_MMIO_NOP_R3:
     133#ifndef IN_RING3
     134            return VINF_IOM_R3_MMIO_READ;
     135#endif
     136            /* fall thru. */
     137        case VMMDEV_TESTING_MMIO_NOP:
    57138            switch (cb)
    58139            {
    59140                case 8:
     141                    *(uint64_t *)pv = VMMDEV_TESTING_NOP_RET | ((uint64_t)VMMDEV_TESTING_NOP_RET << 32);
     142                    break;
    60143                case 4:
     144                    *(uint32_t *)pv = VMMDEV_TESTING_NOP_RET;
     145                    break;
    61146                case 2:
     147                    *(uint16_t *)pv = (uint16_t)VMMDEV_TESTING_NOP_RET;
     148                    break;
    62149                case 1:
     150                    *(uint8_t *)pv  = (uint8_t)VMMDEV_TESTING_NOP_RET;
    63151                    break;
    64152                default:
     
    68156            return VINF_SUCCESS;
    69157
    70         case VMMDEV_TESTING_MMIO_NOP_R3:
    71             switch (cb)
    72             {
    73                 case 8:
    74                 case 4:
    75                 case 2:
    76                 case 1:
    77 #ifndef IN_RING3
    78                     return VINF_IOM_R3_MMIO_READ_WRITE;
    79 #else
    80                     return VINF_SUCCESS;
    81 #endif
    82                 default:
    83                     AssertFailed();
    84                     return VERR_INTERNAL_ERROR_5;
    85             }
    86158
    87159        default:
    88             break;
    89     }
    90     return VINF_SUCCESS;
    91 }
    92 
    93 
    94 /**
    95  * @callback_method_impl{FNIOMMMIOREAD}
    96  */
    97 PDMBOTHCBDECL(int) vmmdevTestingMmioRead(PPDMDEVINS pDevIns, void *pvUser, RTGCPHYS GCPhysAddr, void *pv, unsigned cb)
    98 {
    99     switch (GCPhysAddr)
    100     {
    101         case VMMDEV_TESTING_MMIO_NOP_R3:
    102 #ifndef IN_RING3
    103             switch (cb)
    104             {
    105                 case 8:
    106                 case 4:
    107                 case 2:
    108                 case 1:
    109                     return VINF_IOM_R3_MMIO_READ;
    110             }
    111 #endif
    112             /* fall thru. */
    113         case VMMDEV_TESTING_MMIO_NOP:
    114             switch (cb)
    115             {
    116                 case 8:
    117                     *(uint64_t *)pv = VMMDEV_TESTING_NOP_RET | ((uint64_t)VMMDEV_TESTING_NOP_RET << 32);
    118                     break;
    119                 case 4:
    120                     *(uint32_t *)pv = VMMDEV_TESTING_NOP_RET;
    121                     break;
    122                 case 2:
    123                     *(uint16_t *)pv = (uint16_t)VMMDEV_TESTING_NOP_RET;
    124                     break;
    125                 case 1:
    126                     *(uint8_t *)pv  = (uint8_t)VMMDEV_TESTING_NOP_RET;
    127                     break;
    128                 default:
    129                     AssertFailed();
    130                     return VERR_INTERNAL_ERROR_5;
    131             }
     160        {
     161            /*
     162             * Readback register (64 bytes wide).
     163             */
     164            uint32_t off = GCPhysAddr - VMMDEV_TESTING_MMIO_BASE;
     165            if (   (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK
     166                    && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK + 64)
     167#ifndef IN_RING3
     168                || (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK_R3
     169                    && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK_R3 + 64)
     170#endif
     171                    )
     172            {
     173                VMMDevState *pThis = PDMINS_2_DATA(pDevIns, VMMDevState *);
     174                off &= 0x3f;
     175                switch (cb)
     176                {
     177                    case 8: *(uint64_t *)pv = *(uint64_t const *)&pThis->TestingData.abReadBack[off]; break;
     178                    case 4: *(uint32_t *)pv = *(uint32_t const *)&pThis->TestingData.abReadBack[off]; break;
     179                    case 2: *(uint16_t *)pv = *(uint16_t const *)&pThis->TestingData.abReadBack[off]; break;
     180                    case 1: *(uint8_t  *)pv = *(uint8_t  const *)&pThis->TestingData.abReadBack[off]; break;
     181                    default: memcpy(pv, &pThis->TestingData.abReadBack[off], cb); break;
     182                }
     183                return VINF_SUCCESS;
     184            }
     185#ifndef IN_RING3
     186            if (   off      >= VMMDEV_TESTING_MMIO_OFF_READBACK_R3
     187                && off + cb <= VMMDEV_TESTING_MMIO_OFF_READBACK_R3 + 64)
     188                return VINF_IOM_R3_MMIO_READ;
     189#endif
     190            break;
     191        }
     192
     193        /*
     194         * Odd NOP accesses (for 16-bit code mainly).
     195         */
     196        case VMMDEV_TESTING_MMIO_NOP_R3 + 1:
     197        case VMMDEV_TESTING_MMIO_NOP_R3 + 2:
     198        case VMMDEV_TESTING_MMIO_NOP_R3 + 3:
     199        case VMMDEV_TESTING_MMIO_NOP_R3 + 4:
     200        case VMMDEV_TESTING_MMIO_NOP_R3 + 5:
     201        case VMMDEV_TESTING_MMIO_NOP_R3 + 6:
     202        case VMMDEV_TESTING_MMIO_NOP_R3 + 7:
     203#ifndef IN_RING3
     204            return VINF_IOM_R3_MMIO_READ;
     205#endif
     206        case VMMDEV_TESTING_MMIO_NOP    + 1:
     207        case VMMDEV_TESTING_MMIO_NOP    + 2:
     208        case VMMDEV_TESTING_MMIO_NOP    + 3:
     209        case VMMDEV_TESTING_MMIO_NOP    + 4:
     210        case VMMDEV_TESTING_MMIO_NOP    + 5:
     211        case VMMDEV_TESTING_MMIO_NOP    + 6:
     212        case VMMDEV_TESTING_MMIO_NOP    + 7:
     213        {
     214            static uint8_t const s_abNopValue[8] =
     215            {
     216                 VMMDEV_TESTING_NOP_RET        & 0xff,
     217                (VMMDEV_TESTING_NOP_RET >>  8) & 0xff,
     218                (VMMDEV_TESTING_NOP_RET >> 16) & 0xff,
     219                (VMMDEV_TESTING_NOP_RET >> 24) & 0xff,
     220                VMMDEV_TESTING_NOP_RET        & 0xff,
     221                (VMMDEV_TESTING_NOP_RET >>  8) & 0xff,
     222                (VMMDEV_TESTING_NOP_RET >> 16) & 0xff,
     223                (VMMDEV_TESTING_NOP_RET >> 24) & 0xff,
     224            };
     225
     226            memset(pv, 0xff, cb);
     227            memcpy(pv, &s_abNopValue[GCPhysAddr & 7], RT_MIN(8 - (GCPhysAddr & 7), cb));
    132228            return VINF_SUCCESS;
    133 
    134         default:
    135             break;
     229        }
    136230    }
    137231
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