Changeset 53563 in vbox for trunk/src/VBox
- Timestamp:
- Dec 18, 2014 2:31:37 AM (10 years ago)
- Location:
- trunk/src/VBox/ValidationKit/utils/cpu
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/ValidationKit/utils/cpu/cidet-app.cpp
r53548 r53563 103 103 /** Data buffers (runs parallel to g_aDataBufCfgs). */ 104 104 CIDETAPPBUF aDataBuffers[CIDETAPP_DATA_BUF_COUNT]; 105 106 /** The lowest stack address. */ 107 uint8_t *pbStackLow; 108 /** The end of the stack allocation (highest address). */ 109 uint8_t *pbStackEnd; 110 /** Stack size (= pbStackEnd - pbStackLow). */ 111 uint32_t cbStack; 105 112 } CIDETAPP; 106 113 /** Pointer to a CIDET driver app instance. */ … … 347 354 } 348 355 356 357 /** 358 * Vectored exception handler. 359 * 360 * @returns Long jumps or terminates the process. 361 * @param pXcptPtrs The exception record. 362 */ 363 static LONG CALLBACK CidetAppVectoredXcptHandler(EXCEPTION_POINTERS *pXcptPtrs) 364 { 365 RTStrmPrintf(g_pStdErr, "CidetAppVectoredXcptHandler!\n"); 366 CidetAppXcptFilter(pXcptPtrs); 367 368 /* won't get here. */ 369 return EXCEPTION_CONTINUE_SEARCH; 370 } 371 372 373 /** 374 * Unhandled exception filter. 375 * 376 * @returns Long jumps or terminates the process. 377 * @param pXcptPtrs The exception record. 378 */ 379 static LONG CALLBACK CidetAppUnhandledXcptFilter(EXCEPTION_POINTERS *pXcptPtrs) 380 { 381 RTStrmPrintf(g_pStdErr, "CidetAppUnhandledXcptFilter!\n"); 382 CidetAppXcptFilter(pXcptPtrs); 383 384 /* won't get here. */ 385 return EXCEPTION_CONTINUE_SEARCH; 386 } 387 388 349 389 #elif defined(USE_SIGNALS) 350 390 /** … … 395 435 * 396 436 */ 397 398 static void CidetAppDeleteBuffer(PCIDETAPPBUF pBuf)399 {400 RTMemPageFree(pBuf->pbNormal - PAGE_SIZE, PAGE_SIZE + pBuf->cb + PAGE_SIZE);401 if (pBuf->pbLow != pBuf->pbNormal && pBuf->pbLow)402 RTMemFreeEx(pBuf->pbLow, pBuf->cb);403 }404 405 437 406 438 static int cidetAppAllocateAndConfigureOneBuffer(PCIDETAPP pThis, PCIDETAPPBUF pBuf, uint16_t idxBuf, bool fIsCode, … … 500 532 501 533 534 static void CidetAppDeleteBuffer(PCIDETAPPBUF pBuf) 535 { 536 RTMemProtect(pBuf->pbNormal - PAGE_SIZE, PAGE_SIZE + pBuf->cb + PAGE_SIZE, RTMEM_PROT_READ | RTMEM_PROT_WRITE); 537 RTMemPageFree(pBuf->pbNormal - PAGE_SIZE, PAGE_SIZE + pBuf->cb + PAGE_SIZE); 538 if (pBuf->pbLow != pBuf->pbNormal && pBuf->pbLow) 539 { 540 RTMemProtect(pBuf->pbLow, pBuf->cb, RTMEM_PROT_READ | RTMEM_PROT_WRITE); 541 RTMemFreeEx(pBuf->pbLow, pBuf->cb); 542 } 543 } 502 544 503 545 … … 532 574 } 533 575 pAppBuf->fArmed = false; 534 return false;576 return true; 535 577 } 536 578 … … 544 586 PCIDETAPPBUF pAppBuf = &pThisApp->aDataBuffers[pBuf->idxCfg]; 545 587 Assert(CIDETBUF_IS_DATA(pBuf->pCfg->fFlags)); 546 Assert(!pAppBuf->fArmed);547 588 548 589 /* … … 680 721 */ 681 722 uint16_t cbPrologue = 0; 682 uint16_t cbEpilogue = ARCH_BITS == 64 ? 0x 3b : 0x36;723 uint16_t cbEpilogue = ARCH_BITS == 64 ? 0x56 : 0x4e; 683 724 if (pThis->InCtx.fTrickyStack) 684 { 685 /** @todo tricky stack. */ 686 AssertReleaseFailedReturn(false); 687 } 688 725 cbEpilogue = 16; 689 726 690 727 /* … … 743 780 * Emit epilogue code. 744 781 */ 745 /* Restore working stack if necessary. */ 746 if (pThis->InCtx.fTrickyStack) 747 { 748 /** @todo emit code for establishing a working stack. */ 749 AssertReleaseFailedReturn(false); 750 } 751 else 782 if (!pThis->InCtx.fTrickyStack) 752 783 { 753 784 /* 754 785 * The stack is reasonably good, do minimal work. 786 * 787 * Note! Ideally, we would just fill in 16 int3s here and check that 788 * we hit the first right one. However, if we wish to run this 789 * code with IEM, we better skip unnecessary trips to ring-0. 755 790 */ 791 792 /* jmp $+6 */ 793 *pbDst++ = 0xeb; 794 *pbDst++ = 0x06; /* This is a push es, so if the decoder is one off, we'll hit the int 3 below. */ 795 796 /* Six int3s for trapping incorrectly decoded instructions. */ 797 *pbDst++ = 0xcc; 798 *pbDst++ = 0xcc; 799 *pbDst++ = 0xcc; 800 *pbDst++ = 0xcc; 801 *pbDst++ = 0xcc; 802 *pbDst++ = 0xcc; 803 804 /* push rip / call $+0 */ 805 *pbDst++ = 0xe8; 806 *pbDst++ = 0x00; 807 *pbDst++ = 0x00; 808 *pbDst++ = 0x00; 809 *pbDst++ = 0x00; 756 810 757 811 /* push xCX */ 758 812 *pbDst++ = 0x51; 813 814 /* mov xCX, [xSP + xCB] */ 815 *pbDst++ = 0x48; 816 *pbDst++ = 0x8b; 817 *pbDst++ = 0x4c; 818 *pbDst++ = 0x24; 819 *pbDst++ = 0x08; 820 821 /* lea xCX, [xCX - 14] */ 822 *pbDst++ = 0x48; 823 *pbDst++ = 0x8d; 824 *pbDst++ = 0x49; 825 *pbDst++ = 0xf2; 826 827 /* mov xCX, [xSP + xCB] */ 828 *pbDst++ = 0x48; 829 *pbDst++ = 0x89; 830 *pbDst++ = 0x4c; 831 *pbDst++ = 0x24; 832 *pbDst++ = 0x08; 759 833 760 834 /* mov xCX, &pThis->ActualCtx */ … … 778 852 *pbDst++ = 0x48; 779 853 #endif 780 *pbDst++ = 0x8 5;854 *pbDst++ = 0x89; 781 855 *pbDst++ = 0x51; 782 856 *pbDst++ = RT_OFFSETOF(CIDETCPUCTX, aGRegs[X86_GREG_xDX]); … … 819 893 *(uintptr_t *)pbDst = (uintptr_t)CidetAppSaveAndRestoreCtx; 820 894 pbDst += sizeof(uintptr_t); 821 } 822 823 824 *pbDst++ = 0xcc; /* int3 */ 895 896 /* int3 */ 897 *pbDst++ = 0xcc; 898 } 899 else 900 { 901 /* 902 * Tricky stack, so just make it raise #UD after a successful run. 903 */ 904 *pbDst++ = 0xf0; /* lock prefix */ 905 //*pbDst++ = 0xcc; /* lock prefix */ 906 memset(pbDst, 0xcc, 15); /* int3 */ 907 pbDst += 15; 908 } 909 825 910 AssertMsg(pbDst == &pAppBuf->pbNormal[pBuf->offActive + pBuf->cb + pBuf->cbEpilogue], 826 911 ("cbEpilogue=%#x, actual %#x\n", pBuf->cbEpilogue, pbDst - &pAppBuf->pbNormal[pBuf->offActive + pBuf->cb])); … … 834 919 835 920 /** 836 * @interface_method_impl{CIDETCORE::pfnSetupBuf} 837 */ 838 static DECLCALLBACK(void) CidetAppCbExecute(PCIDETCORE pThis) 839 { 921 * @interface_method_impl{CIDETCORE::pfnExecute} 922 */ 923 static DECLCALLBACK(bool) CidetAppCbExecute(PCIDETCORE pThis) 924 { 925 #if defined(RT_OS_WINDOWS) 926 /* Skip tricky stack because windows cannot dispatch exception if RSP/ESP is bad. */ 927 if (pThis->InCtx.fTrickyStack) 928 return false; 929 #endif 930 840 931 g_pExecutingThis = (PCIDETAPP)pThis; 841 932 #ifdef RT_OS_WINDOWS … … 852 943 #endif 853 944 g_pExecutingThis = NULL; 945 946 return true; 854 947 } 855 948 … … 879 972 static int cidetAppAllocateAndConfigureBuffers(PCIDETAPP pThis) 880 973 { 974 /* 975 * Code buffers. 976 */ 881 977 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aCodeBuffers); i++) 882 978 { … … 887 983 } 888 984 985 /* 986 * Data buffers. 987 */ 889 988 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aDataBuffers); i++) 890 989 { … … 894 993 return rc; 895 994 } 995 996 /* 997 * Stack. 998 */ 999 pThis->cbStack = _32K; 1000 pThis->pbStackLow = (uint8_t *)RTMemPageAlloc(pThis->cbStack); 1001 if (!pThis->pbStackLow) 1002 { 1003 RTTestIFailed("Failed to allocate %u bytes for stack\n", pThis->cbStack); 1004 return false; 1005 } 1006 pThis->pbStackEnd = pThis->pbStackLow + pThis->cbStack; 1007 896 1008 return true; 897 1009 } … … 943 1055 pThis->Core.InTemplateCtx.aSRegs[X86_SREG_GS] = ASMGetGS(); 944 1056 pThis->Core.InTemplateCtx.aSRegs[X86_SREG_SS] = ASMGetSS(); 1057 pThis->Core.InTemplateCtx.aGRegs[X86_GREG_xSP] = (uintptr_t)pThis->pbStackEnd - 64; 945 1058 946 1059 *ppThis = pThis; … … 973 1086 for (uint32_t i = 0; i < RT_ELEMENTS(pThis->aDataBuffers); i++) 974 1087 CidetAppDeleteBuffer(&pThis->aDataBuffers[i]); 1088 RTMemPageFree(pThis->pbStackLow, pThis->cbStack); 1089 975 1090 RTMemFree(pThis); 976 1091 } … … 1030 1145 #ifdef USE_SIGNALS 1031 1146 /* 1032 * Set up signal handlers. 1033 */ 1147 * Set up signal handlers with alternate stack. 1148 */ 1149 /* Alternative stack so we can play with esp/rsp. */ 1150 struct sigaltstack AltStack; 1151 RT_ZERO(AltStack); 1152 AltStack.ss_flags = SS_ONSTACK; 1153 # ifdef SIGSTKSZ 1154 AltStack.ss_size = RT_MAX(SIGSTKSZ, _128K); 1155 # else 1156 AltStack.ss_size = _128K; 1157 # endif 1158 AltStack.ss_sp = RTMemPageAlloc(AltStack.ss_size); 1159 RTTESTI_CHECK_RET(AltStack.ss_sp != NULL, RTEXITCODE_FAILURE); 1160 RTTESTI_CHECK_RC_RET(sigaltstack(&AltStack, NULL), 0, RTEXITCODE_FAILURE); 1161 1162 /* Default signal action config. */ 1034 1163 struct sigaction Act; 1035 1164 RT_ZERO(Act); 1036 Act.sa_sigaction = CidetAppSigHandler;1037 Act.sa_flags = SA_SIGINFO;1165 Act.sa_sigaction = CidetAppSigHandler; 1166 Act.sa_flags = SA_SIGINFO | SA_ONSTACK; 1038 1167 sigfillset(&Act.sa_mask); 1039 1168 1169 /* Hook the signals we might need. */ 1040 1170 sigaction(SIGILL, &Act, NULL); 1041 1171 sigaction(SIGTRAP, &Act, NULL); … … 1046 1176 sigaction(SIGBUS, &Act, NULL); 1047 1177 sigaction(SIGSEGV, &Act, NULL); 1178 1179 #elif defined(RT_OS_WINDOWS) 1180 /* 1181 * Register vectored exception handler and override the default unhandled 1182 * exception filter, just to be on the safe side... 1183 */ 1184 RTTESTI_CHECK(AddVectoredExceptionHandler(1 /* first */, CidetAppVectoredXcptHandler) != NULL); 1185 SetUnhandledExceptionFilter(CidetAppUnhandledXcptFilter); 1048 1186 #endif 1049 1187 -
trunk/src/VBox/ValidationKit/utils/cpu/cidet-appA.asm
r53548 r53563 57 57 ; 58 58 mov [xCX + CIDETCPUCTX.aGRegs + X86_GREG_xAX * 8], xAX ; need scratch register. 59 mov [xCX + CIDETCPUCTX.aGRegs + X86_GREG_xSP * 8], xSP 59 lea xAX, [xSP + xCB] 60 mov [xCX + CIDETCPUCTX.aGRegs + X86_GREG_xSP * 8], xAX 60 61 mov word [xCX + CIDETCPUCTX.aSRegs + X86_SREG_SS * 2], ss 61 62 mov word [xCX + CIDETCPUCTX.aSRegs + X86_SREG_CS * 2], cs … … 145 146 146 147 ; 147 ; Restore the other state .148 ; Restore the other state (pointer in xDX). 148 149 ; 149 150 NAME(CidetAppSaveAndRestoreCtx_Restore): … … 240 241 mov [xCX + CIDETCPUCTX.aGRegs + X86_GREG_xDX * 8], xDX 241 242 mov [xCX + CIDETCPUCTX.aGRegs + X86_GREG_xCX * 8], xCX 242 mov [xDX + CIDETCPUCTX.aGRegs + X86_GREG_xSP * 8], xSP243 243 jmp NAME(CidetAppSaveAndRestoreCtx) 244 244 ENDPROC CidetAppExecute … … 254 254 %elifdef ASM_CALL64_GCC 255 255 mov rdx, rdi 256 %elifndef ASM_CALL64_MSC 256 %elifdef ASM_CALL64_MSC 257 mov rdx, rcx 258 %else 257 259 %error "unsupport arch." 258 260 %endif -
trunk/src/VBox/ValidationKit/utils/cpu/cidet-core.cpp
r53548 r53563 61 61 /** @def CIDET_DPRINTF 62 62 * Debug printf. */ 63 #if def DEBUG_bird64 # define CIDET_DPRINTF(a) RTPrintf a63 #if 0 //def DEBUG_bird 64 # define CIDET_DPRINTF(a) do { RTPrintf a; } while (0) 65 65 #else 66 66 # define CIDET_DPRINTF(a) do { } while (0) 67 #endif 68 69 /** @def CIDET_DEBUG_DISAS 70 * Enables instruction disassembly. */ 71 #if defined(DOXYGEN_RUNNING) 72 # define CIDET_DEBUG_DISAS 1 67 73 #endif 68 74 … … 107 113 }; 108 114 115 /** Converts operand sizes in bytes to 64-bit signed max values. */ 116 static const int64_t g_ai64ByteSizeToMax[] = 117 { 118 INT64_C(0x0000000000000000), 119 INT64_C(0x000000000000007f), 120 INT64_C(0x0000000000007fff), 121 INT64_C(0x00000000007fffff), 122 INT64_C(0x000000007fffffff), 123 INT64_C(0x0000007fffffffff), 124 INT64_C(0x00007fffffffffff), 125 INT64_C(0x007fffffffffffff), 126 INT64_C(0x7fffffffffffffff), 127 }; 128 109 129 110 130 bool CidetInstrHasMrmMemOperand(PCCIDETINSTR pInstr) … … 240 260 | ((uint32_t)i << 12) 241 261 | ((uint32_t)i << 8); 242 243 262 i = RT_ELEMENTS(pThis->InTemplateCtx.aSRegs); 244 263 while (i-- > 0) … … 282 301 case CIDETMODE_PAE_32: 283 302 //case CIDETMODE_PAE_V86: 284 //case CIDETMODE_LM_ 16:303 //case CIDETMODE_LM_S16: 285 304 //case CIDETMODE_LM_32: 286 305 case CIDETMODE_LM_64: … … 488 507 pThis->aOperands[pThis->idxMrmRmOp].fIsMem = false; 489 508 pThis->aOperands[pThis->idxMrmRmOp].fIsRipRelative = false; 509 pThis->aOperands[pThis->idxMrmRmOp].fIsHighByteRegister = false; 510 pThis->aOperands[pThis->idxMrmRmOp].cbMemDisp = 0; 490 511 pThis->aOperands[pThis->idxMrmRmOp].iMemBaseReg = UINT8_MAX; 491 512 pThis->aOperands[pThis->idxMrmRmOp].iMemIndexReg = UINT8_MAX; 492 513 pThis->aOperands[pThis->idxMrmRmOp].uMemScale = 1; 514 pThis->aOperands[pThis->idxMrmRmOp].iEffSeg = UINT8_MAX; 493 515 pThis->bModRm &= ~(X86_MODRM_RM_MASK | X86_MODRM_MOD_MASK); 494 516 pThis->bModRm |= 3 << X86_MODRM_MOD_SHIFT; … … 501 523 pThis->fHasRegCollisionMemBase = false; 502 524 pThis->fHasRegCollisionMemIndex = false; 525 pThis->fHasStackRegInMrmRmBase = false; 503 526 } 504 527 else … … 508 531 pThis->aOperands[pThis->idxMrmRmOp].fIsMem = true; 509 532 pThis->aOperands[pThis->idxMrmRmOp].fIsRipRelative = false; 533 pThis->aOperands[pThis->idxMrmRmOp].fIsHighByteRegister = false; 534 pThis->aOperands[pThis->idxMrmRmOp].cbMemDisp = 0; 510 535 pThis->aOperands[pThis->idxMrmRmOp].iMemBaseReg = X86_GREG_xBX; 511 536 pThis->aOperands[pThis->idxMrmRmOp].iMemIndexReg = X86_GREG_xSI; 512 537 pThis->aOperands[pThis->idxMrmRmOp].uMemScale = 1; 538 pThis->aOperands[pThis->idxMrmRmOp].iEffSeg = UINT8_MAX; 513 539 pThis->bModRm &= ~(X86_MODRM_RM_MASK | X86_MODRM_MOD_MASK); 514 540 pThis->fRexB = false; … … 519 545 pThis->fHasRegCollisionMemIndex = iReg == X86_GREG_xSI && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 520 546 pThis->fHasRegCollisionMem = pThis->fHasRegCollisionMemBase || pThis->fHasRegCollisionMemIndex; 547 pThis->fHasStackRegInMrmRmBase = false; 521 548 } 522 549 } … … 554 581 pThis->fHasRegCollisionDirect = iRm == iReg 555 582 && CIDET_OF_K_IS_SAME(pThis->fMrmRmOp, pThis->fMrmRegOp); 583 pThis->fHasStackRegInMrmRmBase = iRm == X86_GREG_xSP && CIDET_OF_K_IS_GPR(pThis->fMrmRmOp); 556 584 return true; 557 585 } … … 648 676 pThis->fHasMemoryOperand = true; 649 677 pThis->fHasRegCollisionDirect = false; 678 pThis->fHasStackRegInMrmRmBase = false; 650 679 if (CIDET_OF_K_IS_GPR(pThis->fMrmRmOp)) 651 680 { … … 672 701 pThis->aOperands[pThis->idxMrmRmOp].fIsMem = false; 673 702 pThis->aOperands[pThis->idxMrmRmOp].fIsRipRelative = false; 703 pThis->aOperands[pThis->idxMrmRmOp].fIsHighByteRegister = false; 704 pThis->aOperands[pThis->idxMrmRmOp].cbMemDisp = 0; 674 705 pThis->aOperands[pThis->idxMrmRmOp].iMemBaseReg = UINT8_MAX; 675 706 pThis->aOperands[pThis->idxMrmRmOp].iMemIndexReg = UINT8_MAX; 676 707 pThis->aOperands[pThis->idxMrmRmOp].uMemScale = 1; 708 pThis->aOperands[pThis->idxMrmRmOp].iEffSeg = UINT8_MAX; 677 709 pThis->bModRm &= ~(X86_MODRM_RM_MASK | X86_MODRM_MOD_MASK); 678 710 pThis->bModRm |= 3 << X86_MODRM_MOD_SHIFT; … … 685 717 pThis->fHasRegCollisionMemBase = false; 686 718 pThis->fHasRegCollisionMemIndex = false; 719 pThis->fHasStackRegInMrmRmBase = false; 687 720 } 688 721 else … … 692 725 pThis->aOperands[pThis->idxMrmRmOp].fIsMem = true; 693 726 pThis->aOperands[pThis->idxMrmRmOp].fIsRipRelative = false; 727 pThis->aOperands[pThis->idxMrmRmOp].fIsHighByteRegister = false; 728 pThis->aOperands[pThis->idxMrmRmOp].cbMemDisp = 0; 694 729 pThis->aOperands[pThis->idxMrmRmOp].iMemBaseReg = 0; 695 730 pThis->aOperands[pThis->idxMrmRmOp].iMemIndexReg = UINT8_MAX; 696 731 pThis->aOperands[pThis->idxMrmRmOp].uMemScale = 1; 732 pThis->aOperands[pThis->idxMrmRmOp].iEffSeg = UINT8_MAX; 697 733 pThis->bModRm &= ~(X86_MODRM_RM_MASK | X86_MODRM_MOD_MASK); 698 734 pThis->fRexB = false; … … 703 739 pThis->fHasRegCollisionMemBase = iReg == 0 && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 704 740 pThis->fHasRegCollisionMem = pThis->fHasRegCollisionMemBase; 741 pThis->fHasStackRegInMrmRmBase = false; 705 742 } 706 743 } … … 761 798 pThis->fHasRegCollisionDirect = CIDET_OF_K_IS_GPR(pThis->fMrmRegOp) 762 799 && iRm == iReg - pThis->fHasHighByteRegInMrmReg * 4; 800 pThis->fHasStackRegInMrmRmBase = iRm == X86_GREG_xSP && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 763 801 } 764 802 else … … 779 817 pThis->fHasRegCollisionDirect = CIDET_OF_K_IS_GPR(pThis->fMrmRegOp) 780 818 && iRm - 4 == iReg - pThis->fHasHighByteRegInMrmReg * 4; 819 pThis->fHasStackRegInMrmRmBase = false; 781 820 782 821 } … … 787 826 pThis->fHasRegCollisionDirect = CIDET_OF_K_IS_GPR(pThis->fMrmRegOp) 788 827 && iRm == iReg - pThis->fHasHighByteRegInMrmReg * 4; 828 pThis->fHasStackRegInMrmRmBase = iRm == X86_GREG_xSP && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 789 829 } 790 830 } … … 803 843 pThis->fHasRegCollisionDirect = iRm == iReg - pThis->fHasHighByteRegInMrmReg * 4 804 844 && CIDET_OF_K_IS_SAME(pThis->fMrmRmOp, pThis->fMrmRegOp); 845 pThis->fHasStackRegInMrmRmBase = iRm == X86_GREG_xSP && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 805 846 } 806 847 return true; … … 826 867 Assert(pThis->idxMrmRmOp < RT_ELEMENTS(pThis->aOperands) && pThis->aOperands[pThis->idxMrmRmOp].fIsMem); 827 868 Assert(pThis->fHasMemoryOperand); 869 Assert(!pThis->fHasStackRegInMrmRmBase); 828 870 if (iRm < (CIDETMODE_IS_64BIT(pThis->bMode) && !pThis->fNoRexPrefix ? 15 : 7)) 829 871 { … … 894 936 pThis->fHasRegCollisionMemBase = iReg == X86_GREG_xAX && CIDET_OF_K_IS_GPR(pThis->fMrmRmOp); 895 937 pThis->fHasRegCollisionMem = pThis->fHasRegCollisionMemBase; 938 pThis->fHasStackRegInMrmRmBase = false; 896 939 return true; 897 940 } … … 949 992 && CIDET_OF_K_IS_GPR(pThis->fMrmRegOp); 950 993 pThis->fHasRegCollisionMem = pThis->fHasRegCollisionMemBase || pThis->fHasRegCollisionMemIndex; 994 pThis->fHasStackRegInMrmRmBase = iBase == X86_GREG_xSP; 951 995 952 996 return iBase != 0; … … 1210 1254 pThis->fHasRegCollisionMemBase = false; 1211 1255 pThis->fHasRegCollisionMemIndex = false; 1212 pThis->fHas RegCollisionDirect= false;1256 pThis->fHasStackRegInMrmRmBase = false; 1213 1257 1214 1258 /* … … 1536 1580 else if (iMemBaseReg != UINT8_MAX) 1537 1581 { 1538 /* [base] or [base + disp] or [base + index * scale] or [base + index * scale + disp] */1539 if (pThis->aOperands[idxOp].cbMemDisp > 0)1582 if ( iMemBaseReg != iMemIndexReg 1583 || pThis->fUsesVexIndexRegs) 1540 1584 { 1541 pThis->aOperands[idxOp].uImmDispValue = CidetCoreGetRandS64(pThis, pThis->aOperands[idxOp].cbMemDisp); 1542 offSeg -= pThis->aOperands[idxOp].uImmDispValue; 1585 /* [base] or [base + disp] or [base + index * scale] or [base + index * scale + disp] */ 1586 if (pThis->aOperands[idxOp].cbMemDisp > 0) 1587 { 1588 pThis->aOperands[idxOp].uImmDispValue = CidetCoreGetRandS64(pThis, pThis->aOperands[idxOp].cbMemDisp); 1589 offSeg -= (int64_t)pThis->aOperands[idxOp].uImmDispValue; 1590 } 1591 1592 if (iMemIndexReg != UINT8_MAX) 1593 { 1594 pThis->aOperands[idxOp].uMemIndexRegValue = CidetCoreGetRandU64(pThis, pThis->cbAddrMode); 1595 offSeg -= pThis->aOperands[idxOp].uMemIndexRegValue * pThis->aOperands[idxOp].uMemScale; 1596 } 1597 1598 pThis->aOperands[idxOp].uMemBaseRegValue = offSeg & g_au64ByteSizeToMask[pThis->cbAddrMode]; 1543 1599 } 1544 1545 if (iMemIndexReg != UINT8_MAX) 1600 else 1546 1601 { 1547 pThis->aOperands[idxOp].uMemIndexRegValue = CidetCoreGetRandU64(pThis, pThis->cbAddrMode); 1548 offSeg -= pThis->aOperands[idxOp].uMemIndexRegValue * pThis->aOperands[idxOp].uMemScale; 1602 /* base == index; [base + index * scale] or [base * (scale + 1)]. */ 1603 uint8_t const uEffScale = pThis->aOperands[idxOp].uMemScale + 1; 1604 if (pThis->aOperands[idxOp].cbMemDisp > 0) 1605 { 1606 pThis->aOperands[idxOp].uImmDispValue = CidetCoreGetRandS64(pThis, pThis->aOperands[idxOp].cbMemDisp); 1607 offSeg -= (int64_t)pThis->aOperands[idxOp].uImmDispValue; 1608 offSeg &= g_au64ByteSizeToMask[pThis->cbAddrMode]; 1609 uint8_t uRemainder = offSeg % uEffScale; 1610 if (uRemainder != 0) 1611 { 1612 Assert(pThis->aOperands[idxOp].cbMemDisp < 8); 1613 Assert( (int64_t)pThis->aOperands[idxOp].uImmDispValue 1614 <= g_ai64ByteSizeToMax[pThis->aOperands[idxOp].cbMemDisp]); 1615 pThis->aOperands[idxOp].uImmDispValue = (int64_t)pThis->aOperands[idxOp].uImmDispValue 1616 + uRemainder; 1617 offSeg -= uRemainder; 1618 if ( (int64_t)pThis->aOperands[idxOp].uImmDispValue 1619 > g_ai64ByteSizeToMax[pThis->aOperands[idxOp].cbMemDisp]) 1620 { 1621 pThis->aOperands[idxOp].uImmDispValue -= uEffScale; 1622 offSeg += uEffScale; 1623 } 1624 Assert(offSeg % uEffScale == 0); 1625 } 1626 } 1627 else 1628 { 1629 offSeg &= g_au64ByteSizeToMask[pThis->cbAddrMode]; 1630 if (offSeg % uEffScale != 0) 1631 return false; 1632 } 1633 offSeg /= uEffScale; 1634 pThis->aOperands[idxOp].uMemBaseRegValue = pThis->aOperands[idxOp].uMemIndexRegValue = offSeg; 1549 1635 } 1550 1551 pThis->aOperands[idxOp].uMemBaseRegValue = offSeg & g_au64ByteSizeToMask[pThis->cbAddrMode];1552 1636 } 1553 1637 else if (iMemIndexReg != UINT8_MAX) … … 1557 1641 { 1558 1642 pThis->aOperands[idxOp].uImmDispValue = CidetCoreGetRandS64(pThis, pThis->aOperands[idxOp].cbMemDisp); 1559 offSeg -= pThis->aOperands[idxOp].uImmDispValue;1643 offSeg -= (int64_t)pThis->aOperands[idxOp].uImmDispValue; 1560 1644 pThis->aOperands[idxOp].uImmDispValue += offSeg & (RT_BIT_64(pThis->aOperands[idxOp].uMemScale) - 1); 1561 1645 offSeg &= ~(RT_BIT_64(pThis->aOperands[idxOp].uMemScale) - 1); … … 1998 2082 { 1999 2083 //CIDET_DPRINTF(("%04u: %.*Rhxs\n", i, pThis->cbInstr, pThis->abInstr)); 2084 #ifdef CIDET_DEBUG_DISAS 2000 2085 DISCPUSTATE Dis; 2001 2086 char szInstr[80] = {0}; … … 2012 2097 CIDET_DPRINTF(("%04u: %s", iSubTest, szInstr)); 2013 2098 Assert(cbInstr == pThis->cbInstr); 2014 2099 #endif 2015 2100 if (pThis->pfnSetupCodeBuf(pThis, &pThis->CodeBuf, pThis->abInstr)) 2016 2101 { … … 2051 2136 */ 2052 2137 pThis->InCtx = pThis->InTemplateCtx; 2053 pThis->ExpectedCtx = pThis->InTemplateCtx; 2138 pThis->InCtx.fTrickyStack = pThis->fHasStackRegInMrmRmBase || pThis->fHasStackRegInMrmReg; 2139 pThis->ExpectedCtx = pThis->InCtx; 2054 2140 if ( CidetCoreReInitCodeBuf(pThis) 2055 2141 && CidetCoreSetupInOut(pThis) … … 2057 2143 ) 2058 2144 { 2059 pThis->pfnExecute(pThis); 2060 cExecuted++; 2145 if (pThis->pfnExecute(pThis)) 2146 { 2147 cExecuted++; 2148 2149 /* 2150 * Check the result against our expectations. 2151 */ 2152 /** @todo check result. */ 2153 2154 } 2155 else 2156 cSkipped++; 2061 2157 } 2062 2158 else -
trunk/src/VBox/ValidationKit/utils/cpu/cidet.h
r53548 r53563 843 843 * Executes the code indicated by InCtx, returning the result in ActualCtx. 844 844 * 845 * @returns true if execute, false if skipped. 845 846 * @param pThis Pointer to the core structure. 846 847 */ 847 DECLCALLBACKMEMBER( void, pfnExecute)(struct CIDETCORE *pThis);848 DECLCALLBACKMEMBER(bool, pfnExecute)(struct CIDETCORE *pThis); 848 849 849 850 /** … … 916 917 /** Indicator: Helper indicator for tracking SIB.BASE collision. */ 917 918 bool fHasRegCollisionMemBase : 1; 918 /** Indicator: Helper indicator for tracking SIB. BASEcollision. */919 /** Indicator: Helper indicator for tracking SIB.INDEX collision. */ 919 920 bool fHasRegCollisionMemIndex : 1; 920 921 /** Indicator: Set if a register is used directly in more than one operand. */ 921 922 bool fHasRegCollisionDirect : 1; 923 924 /** Indicator: Set if MODRM.REG is the stack register. */ 925 bool fHasStackRegInMrmReg : 1; 926 /** Indicator: Set if MODRM.RM or SIB.BASE is the stack register. */ 927 bool fHasStackRegInMrmRmBase: 1; 928 922 929 /** Indicator: High byte-register specified by MODRM.REG. */ 923 930 bool fHasHighByteRegInMrmReg : 1;
Note:
See TracChangeset
for help on using the changeset viewer.