Applied all mainline PCem commits;

Added experimental NVidia Riva TNT2 emulation (patch from MoochMcGee);
ASUS P/I-P54TP4XE, ASUS P/I-P55T2P4, and ASUS P/I-P55TVP4 are back;
National Semiconductor PC87306 Super I/O chip now correctly reenables devices after a chip power cycle;
Several FDC improvements and the behavior is now a bit closer to real hardware (based on actual tests);
Added MR Intel Advanced/ATX with Microid Research BIOS with support for 4 floppy drives and up to 4 IDE controllers;
Added floppy drives 3 and 4, bringing the maximum to 4;
You can now connect hard disks to the tertiary IDE controller;
Correct undocumented behavior of the LEA instruction with register is back on 286 and later CPU's;
Pentium-rea models with Intel chipsets now have port 92 (with alternate reset and alternate A20 toggle);
Overhauled DMA channel read and write routines and fixed cascading;
Improved IMG detection of a bad BPB (or complete lack of a BPB);
Added preliminary emulation of PS/2 1.44 MB and PC-98 1.25 MB 3-mode drives (both have an inverted DENSEL pin);
Removed the incorrect Amstrad mouse patch from TheCollector1995;
Fixed ATAPI CD-ROM disk change detection;
Windows IOCTL CD-ROM handler now tries to use direct SCSI passthrough for more things, including obtaining CD-ROM capacity;
The Diamond Stealth32 (ET4000/W32p) now also works correctly on the two Award SiS 496/497 boxes;
The (S)VGA handler now converts 6-bit RAMDAC RGB channels to standard 8-bit RGB using a lookup table generated at emulator start, calculated using the correct intensity conversion method and treating intensity 64 as equivalent to 63;
Moved a few options from the Configuration dialog box to the menu;
SIO, PIIX, and PIIX3 now have the reset control register on port CF9 as they should;
Several bugfixes.
This commit is contained in:
OBattler
2016-12-23 03:16:24 +01:00
parent 724c5699ca
commit dc46480aa4
142 changed files with 8778 additions and 3331 deletions

View File

@@ -145,6 +145,18 @@ static int LOAD_VAR_W(uintptr_t addr)
return host_reg;
}
static int LOAD_VAR_WL(uintptr_t addr)
{
int host_reg = find_host_reg();
host_reg_mapping[host_reg] = 0;
addbyte(0x0f); /*MOVZX host_reg, [addr]*/
addbyte(0xb7);
addbyte(0x05 | (host_reg << 3));
addlong((uint32_t)addr);
return host_reg;
}
static int LOAD_VAR_L(uintptr_t addr)
{
int host_reg = find_host_reg();
@@ -693,6 +705,19 @@ static void MEM_LOAD_ADDR_EA_W(x86seg *seg)
host_reg_mapping[0] = 8;
}
static void MEM_LOAD_ADDR_EA_W_OFFSET(x86seg *seg, int offset)
{
addbyte(0x8b); /*MOVL EDX, seg->base*/
addbyte(0x05 | (REG_EDX << 3));
addlong((uint32_t)&seg->base);
addbyte(0x83); /*ADD EAX, offset*/
addbyte(0xc0);
addbyte(offset);
addbyte(0xe8); /*CALL mem_load_addr_ea_w*/
addlong(mem_load_addr_ea_w - (uint32_t)(&codeblock[block_current].data[block_pos + 4]));
host_reg_mapping[0] = 8;
}
static int MEM_LOAD_ADDR_EA_W_NO_ABRT(x86seg *seg)
{
addbyte(0x8b); /*MOVL EDX, seg->base*/
@@ -2169,6 +2194,59 @@ static void FP_LOAD_IQ()
}
}
static void FP_LOAD_IMM_Q(uint64_t v)
{
if (codeblock[block_current].flags & CODEBLOCK_STATIC_TOP)
{
addbyte(0xc7); /*MOV ST[reg][EBP], v*/
addbyte(0x45);
addbyte(cpu_state_offset(ST[(cpu_state.TOP - 1) & 7]));
addlong(v & 0xffffffff);
addbyte(0xc7); /*MOV ST[reg][EBP]+4, v*/
addbyte(0x45);
addbyte(cpu_state_offset(ST[(cpu_state.TOP - 1) & 7]) + 4);
addlong(v >> 32);
addbyte(0xc6); /*MOVB TOP[EBP], (TOP-1) & 7*/
addbyte(0x45);
addbyte(cpu_state_offset(TOP));
addbyte((cpu_state.TOP - 1) & 7);
addbyte(0xc6); /*MOVB tag[reg][EBP], 1:0*/
addbyte(0x45);
addbyte(cpu_state_offset(tag[(cpu_state.TOP - 1) & 7]));
addbyte(v ? 0 : 1);
}
else
{
addbyte(0x8b); /*MOV EBX, TOP*/
addbyte(0x5d);
addbyte(cpu_state_offset(TOP));
addbyte(0x83); /*SUB EBX, 1*/
addbyte(0xeb);
addbyte(1);
addbyte(0x83); /*AND EBX, 7*/
addbyte(0xe3);
addbyte(7);
addbyte(0xc7); /*MOV ST[EBP+EBX*8], v*/
addbyte(0x44);
addbyte(0xdd);
addbyte(cpu_state_offset(ST));
addlong(v & 0xffffffff);
addbyte(0xc7); /*MOV ST[EBP+EBX*8]+4, v*/
addbyte(0x44);
addbyte(0xdd);
addbyte(cpu_state_offset(ST) + 4);
addlong(v >> 32);
addbyte(0xc6); /*MOVB tag[reg][EBP], 1:0*/
addbyte(0x44);
addbyte(0x1d);
addbyte(cpu_state_offset(tag[0]));
addbyte(v ? 0 : 1);
addbyte(0x89); /*MOV TOP, EBX*/
addbyte(0x5d);
addbyte(cpu_state_offset(TOP));
}
}
static int FP_LOAD_REG(int reg)
{
if (codeblock[block_current].flags & CODEBLOCK_STATIC_TOP)
@@ -2425,6 +2503,42 @@ static void FP_POP()
addbyte(cpu_state_offset(TOP));
}
}
static void FP_POP2()
{
if (codeblock[block_current].flags & CODEBLOCK_STATIC_TOP)
{
addbyte(0xc6); /*MOVB tag[0][EBP], 3*/
addbyte(0x45);
addbyte(cpu_state_offset(tag[cpu_state.TOP]));
addbyte(3);
addbyte(0xc6); /*MOVB tag[1][EBP], 3*/
addbyte(0x45);
addbyte(cpu_state_offset(tag[(cpu_state.TOP+1)&7]));
addbyte(3);
addbyte(0xc6); /*MOVB TOP[EBP], (TOP+2) & 7*/
addbyte(0x45);
addbyte(cpu_state_offset(TOP));
addbyte((cpu_state.TOP + 2) & 7);
}
else
{
addbyte(0x8b); /*MOV EAX, TOP*/
addbyte(0x45);
addbyte(cpu_state_offset(TOP));
addbyte(0xc6); /*MOVB tag[EAX], 3*/
addbyte(0x44);
addbyte(0x05);
addbyte(cpu_state_offset(tag[0]));
addbyte(3);
addbyte(0x04); /*ADD AL, 2*/
addbyte(2);
addbyte(0x24); /*AND AL, 7*/
addbyte(7);
addbyte(0x88); /*MOV TOP, AL*/
addbyte(0x45);
addbyte(cpu_state_offset(TOP));
}
}
#define FPU_ADD 0x00
#define FPU_DIV 0x30
@@ -3162,6 +3276,47 @@ static void FP_COMPARE_REG(int dst, int src)
}
}
static void FP_FCHS()
{
if (codeblock[block_current].flags & CODEBLOCK_STATIC_TOP)
{
addbyte(0xdd); /*FLD ST[0][EBP]*/
addbyte(0x45);
addbyte(cpu_state_offset(ST[cpu_state.TOP]));
addbyte(0xd9); /*FCHS*/
addbyte(0xe0);
addbyte(0x80); /*AND tag[dst][EBP], ~TAG_UINT64*/
addbyte(0x65);
addbyte(cpu_state_offset(tag[cpu_state.TOP]));
addbyte(~TAG_UINT64);
addbyte(0xdd); /*FSTP ST[dst][EBP]*/
addbyte(0x5d);
addbyte(cpu_state_offset(ST[cpu_state.TOP]));
}
else
{
addbyte(0x8b); /*MOV EAX, TOP*/
addbyte(0x45);
addbyte(cpu_state_offset(TOP));
addbyte(0xdd); /*FLD [ESI+EAX*8]*/
addbyte(0x44);
addbyte(0xc5);
addbyte(cpu_state_offset(ST));
addbyte(0x80); /*AND tag[EAX], ~TAG_UINT64*/
addbyte(0x64);
addbyte(0x05);
addbyte(cpu_state_offset(tag[0]));
addbyte(~TAG_UINT64);
addbyte(0xd9); /*FCHS*/
addbyte(0xe0);
addbyte(0xdd); /*FSTP ST[EAX*8]*/
addbyte(0x5c);
addbyte(0xc5);
addbyte(cpu_state_offset(ST));
}
}
static void UPDATE_NPXC(int reg)
{
addbyte(0x66); /*AND cpu_state.new_npxc, ~0xc00*/
@@ -3664,3 +3819,23 @@ static void MEM_CHECK_WRITE_L(x86seg *seg)
addlong(mem_check_write_l - (uint32_t)(&codeblock[block_current].data[block_pos + 4]));
LOAD_EA();
}
static void LOAD_SEG(int host_reg, void *seg)
{
addbyte(0xc7); /*MOV [ESP+4], seg*/
addbyte(0x44);
addbyte(0x24);
addbyte(4);
addlong((uint32_t)seg);
addbyte(0x89); /*MOV [ESP], host_reg*/
addbyte(0x04 | (host_reg << 3));
addbyte(0x24);
CALL_FUNC(loadseg);
addbyte(0x80); /*CMP abrt, 0*/
addbyte(0x7d);
addbyte(cpu_state_offset(abrt));
addbyte(0);
addbyte(0x0f); /*JNE end*/
addbyte(0x85);
addlong(BLOCK_EXIT_OFFSET - (block_pos + 4));
}