diff --git a/src/bin/upddisasm/main.rs b/src/bin/upddisasm/main.rs index 3ac0fb8..25cdd7e 100644 --- a/src/bin/upddisasm/main.rs +++ b/src/bin/upddisasm/main.rs @@ -17,7 +17,7 @@ fn main() -> Result<()> { let mut pos = 0; while let Ok(ins) = Instruction::decode(&mut fiter) { println!("{:04X} {}", pos, ins); - pos += ins.len(); + pos += 1; } Ok(()) } diff --git a/src/snes/cpu_upd77c25/cpu.rs b/src/snes/cpu_upd77c25/cpu.rs index 18e4b53..d55de39 100644 --- a/src/snes/cpu_upd77c25/cpu.rs +++ b/src/snes/cpu_upd77c25/cpu.rs @@ -95,7 +95,7 @@ impl CpuUpd77c25 { fn execute_mul(&mut self) { let k = self.regs.read(Register::K) as i32; let l = self.regs.read(Register::L) as i32; - let result = k * l; + let result = k.wrapping_mul(l); self.regs.write(Register::M, (result >> 15) as i16 as u16); self.regs.write(Register::N, (result << 1) as i16 as u16); } @@ -266,10 +266,11 @@ impl CpuUpd77c25 { fn op_op_alu(&mut self, instr: &InstructionOpRt) -> Result<()> { // First operand - let (a, a_flags) = match instr.asl() { - ASL::ACCA => (self.regs.read(Register::ACCA), Flags::A), - ASL::ACCB => (self.regs.read(Register::ACCB), Flags::B), + let (a_reg, a_flags) = match instr.asl() { + ASL::ACCA => (Register::ACCA, Flags::A), + ASL::ACCB => (Register::ACCB, Flags::B), }; + let a = self.regs.read(a_reg); // Second operand let b = match instr.pselect() { @@ -313,21 +314,28 @@ impl CpuUpd77c25 { a_flags, &[(Flag::Z, c == 0), (Flag::S0, c & 0x8000 == 0x8000)], ); - if self.regs.test_flag(a_flags, Flag::OV1) { + if !self.regs.test_flag(a_flags, Flag::OV1) { self.regs.write_flags( a_flags, &[(Flag::S1, self.regs.test_flag(a_flags, Flag::S0))], ); } + self.regs.write(a_reg, c); + self.regs.write_flags( a_flags, &match instr.alu() { AluFunction::Nop => unreachable!(), - AluFunction::And | AluFunction::Cmp | AluFunction::Or | AluFunction::Xor => { - [(Flag::C, false), (Flag::OV0, false), (Flag::OV1, false)] - } + AluFunction::And + | AluFunction::Cmp + | AluFunction::Or + | AluFunction::Xor + | AluFunction::Shl2 + | AluFunction::Shl4 + | AluFunction::Xchg => [(Flag::C, false), (Flag::OV0, false), (Flag::OV1, false)], AluFunction::Sub | AluFunction::Sbr | AluFunction::Dec => { + todo!(); let fcarry = a ^ b ^ c; let foverflow = (a ^ c) & (a ^ b); let ov0 = foverflow & 0x8000 == 0x8000; @@ -355,10 +363,6 @@ impl CpuUpd77c25 { (Flag::OV0, false), (Flag::OV1, false), ], - AluFunction::Shl2 | AluFunction::Shl4 => { - [(Flag::C, false), (Flag::OV0, false), (Flag::OV1, false)] - } - AluFunction::Xchg => todo!(), }, ); diff --git a/src/snes/cpu_upd77c25/instruction.rs b/src/snes/cpu_upd77c25/instruction.rs index e2c79a1..b9f3eab 100644 --- a/src/snes/cpu_upd77c25/instruction.rs +++ b/src/snes/cpu_upd77c25/instruction.rs @@ -222,12 +222,12 @@ impl InstructionOpRt { } pub fn pselect(&self) -> PSelect { - PSelect::from_u32((self.opcode >> 20) >> 0x03) + PSelect::from_u32((self.opcode >> 20) & 0x03) .expect(format!("Invalid PSelect in {:?}", self).as_str()) } pub fn alu(&self) -> AluFunction { - AluFunction::from_u32((self.opcode >> 16) & 0x07) + AluFunction::from_u32((self.opcode >> 16) & 0x0F) .expect(format!("Invalid ALU in {:?}", self).as_str()) } diff --git a/src/snes/cpu_upd77c25/regs.rs b/src/snes/cpu_upd77c25/regs.rs index a4cf44c..c6ccfbe 100644 --- a/src/snes/cpu_upd77c25/regs.rs +++ b/src/snes/cpu_upd77c25/regs.rs @@ -302,7 +302,7 @@ impl fmt::Display for RegisterFile { write!( f, - "ACCA:{:04X} ACCB:{:04X} K:{:04X} L:{:04X} M:{:04X} N:{:04X} TR:{:04X} TRB:{:04X} SP:{:01X} PC:{:04X} DP:{:04X} RP:{:04X} SR:{:04X} ({}) Flg-A:{:02X} ({}) Flg-B:{:02X} ({})", + "ACCA:{:04X} ACCB:{:04X} K:{:04X} L:{:04X} M:{:04X} N:{:04X} TR:{:04X} TRB:{:04X} SP:{:01X} PC:{:04X} DP:{:04X} RP:{:04X} DR:{:04X} SR:{:04X} ({}) Flg-A:{:02X} ({}) Flg-B:{:02X} ({})", self.acca, self.accb, self.k, @@ -315,6 +315,7 @@ impl fmt::Display for RegisterFile { self.pc, self.dp, self.rp, + self.dr, self.sr, sr, self.flags[0],