ARM (26-bit): TST/TEQ should only update flags

This eliminates the need for patches in poizone/ertictac, all deco32 games 
still run (including hvysmsh), and it better matches the documentation.
This commit is contained in:
R. Belmont 2009-07-05 17:32:15 +00:00
parent ce8e7c07ab
commit c79dfb05f3
2 changed files with 21 additions and 45 deletions

View File

@ -333,7 +333,7 @@ static CPU_EXECUTE( arm )
cpustate->icount = cycles; cpustate->icount = cycles;
do do
{ {
debugger_instruction_hook(device, R15); debugger_instruction_hook(device, R15 & ADDRESS_MASK);
/* load instruction */ /* load instruction */
pc = R15; pc = R15;
@ -805,7 +805,6 @@ static void HandleALU( ARM_REGS* cpustate, UINT32 insn )
rd = (rn + op2); rd = (rn + op2);
HandleALUAddFlags(rd, rn, op2); HandleALUAddFlags(rd, rn, op2);
break; break;
/* Logical operations */ /* Logical operations */
case OPCODE_AND: case OPCODE_AND:
case OPCODE_TST: case OPCODE_TST:
@ -866,36 +865,25 @@ static void HandleALU( ARM_REGS* cpustate, UINT32 insn )
} }
} }
/* TST & TEQ can affect R15 (the condition code register) with the S bit set */ /* TST & TEQ can affect R15 (the condition code register) with the S bit set */
} else if (rdn==eR15) { }
if (insn & INSN_S) { else if ((rdn==eR15) && (insn & INSN_S))
if (ARM_DEBUG_CORE) {
logerror("%08x: TST class on R15 s bit set\n",R15); // update only the flags
if ((R15&MODE_MASK)!=0)
/* Dubious hack for 'TEQS R15, #$3', the docs suggest execution {
should continue two instructions later (because pipelined R15 // combine the flags from rd with the address from R15
is read back as already being incremented), but it seems the rd &= ~ADDRESS_MASK;
hardware should execute the instruction in the delay slot. rd |= (R15 & ADDRESS_MASK);
Simulate it by just setting the PC back to the previously SetRegister(cpustate,rdn,rd);
skipped instruction.
See Heavy Smash (Data East) at 0x1c4
*/
if (insn==0xe33ff003)
rd-=4;
cpustate->icount -= S_CYCLE + N_CYCLE;
if ((R15&MODE_MASK)!=0)
{
SetRegister(cpustate, 15, rd);
}
else
{
SetRegister(cpustate, 15, (rd&ADDRESS_MASK) | (rd&PSR_MASK) | (R15&IRQ_MASK) | (R15&MODE_MASK));
}
} else {
if (ARM_DEBUG_CORE)
logerror("%08x: TST class on R15 no s bit set\n",R15);
} }
else
{
// combine the flags from rd with the address from R15
rd &= ~ADDRESS_MASK; // clear address part of RD
rd |= (R15 & ADDRESS_MASK); // RD = address part of R15
SetRegister(cpustate, rdn,(rd&ADDRESS_MASK) | (rd&PSR_MASK) | (R15&IRQ_MASK) | (R15&MODE_MASK));
}
cpustate->icount -= S_CYCLE + N_CYCLE;
} }
} }

View File

@ -439,18 +439,6 @@ ROM_START( poizone )
ROM_LOAD32_BYTE( "p_son24.bin", 0x140003, 0x10000, CRC(a09d7f55) SHA1(e0d562c655c16034b40db93de801b98b7948beb2) ) ROM_LOAD32_BYTE( "p_son24.bin", 0x140003, 0x10000, CRC(a09d7f55) SHA1(e0d562c655c16034b40db93de801b98b7948beb2) )
ROM_END ROM_END
static DRIVER_INIT( ertictac ) GAME( 1990, ertictac, 0, ertictac, ertictac, 0, ROT0, "Sisteme", "Erotictac/Tactic" ,GAME_NO_SOUND)
{ GAME( 1991, poizone, 0, ertictac, poizone, 0, ROT0, "Eterna" ,"Poizone" ,GAME_NO_SOUND|GAME_NOT_WORKING)
((UINT32 *)memory_region(machine, "user1"))[0x55]=0;// patched TSTS r11,r15,lsl #32 @ $3800154
}
static DRIVER_INIT( poizone )
{
((UINT32 *)memory_region(machine, "user1"))[0x21C/4]=0;// patched TSTS r11,r15,lsl #32 @ $380021C
}
GAME( 1990, ertictac, 0, ertictac, ertictac, ertictac, ROT0, "Sisteme", "Erotictac/Tactic" ,GAME_NO_SOUND)
GAME( 1991, poizone, 0, ertictac, poizone, poizone, ROT0, "Eterna" ,"Poizone" ,GAME_NO_SOUND|GAME_NOT_WORKING)