VirtualBox

Changeset 46728 in vbox for trunk/src/VBox/VMM/testcase


Ignore:
Timestamp:
Jun 21, 2013 4:58:04 PM (11 years ago)
Author:
vboxsync
Message:

-> home

Location:
trunk/src/VBox/VMM/testcase/Instructions
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/testcase/Instructions/InstructionTestGen.py

    r46571 r46728  
    341341        """ Writes the instruction with two general registers as operands. """
    342342        if cbEffOp == 8:
    343             iOp2 = iOp2 % len(g_asGRegs32);
    344             oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs64[iOp1], g_asGRegs32[iOp2]));
     343            oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs64[iOp1], g_asGRegs64[iOp2]));
    345344        elif cbEffOp == 4:
    346             oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs32[iOp1], g_asGRegs16[iOp2]));
     345            oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs32[iOp1], g_asGRegs32[iOp2]));
    347346        elif cbEffOp == 2:
    348             oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs16[iOp1], g_asGRegs8[iOp2]));
     347            oGen.write('        %s %s, %s\n' % (self.sInstr, g_asGRegs16[iOp1], g_asGRegs16[iOp2]));
    349348        else:
    350349            assert False;
     350        return True;
     351
     352    def writeInstrGregPureRM(self, cbEffOp, iOp1, cAddrBits, iOp2, iMod, offDisp, oGen):
     353        """ Writes the instruction with two general registers as operands. """
     354        if cbEffOp == 8:
     355            oGen.write('        %s %s, [' % (self.sInstr, g_asGRegs64[iOp1],));
     356        elif cbEffOp == 4:
     357            oGen.write('        %s %s, [' % (self.sInstr, g_asGRegs64[iOp1],));
     358        elif cbEffOp == 2:
     359            oGen.write('        %s %s, [' % (self.sInstr, g_asGRegs16[iOp1],));
     360        else:
     361            assert False;
     362
     363        if iOp2 == 5 and iMod == 0:
     364            oGen.write('VBINSTST_NAME(g_u%sData)' % (cbEffOp * 8,))
     365            if oGen.oTarget.is64Bit():
     366                oGen.write(' wrt rip');
     367        else:
     368            if iMod == 1:
     369                oGen.write('byte %d + ' % (offDisp,));
     370            elif iMod == 2:
     371                oGen.write('dword %d + ' % (offDisp,));
     372            else:
     373                assert iMod == 0;
     374
     375            if cAddrBits == 64:
     376                oGen.write(g_asGRegs64[iOp2]);
     377            elif cAddrBits == 32:
     378                oGen.write(g_asGRegs32[iOp2]);
     379            elif cAddrBits == 16:
     380                assert False; ## @todo implement 16-bit addressing.
     381            else:
     382                assert False, str(cAddrBits);
     383
     384        oGen.write(']\n');
    351385        return True;
    352386
     
    357391        oGen.write('        push    %s\n' % (oGen.oTarget.asGRegs[iOp2],));
    358392        self.writeInstrGregGreg(cbEffOp, iOp1, iOp2, oGen);
    359         oGen.pushConst(uResult, cbMaxOp);
     393        oGen.pushConst(uResult);
    360394        oGen.write('        call VBINSTST_NAME(%s)\n' % (oGen.needGRegChecker(iOp1, iOp2),));
    361         return True;
    362 
    363     def generateStandardTests(self, oGen):
     395        _ = cbMaxOp;
     396        return True;
     397
     398    def generateMemSetupPureRM(self, oGen, cAddrBits, cbEffOp, iOp2, iMod, uInput, offDisp = None):
     399        """ Sets up memory for a pure R/M addressed read, iOp2 being the R/M value. """
     400        oGen.pushConst(uInput);
     401        assert offDisp is None or iMod != 0;
     402        if (iOp2 != 5 and iOp2 != 13) or iMod != 0:
     403            oGen.write('        call    VBINSTST_NAME(%s)\n'
     404                       % (oGen.needGRegMemSetup(cAddrBits, cbEffOp, iOp2, offDisp),));
     405        else:
     406            ## @todo generate REX.B=1 variant.
     407            oGen.write('        call    VBINSTST_NAME(Common_SetupMemReadU%u)\n' % (cbEffOp/2,));
     408        oGen.write('        push    %s\n' % (oGen.oTarget.asGRegs[iOp2],));
     409        return True;
     410
     411
     412    def generateOneStdTestGregMemNoSib(self, oGen, cAddrBits, cbEffOp, cbMaxOp, iOp1, iOp2, uInput, uResult):
     413        """ Generate mode 0, 1 and 2 test for the R/M=iOp2. """
     414        if cAddrBits == 16:
     415            _ = cbMaxOp;
     416        else:
     417            iMod = 0; # No disp, except for i=5.
     418            oGen.write('        call    VBINSTST_NAME(Common_LoadKnownValues)\n');
     419            self.generateMemSetupPureRM(oGen, cAddrBits, cbEffOp, iOp2, iMod, uInput);
     420            self.writeInstrGregPureRM(cbEffOp, iOp1, cAddrBits, iOp2, iMod, None, oGen);
     421            oGen.pushConst(uResult);
     422            oGen.write('        call    VBINSTST_NAME(%s)\n' % (oGen.needGRegChecker(iOp1, iOp2),));
     423
     424            iMod = 2;
     425            for offDisp in (127, -128):
     426                oGen.write('        call    VBINSTST_NAME(Common_LoadKnownValues)\n');
     427                self.generateMemSetupPureRM(oGen, cAddrBits, cbEffOp, iOp2, iMod, uInput, offDisp);
     428                self.writeInstrGregPureRM(cbEffOp, iOp1, cAddrBits, iOp2, iMod, offDisp, oGen);
     429                oGen.pushConst(uResult);
     430                oGen.write('        call    VBINSTST_NAME(%s)\n' % (oGen.needGRegChecker(iOp1, iOp2),));
     431
     432            iMod = 2;
     433            for offDisp in (2147483647, -2147483648):
     434                oGen.write('        call    VBINSTST_NAME(Common_LoadKnownValues)\n');
     435                self.generateMemSetupPureRM(oGen, cAddrBits, cbEffOp, iOp2, iMod, uInput, offDisp);
     436                self.writeInstrGregPureRM(cbEffOp, iOp1, cAddrBits, iOp2, iMod, offDisp, oGen);
     437                oGen.pushConst(uResult);
     438                oGen.write('        call    VBINSTST_NAME(%s)\n' % (oGen.needGRegChecker(iOp1, iOp2),));
     439
     440        return True;
     441
     442
     443    def generateStandardTests(self, oGen): # pylint: disable=R0914
    364444        """ Generate standard tests. """
    365445
     
    378458
    379459        # Register tests
     460        if False:
     461            for cbEffOp in self.acbOpVars:
     462                if cbEffOp > cbMaxOp:
     463                    continue;
     464                for iOp1 in range(oGen.oTarget.getGRegCount()):
     465                    if oGen.oTarget.asGRegsNoSp[iOp1] is None:
     466                        continue;
     467                    for iOp2 in oOp2Range:
     468                        if oGen.oTarget.asGRegsNoSp[iOp2] is None:
     469                            continue;
     470                        for uInput in (auLongInputs if iOp1 == iLongOp1 and iOp2 == iLongOp2 else auShortInputs):
     471                            uResult = self.fnCalcResult(cbEffOp, uInput,
     472                                                        oGen.auRegValues[iOp1] if iOp1 != iOp2 else uInput, oGen);
     473                            oGen.newSubTest();
     474                            self.generateOneStdTestGregGreg(oGen, cbEffOp, cbMaxOp, iOp1, iOp2, uInput, uResult);
     475
     476        # Memory test.
    380477        for cbEffOp in self.acbOpVars:
    381478            if cbEffOp > cbMaxOp:
    382479                continue;
    383             for iOp1 in range(oGen.oTarget.getGRegCount()):
     480            for iOp1 in oOp1MemRange:
    384481                if oGen.oTarget.asGRegsNoSp[iOp1] is None:
    385482                    continue;
    386                 for iOp2 in oOp2Range:
    387                     if oGen.oTarget.asGRegsNoSp[iOp2] is None:
    388                         continue;
    389                     for uInput in (auLongInputs if iOp1 == iLongOp1 and iOp2 == iLongOp2 else auShortInputs):
    390                         uResult = self.fnCalcResult(cbEffOp, uInput, oGen.auRegValues[iOp1] if iOp1 != iOp2 else uInput, oGen);
    391                         oGen.newSubTest();
    392                         self.generateOneStdTestGregGreg(oGen, cbEffOp, cbMaxOp, iOp1, iOp2, uInput, uResult);
    393 
    394         ## Memory test.
    395         #for cbEffOp in self.acbOpVars:
    396         #    if cbEffOp > cbMaxOp:
    397         #        continue;
    398         #    for iOp1 in oOp1MemRange:
    399         #        if oGen.oTarget.asGRegsNoSp[iOp1] is None:
    400         #            continue;
    401         #        for cbAddrMode in oGen.oTarget.getAddrModes():
    402         #
    403         #            for uInput in (auLongInputs if iOp1 == iLongOp1 and False else auShortInputs):
    404         #                uResult = self.fnCalcResult(cbEffOp, uInput, oGen.auRegValues[iOp1] if iOp1 != iOp2 else uInput, oGen);
    405         #                oGen.newSubTest();
    406         #                self.generateOneStdTestGregGreg(oGen, cbEffOp, cbMaxOp, iOp1, iOp2, uInput, uResult);
    407         #
     483                for cAddrBits in oGen.oTarget.getAddrModes():
     484                    for iOp2 in range(len(oGen.oTarget.asGRegs)):
     485                        if iOp2 != 4:
     486
     487                            for uInput in (auLongInputs if iOp1 == iLongOp1 and False else auShortInputs):
     488                                oGen.newSubTest();
     489                                if iOp1 == iOp2 and iOp2 != 5 and iOp2 != 13 and cbEffOp != cbMaxOp:
     490                                    continue; # Don't know the high bit of the address ending up the result - skip it.
     491                                uResult = self.fnCalcResult(cbEffOp, uInput, oGen.auRegValues[iOp1], oGen);
     492                                self.generateOneStdTestGregMemNoSib(oGen, cAddrBits, cbEffOp, cbMaxOp,
     493                                                                    iOp1, iOp2, uInput, uResult);
     494                        else:
     495                            pass; # SIB
     496                    break; ## remove me!
     497                break; ## remove me!
     498            break; ## remove me!
    408499
    409500        return True;
     
    504595        self.sFile          = '';
    505596        self.dCheckFns      = dict();
     597        self.dMemSetupFns   = dict();
    506598        self.d64BitConsts   = dict();
    507599
     
    548640        return 'Common_Check_%s_%s' % (self.oTarget.asGRegs[iReg1], self.oTarget.asGRegs[iReg2]);
    549641
     642    def needGRegMemSetup(self, cAddrBits, cbEffOp, iReg1, offDisp = None):
     643        """
     644        Records the need for a given register checker function, returning its label.
     645        """
     646        sName = '%ubit_U%u_%s' % (cAddrBits, cbEffOp * 8, self.oTarget.asGRegs[iReg1]);
     647        if offDisp is not None:
     648            sName += '_0x%016x' % (offDisp & UINT64_MAX, );
     649        if sName in self.dCheckFns:
     650            self.dMemSetupFns[sName] += 1;
     651        else:
     652            self.dMemSetupFns[sName]  = 1;
     653        return 'Common_MemSetup_' + sName;
     654
    550655    def need64BitConstant(self, uVal):
    551656        """
     
    560665        return 'g_u64Const_0x%016x' % (uVal, );
    561666
    562     def pushConst(self, uResult, cbMaxOp):
     667    def pushConst(self, uResult):
    563668        """
    564669        Emits a push constant value, taking care of high values on 64-bit hosts.
    565670        """
    566         if cbMaxOp == 8 and uResult >= 0x80000000:
     671        if self.oTarget.is64Bit() and uResult >= 0x80000000:
    567672            self.write('        push    qword [%s wrt rip]\n' % (self.need64BitConstant(uResult),));
    568673        else:
     
    610715                   ';\n');
    611716        self.write('VBINSTST_BEGINDATA\n'
    612                    'VBINSTST_GLOBALNAME_EX g_pvLowMem4K, data hidden\n'
     717                   'VBINSTST_GLOBALNAME_EX g_pvLow16Mem4K, data hidden\n'
     718                   '        dq      0\n'
     719                   'VBINSTST_GLOBALNAME_EX g_pvLow32Mem4K, data hidden\n'
     720                   '        dq      0\n'
     721                   'VBINSTST_GLOBALNAME_EX g_pvMem4K, data hidden\n'
    613722                   '        dq      0\n'
    614723                   'VBINSTST_GLOBALNAME_EX g_uVBInsTstSubTestIndicator, data hidden\n'
  • trunk/src/VBox/VMM/testcase/Instructions/env-common.mac

    r46548 r46728  
    9595
    9696
     97
     98;*******************************************************************************
     99;*  Internal Functions                                                         *
     100;*******************************************************************************
     101
     102
    97103;;
    98104; Report bad register value.
     
    149155VBINSTST_ENDPROC   Common_BadValue
    150156
    151 %endif
    152 
     157
     158
     159;
     160; Global data variables used by Common_SetupMemReadUxx.
     161;
     162BEGINDATA
     163VBINSTST_GLOBALNAME_EX g_u64Data, data hidden
     164        dq      0
     165VBINSTST_GLOBALNAME_EX g_u32Data, data hidden
     166        dd      0
     167VBINSTST_GLOBALNAME_EX g_u16Data, data hidden
     168        dw      0
     169VBINSTST_GLOBALNAME_EX g_u8Data, data hidden
     170        db      0
     171        db      90h
     172
     173BEGINCODE
     174
     175;;
     176; Sets up g_u8Data.
     177; @param    uValue
     178VBINSTST_BEGINPROC Common_SetupMemReadU8
     179        push    sAX
     180        mov     ax, [xSP + sCB + xCB]
     181        mov     [VBINSTST_NAME(g_u8Data) xWrtRip], ax
     182        pop     sAX
     183        ret sCB
     184VBINSTST_ENDPROC   Common_SetupMemReadU8
     185
     186;;
     187; Sets up g_u16Data.
     188; @param    uValue
     189VBINSTST_BEGINPROC Common_SetupMemReadU16
     190        push    sAX
     191        mov     ax, [xSP + sCB + xCB]
     192        mov     [VBINSTST_NAME(g_u16Data) xWrtRip], ax
     193        pop     sAX
     194        ret sCB
     195VBINSTST_ENDPROC   Common_SetupMemReadU16
     196
     197;;
     198; Sets up g_u32Data.
     199; @param    uValue
     200VBINSTST_BEGINPROC Common_SetupMemReadU32
     201        push    sAX
     202        mov     eax, [xSP + sCB + xCB]
     203        mov     [VBINSTST_NAME(g_u32Data) xWrtRip], eax
     204        pop     sAX
     205        ret sCB
     206VBINSTST_ENDPROC   Common_SetupMemReadU32
     207
     208;;
     209; Sets up g_u64Data.
     210; @param    uValue
     211VBINSTST_BEGINPROC Common_SetupMemReadU64
     212        push    sAX
     213%ifdef RT_ARCH_AMD64
     214        mov     rax, [xSP + sCB + xCB]
     215        mov     [VBINSTST_NAME(g_u64Data) xWrtRip], rax
     216%else
     217        mov     eax, [xSP + sCB + xCB]
     218        mov     [VBINSTST_NAME(g_u64Data) xWrtRip], eax
     219        mov     eax, [xSP + sCB + xCB + 4]
     220        mov     [VBINSTST_NAME(g_u64Data) + 4 xWrtRip], eax
     221%endif
     222        pop     sAX
     223        ret sCB
     224VBINSTST_ENDPROC   Common_SetupMemReadU64
     225
     226
     227%endif
     228
  • trunk/src/VBox/VMM/testcase/Instructions/tstVBInsTstR3.cpp

    r46571 r46728  
    5050
    5151RT_C_DECLS_BEGIN
    52 extern void *g_pvLowMem4K;
     52extern void *g_pvLow16Mem4K;
     53extern void *g_pvLow32Mem4K;
    5354DECLASM(void)    TestInstrMain(void);
    5455
     
    99100    RTTestBanner(g_hTest);
    100101
    101     int rc = RTMemAllocEx(_4K, 0, RTMEMALLOCEX_FLAGS_16BIT_REACH, &g_pvLowMem4K);
     102    int rc = RTMemAllocEx(_4K, 0, RTMEMALLOCEX_FLAGS_16BIT_REACH, &g_pvLow16Mem4K);
    102103    if (RT_FAILURE(rc))
    103104    {
    104         RTTestPrintf(g_hTest, RTTESTLVL_ALWAYS, "Could not allocate low memory (%Rrc)\n", rc);
    105         g_pvLowMem4K = NULL;
     105        RTTestPrintf(g_hTest, RTTESTLVL_ALWAYS, "Could not allocate low 16-bit memory (%Rrc)\n", rc);
     106        g_pvLow16Mem4K = NULL;
     107    }
     108
     109    rc = RTMemAllocEx(_4K, 0, RTMEMALLOCEX_FLAGS_32BIT_REACH, &g_pvLow32Mem4K);
     110    if (RT_FAILURE(rc))
     111    {
     112        RTTestPrintf(g_hTest, RTTESTLVL_ALWAYS, "Could not allocate low 32-bit memory (%Rrc)\n", rc);
     113        g_pvLow32Mem4K = NULL;
    106114    }
    107115
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