Make sure certain instructions are only executed in supervisor mode
This commit is contained in:
parent
6bbc879244
commit
8c6e26005d
43
src/m68k.rs
43
src/m68k.rs
@ -335,7 +335,13 @@ impl M68K {
|
||||
Instruction::OriCcr(val) => {
|
||||
self.sr = (self.sr & 0xFF00) | ((self.sr & 0xFF) | u16::from(val));
|
||||
}
|
||||
Instruction::OriSr(val) => self.sr |= val,
|
||||
Instruction::OriSr(val) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
self.sr |= val;
|
||||
}
|
||||
Instruction::Ori(size, dst, val) => {
|
||||
let dst_val = self.read_effective(dst, size)?;
|
||||
let res = dst_val | val;
|
||||
@ -353,7 +359,13 @@ impl M68K {
|
||||
Instruction::AndiCcr(val) => {
|
||||
self.sr = (self.sr & 0xFF00) | ((self.sr & 0xFF) & u16::from(val));
|
||||
}
|
||||
Instruction::AndiSr(val) => self.sr &= val,
|
||||
Instruction::AndiSr(val) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
self.sr &= val;
|
||||
}
|
||||
Instruction::Andi(size, dst, val) => {
|
||||
let dst_val = self.read_effective(dst, size)?;
|
||||
let res = dst_val & val;
|
||||
@ -377,7 +389,13 @@ impl M68K {
|
||||
Instruction::EoriCcr(val) => {
|
||||
self.sr = (self.sr & 0xFF00) | ((self.sr & 0xFF) ^ u16::from(val));
|
||||
}
|
||||
Instruction::EoriSr(val) => self.sr ^= val,
|
||||
Instruction::EoriSr(val) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
self.sr ^= val;
|
||||
}
|
||||
Instruction::Eori(size, dst, val) => {
|
||||
let dst_val = self.read_effective(dst, size)?;
|
||||
let res = dst_val ^ val;
|
||||
@ -526,6 +544,10 @@ impl M68K {
|
||||
self.sr = (self.sr & 0xFF00) | src_val as u16;
|
||||
}
|
||||
Instruction::MoveToSr(src) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
let src_val = self.read_effective(src, Size::Word)?;
|
||||
self.sr = src_val as u16;
|
||||
}
|
||||
@ -621,6 +643,10 @@ impl M68K {
|
||||
self.write_effective(dst, old_dst, Size::Long)?;
|
||||
}
|
||||
Instruction::MoveUsp(dir, areg) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
let areg = EffectiveAddress::AddressReg(areg);
|
||||
match dir {
|
||||
MoveDirection::MemToReg => self.write_effective(areg, self.usp, Size::Long)?,
|
||||
@ -632,11 +658,19 @@ impl M68K {
|
||||
}
|
||||
Instruction::Nop => (),
|
||||
Instruction::Stop(sr) => {
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
self.sr = sr;
|
||||
self.stopped = true;
|
||||
}
|
||||
Instruction::Rte => {
|
||||
self.sr = self.pop(Size::Word)? as u16;
|
||||
if !self.is_supervisor() {
|
||||
self.trap(8)?;
|
||||
return Err(InsExecError::AbnormalTrap);
|
||||
}
|
||||
let orig_sr = self.pop(Size::Word)? as u16;
|
||||
self.pc = self.pop(Size::Long)?;
|
||||
let format = (self.pop(Size::Word)? & 0xf000) >> 12;
|
||||
if format == 8 {
|
||||
@ -707,6 +741,7 @@ impl M68K {
|
||||
self.stored_mem_cycles.pop();
|
||||
}
|
||||
}
|
||||
self.sr = orig_sr;
|
||||
}
|
||||
Instruction::Rts => self.pc = self.pop(Size::Long)?,
|
||||
Instruction::Trapv => {
|
||||
|
Loading…
Reference in New Issue
Block a user