--- np2/i286x/v30patch.cpp 2003/10/19 14:56:15 1.3 +++ np2/i286x/v30patch.cpp 2005/03/26 07:53:48 1.12 @@ -1,26 +1,34 @@ #include "compiler.h" -#include "i286.h" +#include "cpucore.h" #include "i286x.h" #include "i286xadr.h" #include "i286xs.h" #include "i286xrep.h" #include "i286xcts.h" -#include "memory.h" #include "pccore.h" #include "bios.h" #include "iocore.h" #include "i286x.mcr" #include "i286xea.mcr" -#include "dmap.h" +#include "dmax86.h" +#if defined(ENABLE_TRAP) +#include "steptrap.h" +#endif typedef struct { - DWORD opnum; - void (*v30opcode)(void); -} V30PATCH_T; + UINT opnum; + I286TBL v30opcode; +} V30PATCH; + +static I286TBL v30op[256]; +static I286TBL v30op_repne[256]; +static I286TBL v30op_repe[256]; +static I286TBL v30ope0xf6_xtable[8]; +static I286TBL v30ope0xf7_xtable[8]; -static const BYTE shiftbase16[256] = +static const UINT8 rotatebase16[256] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, 16, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, 16, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, @@ -38,7 +46,7 @@ static const BYTE shiftbase16[256] = 16, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, 16, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15}; -static const BYTE shiftbase09[256] = +static const UINT8 rotatebase09[256] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, @@ -56,7 +64,7 @@ static const BYTE shiftbase09[256] = 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1, 2, 3}; -static const BYTE shiftbase17[256] = +static const UINT8 rotatebase17[256] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, 16,17, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14, 15,16,17, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13, @@ -74,6 +82,24 @@ static const BYTE shiftbase17[256] = 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15,16,17, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15,16,17}; +static const UINT8 shiftbase[256] = + {0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15, + 16,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17}; + I286 v30_reserved(void) { @@ -94,7 +120,7 @@ I286 v30pop_ss(void) { // 17: pop shl eax, 4 // make segreg mov SS_BASE, eax mov SS_FIX, eax - cmp i286reg.prefix, 0 // 00/06/24 + cmp i286core.s.prefix, 0 // 00/06/24 je noprefix call removeprefix pop eax @@ -204,7 +230,7 @@ I286 v30mov_seg_ea(void) { // 8E: m segsetr:ret align 4 - setss: cmp i286reg.prefix, 0 // 00/05/13 + setss: cmp i286core.s.prefix, 0 // 00/05/13 je noprefix pop eax call eax // eax<-offset removeprefix @@ -252,7 +278,7 @@ I286 v30_popf(void) { // 9D: popf I286 rol_r8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] rol byte ptr [edx], cl FLAG_STORE_OC ret @@ -262,7 +288,7 @@ I286 rol_r8_v30(void) { I286 ror_r8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] ror byte ptr [edx], cl FLAG_STORE_OC ret @@ -272,7 +298,7 @@ I286 ror_r8_v30(void) { I286 rcl_r8_v30(void) { __asm { - mov cl, shiftbase09[ecx] + mov cl, rotatebase09[ecx] CFLAG_LOAD rcl byte ptr [edx], cl FLAG_STORE_OC @@ -283,7 +309,7 @@ I286 rcl_r8_v30(void) { I286 rcr_r8_v30(void) { __asm { - mov cl, shiftbase09[ecx] + mov cl, rotatebase09[ecx] CFLAG_LOAD rcr byte ptr [edx], cl FLAG_STORE_OC @@ -294,7 +320,7 @@ I286 rcr_r8_v30(void) { I286 shl_r8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shl byte ptr [edx], cl FLAG_STORE_OF ret @@ -304,7 +330,7 @@ I286 shl_r8_v30(void) { I286 shr_r8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shr byte ptr [edx], cl FLAG_STORE_OF ret @@ -314,7 +340,7 @@ I286 shr_r8_v30(void) { I286 sar_r8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] sar byte ptr [edx], cl FLAG_STORE0 ret @@ -328,7 +354,7 @@ static void (*sftreg8v30_table[])(void) I286 rol_ext8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] rol dl, cl FLAG_STORE_OC mov ecx, ebp @@ -339,7 +365,7 @@ I286 rol_ext8_v30(void) { I286 ror_ext8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] ror dl, cl FLAG_STORE_OC mov ecx, ebp @@ -350,7 +376,7 @@ I286 ror_ext8_v30(void) { I286 rcl_ext8_v30(void) { __asm { - mov cl, shiftbase09[ecx] + mov cl, rotatebase09[ecx] CFLAG_LOAD rcl dl, cl FLAG_STORE_OC @@ -362,7 +388,7 @@ I286 rcl_ext8_v30(void) { I286 rcr_ext8_v30(void) { __asm { - mov cl, shiftbase09[ecx] + mov cl, rotatebase09[ecx] CFLAG_LOAD rcr dl, cl FLAG_STORE_OC @@ -374,7 +400,7 @@ I286 rcr_ext8_v30(void) { I286 shl_ext8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shl dl, cl FLAG_STORE_OF mov ecx, ebp @@ -385,7 +411,7 @@ I286 shl_ext8_v30(void) { I286 shr_ext8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shr dl, cl FLAG_STORE_OF mov ecx, ebp @@ -396,7 +422,7 @@ I286 shr_ext8_v30(void) { I286 sar_ext8_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] sar dl, cl FLAG_STORE0 mov ecx, ebp @@ -460,7 +486,7 @@ I286 v30shift_ea8_data8(void) { // C I286 rol_r16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] rol word ptr [edx], cl FLAG_STORE_OC ret @@ -470,7 +496,7 @@ I286 rol_r16_v30(void) { I286 ror_r16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] ror word ptr [edx], cl FLAG_STORE_OC ret @@ -480,7 +506,7 @@ I286 ror_r16_v30(void) { I286 rcl_r16_v30(void) { __asm { - mov cl, shiftbase17[ecx] + mov cl, rotatebase17[ecx] CFLAG_LOAD rcl word ptr [edx], cl FLAG_STORE_OC @@ -491,7 +517,7 @@ I286 rcl_r16_v30(void) { I286 rcr_r16_v30(void) { __asm { - mov cl, shiftbase17[ecx] + mov cl, rotatebase17[ecx] CFLAG_LOAD rcr word ptr [edx], cl FLAG_STORE_OC @@ -502,7 +528,7 @@ I286 rcr_r16_v30(void) { I286 shl_r16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shl word ptr [edx], cl FLAG_STORE_OF ret @@ -512,7 +538,7 @@ I286 shl_r16_v30(void) { I286 shr_r16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shr word ptr [edx], cl FLAG_STORE_OF ret @@ -522,7 +548,7 @@ I286 shr_r16_v30(void) { I286 sar_r16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] sar word ptr [edx], cl FLAG_STORE0 ret @@ -536,7 +562,7 @@ static void (*sftreg16v30_table[])(void) I286 rol_ext16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] rol dx, cl FLAG_STORE_OC mov ecx, ebp @@ -547,7 +573,7 @@ I286 rol_ext16_v30(void) { I286 ror_ext16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, rotatebase16[ecx] ror dx, cl FLAG_STORE_OC mov ecx, ebp @@ -558,7 +584,7 @@ I286 ror_ext16_v30(void) { I286 rcl_ext16_v30(void) { __asm { - mov cl, shiftbase17[ecx] + mov cl, rotatebase17[ecx] CFLAG_LOAD rcl dx, cl FLAG_STORE_OC @@ -570,7 +596,7 @@ I286 rcl_ext16_v30(void) { I286 rcr_ext16_v30(void) { __asm { - mov cl, shiftbase17[ecx] + mov cl, rotatebase17[ecx] CFLAG_LOAD rcr dx, cl FLAG_STORE_OC @@ -582,7 +608,7 @@ I286 rcr_ext16_v30(void) { I286 shl_ext16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shl dx, cl FLAG_STORE_OF mov ecx, ebp @@ -593,7 +619,7 @@ I286 shl_ext16_v30(void) { I286 shr_ext16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] shr dx, cl FLAG_STORE_OF mov ecx, ebp @@ -604,7 +630,7 @@ I286 shr_ext16_v30(void) { I286 sar_ext16_v30(void) { __asm { - mov cl, shiftbase16[ecx] + mov cl, shiftbase[ecx] sar dx, cl FLAG_STORE0 mov ecx, ebp @@ -793,8 +819,164 @@ I286 v30_repe(void) { // F3: repe } } +I286 v30div_ea8(void) { // F6-6: div ea8 + + __asm { + PREPART_EA8(14) + movzx ebp, byte ptr I286_REG[eax] + GET_NEXTPRE2 + jmp divcheck + MEMORY_EA8(17) + movzx ebp, byte ptr I286_MEM[ecx] + jmp divcheck + EXTMEM_EA8 + movzx ebp, al + + align 4 + divcheck: test ebp, ebp + je divovf + mov ax, I286_AX + xor dx, dx + div bp + mov I286_AL, al + mov I286_AH, dl + mov dx, ax + FLAG_STORE_OF + test dh, dh + jne divovf + ret + + align 4 + divovf: INT_NUM(0) + } +} + +I286 v30idiv_ea8(void) { // F6-7 idiv ea8 + + __asm { + PREPART_EA8(17) + movsx ebp, byte ptr I286_REG[eax] + GET_NEXTPRE2 + jmp idivcheck + MEMORY_EA8(20) + movsx ebp, byte ptr I286_MEM[ecx] + jmp idivcheck + EXTMEM_EA8 + movsx ebp, al + + align 4 + idivcheck: test ebp, ebp + je idivovf + mov ax, I286_AX + cwd + idiv bp + mov I286_AL, al + mov I286_AH, dl + mov dx, ax + FLAG_STORE_OF + bt dx, 7 + adc dh, 0 + jne idivovf + ret + + align 4 + idivovf: INT_NUM(0) + } +} + +I286 v30_ope0xf6(void) { // F6: + + __asm { + movzx eax, bh + mov edi, eax + shr edi, 3-2 + and edi, 7*4 + jmp v30ope0xf6_xtable[edi] + } +} + +I286 v30div_ea16(void) { // F7-6: div ea16 + + __asm { + PREPART_EA16(22) + movzx ebp, word ptr I286_REG[eax*2] + GET_NEXTPRE2 + jmp divcheck + MEMORY_EA16(25) + movzx ebp, word ptr I286_MEM[ecx] + jmp divcheck + EXTMEM_EA16 + movzx ebp, ax + + align 4 + divcheck: test ebp, ebp + je divovf + movzx eax, I286_DX + shl eax, 16 + mov ax, I286_AX + xor edx, edx + div ebp + mov I286_AX, ax + mov I286_DX, dx + FLAG_STORE_OF + cmp eax, 10000h + jae divovf + ret + + align 4 + divovf: INT_NUM(0) + } +} + +I286 v30idiv_ea16(void) { // F7-7: idiv ea16 + + __asm { + PREPART_EA16(25) + movsx ebp, word ptr I286_REG[eax*2] + GET_NEXTPRE2 + jmp idivcheck + MEMORY_EA16(28) + movsx ebp, word ptr I286_MEM[ecx] + jmp idivcheck + EXTMEM_EA16 + cwde + mov ebp, eax -static V30PATCH_T v30patch_op[] = { + align 4 + idivcheck: test ebp, ebp + je idivovf + movzx eax, I286_DX + shl eax, 16 + mov ax, I286_AX + cdq + idiv ebp + mov I286_AX, ax + mov I286_DX, dx + mov edx, eax + FLAG_STORE_OF + shr edx, 16 + adc dx, 0 + jne idivovf + ret + + align 4 + idivovf: INT_NUM(0) + } +} + +I286 v30_ope0xf7(void) { // F7: + + __asm { + movzx eax, bh + mov edi, eax + shr edi, 3-2 + and edi, 7*4 + jmp v30ope0xf7_xtable[edi] + } +} + + +static const V30PATCH v30patch_op[] = { {0x17, v30pop_ss}, // 17: pop ss {0x26, v30segprefix_es}, // 26: es: {0x2e, v30segprefix_cs}, // 2E: cs: @@ -818,8 +1000,10 @@ static V30PATCH_T v30patch_op[] = { {0xd5, v30_aad}, // D5: AAD {0xd6, v30_xlat}, // D6: xlat (8086/V30) {0xf2, v30_repne}, // F2: repne - {0xf3, v30_repe} // F3: repe -}; + {0xf3, v30_repe}, // F3: repe + {0xf6, v30_ope0xf6}, // F6: + {0xf7, v30_ope0xf7}}; // F7: + // ----------------------------------------------------------------- repe @@ -872,7 +1056,7 @@ I286 v30repe_segprefix_ds(void) { } -static V30PATCH_T v30patch_repe[] = { +static const V30PATCH v30patch_repe[] = { {0x17, v30pop_ss}, // 17: pop ss {0x26, v30repe_segprefix_es}, // 26: repe es: {0x2e, v30repe_segprefix_cs}, // 2E: repe cs: @@ -896,8 +1080,10 @@ static V30PATCH_T v30patch_repe[] = { {0xd5, v30_aad}, // D5: AAD {0xd6, v30_xlat}, // D6: xlat (8086/V30) {0xf2, v30_repne}, // F2: repne - {0xf3, v30_repe} // F3: repe -}; + {0xf3, v30_repe}, // F3: repe + {0xf6, v30_ope0xf6}, // F6: + {0xf7, v30_ope0xf7}}; // F7: + // ----------------------------------------------------------------- repne @@ -949,7 +1135,7 @@ I286 v30repne_segprefix_ds(void) { } } -static V30PATCH_T v30patch_repne[] = { +static const V30PATCH v30patch_repne[] = { {0x17, v30pop_ss}, // 17: pop ss {0x26, v30repne_segprefix_es}, // 26: repne es: {0x2e, v30repne_segprefix_cs}, // 2E: repne cs: @@ -973,16 +1159,14 @@ static V30PATCH_T v30patch_repne[] = { {0xd5, v30_aad}, // D5: AAD {0xd6, v30_xlat}, // D6: xlat (8086/V30) {0xf2, v30_repne}, // F2: repne - {0xf3, v30_repe} // F3: repe -}; + {0xf3, v30_repe}, // F3: repe + {0xf6, v30_ope0xf6}, // F6: + {0xf7, v30_ope0xf7}}; // F7: -// --------------------------------------------------------------------------- -void (*v30op[256])(void); -void (*v30op_repne[256])(void); -void (*v30op_repe[256])(void); +// --------------------------------------------------------------------------- -static void v30patching(void (*dst[])(void), V30PATCH_T *patch, int length) { +static void v30patching(I286TBL *dst, const V30PATCH *patch, int length) { while(length--) { dst[patch->opnum] = patch->v30opcode; @@ -990,9 +1174,9 @@ static void v30patching(void (*dst[])(vo } } -#define V30PATCHING(a, b) v30patching(a, b, sizeof(b)/sizeof(V30PATCH_T)) +#define V30PATCHING(a, b) v30patching(a, b, sizeof(b)/sizeof(V30PATCH)) -void v30init(void) { +void v30xinit(void) { CopyMemory(v30op, i286op, sizeof(v30op)); V30PATCHING(v30op, v30patch_op); @@ -1000,13 +1184,19 @@ void v30init(void) { V30PATCHING(v30op_repne, v30patch_repne); CopyMemory(v30op_repe, i286op_repe, sizeof(v30op_repe)); V30PATCHING(v30op_repe, v30patch_repe); + CopyMemory(v30ope0xf6_xtable, ope0xf6_xtable, sizeof(v30ope0xf6_xtable)); + v30ope0xf6_xtable[6] = v30div_ea8; + v30ope0xf6_xtable[7] = v30idiv_ea8; + CopyMemory(v30ope0xf7_xtable, ope0xf7_xtable, sizeof(v30ope0xf7_xtable)); + v30ope0xf7_xtable[6] = v30div_ea16; + v30ope0xf7_xtable[7] = v30idiv_ea16; } -LABEL void v30(void) { +LABEL void v30x(void) { __asm { pushad - mov ebx, dword ptr (i286reg.prefetchque) + mov ebx, dword ptr (i286core.s.prefetchque) movzx esi, I286_IP cmp I286_TRAP, 0 @@ -1015,45 +1205,63 @@ LABEL void v30(void) { jne short v30_dma_mnlp align 4 -v30_mnlp: movzx eax, bl +v30_mnlp: +#if defined(ENABLE_TRAP) + mov edx, esi + movzx ecx, I286_CS + call steptrap +#endif + movzx eax, bl call v30op[eax*4] cmp I286_REMCLOCK, 0 jg v30_mnlp - mov dword ptr (i286reg.prefetchque), ebx + mov dword ptr (i286core.s.prefetchque), ebx mov I286_IP, si popad ret align 4 -v30_dma_mnlp: movzx eax, bl +v30_dma_mnlp: +#if defined(ENABLE_TRAP) + mov edx, esi + movzx ecx, I286_CS + call steptrap +#endif + movzx eax, bl call v30op[eax*4] - call dmap_i286 + call dmax86 cmp I286_REMCLOCK, 0 jg v30_dma_mnlp - mov dword ptr (i286reg.prefetchque), ebx + mov dword ptr (i286core.s.prefetchque), ebx mov I286_IP, si popad ret align 4 -v30_trapping: movzx eax, bl +v30_trapping: +#if defined(ENABLE_TRAP) + mov edx, esi + movzx ecx, I286_CS + call steptrap +#endif + movzx eax, bl call v30op[eax*4] cmp I286_TRAP, 0 je v30notrap mov ecx, 1 call i286x_localint -v30notrap: mov dword ptr (i286reg.prefetchque), ebx +v30notrap: mov dword ptr (i286core.s.prefetchque), ebx mov I286_IP, si popad ret } } -LABEL void v30_step(void) { +LABEL void v30x_step(void) { __asm { pushad - mov ebx, dword ptr (i286reg.prefetchque) + mov ebx, dword ptr (i286core.s.prefetchque) movzx esi, I286_IP movzx eax, bl @@ -1064,10 +1272,10 @@ LABEL void v30_step(void) { mov ecx, 1 call i286x_localint nexts: - mov dword ptr (i286reg.prefetchque), ebx + mov dword ptr (i286core.s.prefetchque), ebx mov I286_IP, si - call dmap_i286 + call dmax86 popad ret }