Fixed bug in m68k with Extend flag in shift instructions

This commit is contained in:
transistor 2021-12-01 10:45:24 -08:00
parent 364c51524f
commit 0f2f989775
4 changed files with 47 additions and 12 deletions

View File

@ -207,6 +207,10 @@ impl M68k {
for _ in 0..count {
pair = shift_operation(pair.0, size, shift_dir, true);
}
self.set_target_value(target, pair.0, size)?;
// Adjust flags
self.set_flag(Flags::Extend, false);
self.set_logic_flags(pair.0, size);
if pair.1 {
self.set_flag(Flags::Carry, true);
@ -215,7 +219,6 @@ impl M68k {
if get_msb(pair.0, size) != get_msb(original, size) {
self.set_flag(Flags::Overflow, true);
}
self.set_target_value(target, pair.0, size)?;
},
Instruction::Bcc(cond, offset) => {
let should_branch = self.get_current_condition(cond);
@ -459,12 +462,15 @@ impl M68k {
for _ in 0..count {
pair = shift_operation(pair.0, size, shift_dir, false);
}
self.set_target_value(target, pair.0, size)?;
// Adjust flags
self.set_flag(Flags::Extend, false);
self.set_logic_flags(pair.0, size);
if pair.1 {
self.set_flag(Flags::Carry, true);
self.set_flag(Flags::Extend, true);
}
self.set_target_value(target, pair.0, size)?;
},
Instruction::MOVE(src, dest, size) => {
let value = self.get_target_value(src, size)?;
@ -614,11 +620,13 @@ impl M68k {
for _ in 0..count {
pair = rotate_operation(pair.0, size, shift_dir, None);
}
self.set_target_value(target, pair.0, size)?;
// Adjust flags
self.set_logic_flags(pair.0, size);
if pair.1 {
self.set_flag(Flags::Carry, true);
}
self.set_target_value(target, pair.0, size)?;
},
Instruction::ROXd(count, target, size, shift_dir) => {
let count = self.get_target_value(count, size)? % 64;
@ -627,11 +635,13 @@ impl M68k {
pair = rotate_operation(pair.0, size, shift_dir, Some(self.get_flag(Flags::Extend)));
self.set_flag(Flags::Extend, pair.1);
}
self.set_target_value(target, pair.0, size)?;
// Adjust flags
self.set_logic_flags(pair.0, size);
if pair.1 {
self.set_flag(Flags::Carry, true);
}
self.set_target_value(target, pair.0, size)?;
},
Instruction::RTE => {
self.require_supervisor()?;

View File

@ -694,6 +694,32 @@ mod execute_tests {
init: TestState { pc: 0x00000000, ssp: 0x00000000, usp: 0x00000000, d0: 0x000000CB, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x27FF, mem: 0x00000000 },
fini: TestState { pc: 0x00000002, ssp: 0x00000000, usp: 0x00000000, d0: 0x000000CB, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x27F0, mem: 0x00000000 },
},
TestCase {
name: "lsl",
ins: Instruction::LSd(Target::Immediate(1), Target::DirectDReg(0), Size::Byte, ShiftDirection::Left),
data: &[ 0xE308 ],
cputype: M68kType::MC68010,
init: TestState { pc: 0x00000000, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000001, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x271F, mem: 0x00000000 },
fini: TestState { pc: 0x00000002, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000002, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x2700, mem: 0x00000000 },
},
TestCase {
name: "lsl with bit out",
ins: Instruction::LSd(Target::Immediate(1), Target::DirectDReg(0), Size::Byte, ShiftDirection::Left),
data: &[ 0xE308 ],
cputype: M68kType::MC68010,
init: TestState { pc: 0x00000000, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000081, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x2700, mem: 0x00000000 },
fini: TestState { pc: 0x00000002, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000002, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x2711, mem: 0x00000000 },
},
TestCase {
name: "lsr",
ins: Instruction::LSd(Target::Immediate(1), Target::DirectDReg(0), Size::Byte, ShiftDirection::Right),
data: &[ 0xE208 ],
cputype: M68kType::MC68010,
init: TestState { pc: 0x00000000, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000081, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x2700, mem: 0x00000000 },
fini: TestState { pc: 0x00000002, ssp: 0x00000000, usp: 0x00000000, d0: 0x00000040, d1: 0x00000000, a0: 0x00000000, a1: 0x00000000, sr: 0x2711, mem: 0x00000000 },
},
TestCase {
name: "muls",
ins: Instruction::MULW(Target::Immediate(0x0276), 0, Sign::Signed),

View File

@ -92,14 +92,15 @@ impl Debugger {
//self.port.dump_memory(self.state.ssp as Address, 0x40 as Address);
}
},
"dp" | "dump_peripheral" => {
"i" | "inspect" => {
if args.len() < 2 {
println!("Usage: dp <device_name> [<device specific arguments>]");
println!("Usage: inspect <device_name> [<device specific arguments>]");
} else {
let device = system.devices.get(args[1]).ok_or_else(|| Error::new(&format!("No device named {}", args[1])))?;
let subargs = if args.len() > 2 { &args[2..] } else { &[""] };
device.borrow_mut().as_inspectable()
.ok_or_else(|| Error::new("That device is not inspectable"))?
.inspect(system, &args[2..])?;
.inspect(system, subargs)?;
}
},
"dis" | "disassemble" => {

View File

@ -649,7 +649,7 @@ impl Addressable for Ym7101 {
self.state.transfer_fill = if data.len() >= 2 { read_beu16(data) } else { data[0] as u16 };
self.state.set_dma_mode(DmaType::Fill);
} else {
info!("{}: data port write {} bytes to {:?}:{:x} with {:?}", DEV_NAME, data.len(), self.state.transfer_target, self.state.transfer_addr, data);
debug!("{}: data port write {} bytes to {:?}:{:x} with {:?}", DEV_NAME, data.len(), self.state.transfer_target, self.state.transfer_addr, data);
{
let addr = self.state.transfer_addr as usize;
@ -664,7 +664,7 @@ impl Addressable for Ym7101 {
// Write to Control Port
0x04 | 0x06 => {
info!("{}: write {} bytes to port {:x} with data {:?}", DEV_NAME, data.len(), addr, data);
debug!("{}: write {} bytes to port {:x} with data {:?}", DEV_NAME, data.len(), addr, data);
let value = read_beu16(data);
if (value & 0xC000) == 0x8000 {
@ -695,9 +695,7 @@ impl Addressable for Ym7101 {
impl Inspectable for Ym7101 {
fn inspect(&mut self, system: &System, args: &[&str]) -> Result<(), Error> {
let cmd = if args.len() > 0 { args[0] } else { "state" };
match cmd {
match args[0] {
"" | "state" => {
self.state.dump_state();
},