vbox的更動 41786 路徑 trunk/src/VBox/Disassembler
- 時間撮記:
- 2012-6-16 下午07:58:22 (12 年 以前)
- 檔案:
-
- 修改 1 筆資料
圖例:
- 未更動
- 新增
- 刪除
-
trunk/src/VBox/Disassembler/DisasmCore.cpp
r41784 r41786 2642 2642 2643 2643 /** 2644 * Inlined worker that initializes the disassembler state. 2645 * 2646 * @returns The primary opcode map to use. 2647 * @param pCpu The disassembler state. 2648 * @param uInstrAddr The instruction address. 2649 * @param enmCpuMode The CPU mode. 2650 * @param fFilter The instruction filter settings. 2651 * @param pfnReadBytes The byte reader, can be NULL. 2652 * @param pvUser The the user data for the reader. 2653 */ 2654 DECL_FORCE_INLINE(PCDISOPCODE) 2655 disInitializeState(PDISCPUSTATE pCpu, RTUINTPTR uInstrAddr, DISCPUMODE enmCpuMode, uint32_t fFilter, 2656 PFNDISREADBYTES pfnReadBytes, void *pvUser) 2657 { 2658 2659 /* 2660 * Initialize the CPU state. 2661 * Note! The RT_BZERO make ASSUMPTIONS about the placement of pvUser2. 2662 */ 2663 RT_BZERO(pCpu, RT_OFFSETOF(DISCPUSTATE, pvUser2)); 2664 2665 #ifdef VBOX_STRICT /* poison */ 2666 pCpu->Param1.Base.idxGenReg = 0xc1; 2667 pCpu->Param2.Base.idxGenReg = 0xc2; 2668 pCpu->Param3.Base.idxGenReg = 0xc3; 2669 pCpu->Param1.Index.idxGenReg = 0xc4; 2670 pCpu->Param2.Index.idxGenReg = 0xc5; 2671 pCpu->Param3.Index.idxGenReg = 0xc6; 2672 pCpu->Param1.uDisp.u64 = UINT64_C(0xd1d1d1d1d1d1d1d1); 2673 pCpu->Param2.uDisp.u64 = UINT64_C(0xd2d2d2d2d2d2d2d2); 2674 pCpu->Param3.uDisp.u64 = UINT64_C(0xd3d3d3d3d3d3d3d3); 2675 pCpu->Param1.uValue = UINT64_C(0xb1b1b1b1b1b1b1b1); 2676 pCpu->Param2.uValue = UINT64_C(0xb2b2b2b2b2b2b2b2); 2677 pCpu->Param3.uValue = UINT64_C(0xb3b3b3b3b3b3b3b3); 2678 pCpu->Param1.uScale = 28; 2679 pCpu->Param2.uScale = 29; 2680 pCpu->Param3.uScale = 30; 2681 #endif 2682 2683 pCpu->fPrefix = DISPREFIX_NONE; 2684 pCpu->idxSegPrefix = DISSELREG_DS; 2685 pCpu->rc = VINF_SUCCESS; 2686 pCpu->pfnDisasmFnTable = g_apfnFullDisasm; 2687 2688 pCpu->uInstrAddr = uInstrAddr; 2689 pCpu->fFilter = fFilter; 2690 pCpu->pfnReadBytes = pfnReadBytes ? pfnReadBytes : disReadBytesDefault; 2691 pCpu->pvUser = pvUser; 2692 pCpu->uCpuMode = enmCpuMode; 2693 PCDISOPCODE paOneByteMap; 2694 if (enmCpuMode == DISCPUMODE_64BIT) 2695 { 2696 pCpu->uAddrMode = DISCPUMODE_64BIT; 2697 pCpu->uOpMode = DISCPUMODE_32BIT; 2698 paOneByteMap = g_aOneByteMapX64; 2699 } 2700 else 2701 { 2702 pCpu->uAddrMode = enmCpuMode; 2703 pCpu->uOpMode = enmCpuMode; 2704 paOneByteMap = g_aOneByteMapX86; 2705 } 2706 return paOneByteMap; 2707 } 2708 2709 2710 /** 2711 * Reads some bytes into the cache. 2712 * 2713 * While this will set DISCPUSTATE::rc on failure, the caller should disregard 2714 * this since that is what would happen if we didn't prefetch bytes prior to the 2715 * instruction parsing. 2716 * 2717 * @param pCpu The disassembler state. 2718 */ 2719 DECL_FORCE_INLINE(void) disPrefetchBytes(PDISCPUSTATE pCpu) 2720 { 2721 /* 2722 * Read some bytes into the cache. (If this fail we continue as nothing 2723 * has gone wrong since this is what would happen if we didn't precharge 2724 * the cache here.) 2725 */ 2726 int rc = pCpu->pfnReadBytes(pCpu, 0, 1, sizeof(pCpu->abInstr)); 2727 if (RT_SUCCESS(rc)) 2728 { 2729 Assert(pCpu->cbCachedInstr >= 1); 2730 Assert(pCpu->cbCachedInstr <= sizeof(pCpu->abInstr)); 2731 } 2732 else 2733 { 2734 Log(("Initial read failed with rc=%Rrc!!\n", rc)); 2735 pCpu->rc = VERR_DIS_MEM_READ; 2736 } 2737 } 2738 2739 2740 /** 2644 2741 * Disassembles on instruction, details in @a pCpu and length in @a pcbInstr. 2645 2742 * … … 2662 2759 PDISCPUSTATE pCpu, uint32_t *pcbInstr) 2663 2760 { 2664 PCDISOPCODE paOneByteMap; 2665 2666 /* 2667 * Initialize the CPU state. 2668 * Note! The RT_BZERO make ASSUMPTIONS about the placement of pvUser2. 2669 */ 2670 RT_BZERO(pCpu, RT_OFFSETOF(DISCPUSTATE, pvUser2)); 2671 2672 #ifdef VBOX_STRICT /* poison */ 2673 pCpu->Param1.Base.idxGenReg = 0xc1; 2674 pCpu->Param2.Base.idxGenReg = 0xc2; 2675 pCpu->Param3.Base.idxGenReg = 0xc3; 2676 pCpu->Param1.Index.idxGenReg = 0xc4; 2677 pCpu->Param2.Index.idxGenReg = 0xc5; 2678 pCpu->Param3.Index.idxGenReg = 0xc6; 2679 pCpu->Param1.uDisp.u64 = UINT64_C(0xd1d1d1d1d1d1d1d1); 2680 pCpu->Param2.uDisp.u64 = UINT64_C(0xd2d2d2d2d2d2d2d2); 2681 pCpu->Param3.uDisp.u64 = UINT64_C(0xd3d3d3d3d3d3d3d3); 2682 pCpu->Param1.uValue = UINT64_C(0xb1b1b1b1b1b1b1b1); 2683 pCpu->Param2.uValue = UINT64_C(0xb2b2b2b2b2b2b2b2); 2684 pCpu->Param3.uValue = UINT64_C(0xb3b3b3b3b3b3b3b3); 2685 pCpu->Param1.uScale = 28; 2686 pCpu->Param2.uScale = 29; 2687 pCpu->Param3.uScale = 30; 2688 #endif 2689 2690 pCpu->uCpuMode = enmCpuMode; 2691 if (enmCpuMode == DISCPUMODE_64BIT) 2692 { 2693 paOneByteMap = g_aOneByteMapX64; 2694 pCpu->uAddrMode = DISCPUMODE_64BIT; 2695 pCpu->uOpMode = DISCPUMODE_32BIT; 2696 } 2697 else 2698 { 2699 paOneByteMap = g_aOneByteMapX86; 2700 pCpu->uAddrMode = enmCpuMode; 2701 pCpu->uOpMode = enmCpuMode; 2702 } 2703 pCpu->fPrefix = DISPREFIX_NONE; 2704 pCpu->idxSegPrefix = DISSELREG_DS; 2705 pCpu->uInstrAddr = uInstrAddr; 2706 pCpu->pfnDisasmFnTable = g_apfnFullDisasm; 2707 pCpu->fFilter = fFilter; 2708 pCpu->rc = VINF_SUCCESS; 2709 pCpu->pfnReadBytes = pfnReadBytes ? pfnReadBytes : disReadBytesDefault; 2710 pCpu->pvUser = pvUser; 2711 2712 /* 2713 * Read some bytes into the cache. (If this fail we continue as nothing 2714 * has gone wrong since this is what would happen if we didn't precharge 2715 * the cache here.) 2716 */ 2717 int rc = pCpu->pfnReadBytes(pCpu, 0, 1, sizeof(pCpu->abInstr)); 2718 if (RT_SUCCESS(rc)) 2719 { 2720 Assert(pCpu->cbCachedInstr >= 1); 2721 Assert(pCpu->cbCachedInstr <= sizeof(pCpu->abInstr)); 2722 } 2723 else 2724 { 2725 Log(("Initial read failed with rc=%Rrc!!\n", rc)); 2726 pCpu->rc = VERR_DIS_MEM_READ; 2727 } 2728 2761 2762 PCDISOPCODE paOneByteMap = disInitializeState(pCpu, uInstrAddr, enmCpuMode, fFilter, pfnReadBytes, pvUser); 2763 disPrefetchBytes(pCpu); 2729 2764 return disInstrWorker(pCpu, paOneByteMap, pcbInstr); 2730 2765 } 2766 2767 2768 /** 2769 * Disassembles on instruction partially or fully from prefetched bytes, details 2770 * in @a pCpu and length in @a pcbInstr. 2771 * 2772 * @returns VBox status code. 2773 * @param uInstrAddr Address of the instruction to decode. What this means 2774 * is left to the pfnReadBytes function. 2775 * @param enmCpuMode The CPU mode. DISCPUMODE_32BIT, DISCPUMODE_16BIT, or DISCPUMODE_64BIT. 2776 * @param pvPrefetched Pointer to the prefetched bytes. 2777 * @param cbPrefetched The number of valid bytes pointed to by @a 2778 * pbPrefetched. 2779 * @param pfnReadBytes Callback for reading instruction bytes. 2780 * @param fFilter Instruction type filter. 2781 * @param pvUser User argument for the instruction reader. (Ends up in pvUser.) 2782 * @param pCpu Pointer to CPU structure. With the exception of 2783 * DISCPUSTATE::pvUser2, the structure will be 2784 * completely initialized by this API, i.e. no input is 2785 * taken from it. 2786 * @param pcbInstr Where to store the size of the instruction. (This 2787 * is also stored in PDISCPUSTATE::cbInstr.) Optional. 2788 */ 2789 DISDECL(int) DISInstWithPrefetchedBytes(RTUINTPTR uInstrAddr, DISCPUMODE enmCpuMode, uint32_t fFilter, 2790 void const *pvPrefetched, size_t cbPretched, 2791 PFNDISREADBYTES pfnReadBytes, void *pvUser, 2792 PDISCPUSTATE pCpu, uint32_t *pcbInstr) 2793 { 2794 PCDISOPCODE paOneByteMap = disInitializeState(pCpu, uInstrAddr, enmCpuMode, fFilter, pfnReadBytes, pvUser); 2795 2796 if (!cbPretched) 2797 disPrefetchBytes(pCpu); 2798 else 2799 { 2800 if (cbPretched >= sizeof(pCpu->abInstr)) 2801 { 2802 memcpy(pCpu->abInstr, pvPrefetched, sizeof(pCpu->abInstr)); 2803 pCpu->cbCachedInstr = (uint8_t)sizeof(pCpu->abInstr); 2804 } 2805 else 2806 { 2807 memcpy(pCpu->abInstr, pvPrefetched, cbPretched); 2808 pCpu->cbCachedInstr = (uint8_t)cbPretched; 2809 } 2810 } 2811 2812 return disInstrWorker(pCpu, paOneByteMap, pcbInstr); 2813 } 2814 2731 2815 2732 2816
注意:
瀏覽 TracChangeset
來幫助您使用更動檢視器