use crate::isa::{An, Dn, Long, Word};
use crate::vm::{
Exception,
Instruction,
InstructionLen,
InstructionVtable,
Mem,
};
impl Instruction {
pub fn decode(mem: &Mem, mut addr: Long) -> Result<Self, Exception> {
let mut data = [u16::default(); InstructionLen::MAX.get()];
data[0] = mem.load_word(addr)?.as_u16();
let vtable = Self::vtable(data[0])
.ok_or(Exception::ILLEGAL_INSTRUCTION)?;
for word in data.iter_mut().take(vtable.len.get()).skip(1) {
addr = addr.add_usize(size_of::<Word>());
*word = mem.load_word(addr)?.as_u16();
}
Ok(Self { data, vtable })
}
#[allow(clippy::unusual_byte_groupings)]
fn vtable(word: u16) -> Option<&'static InstructionVtable> {
match word & 0b1111_000_111_111_000 {
0b1001_000_000_001_000 => {
return None;
}
0b1001_000_000_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b ({r0}), {r1}")
},
});
}
0b1001_000_000_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b ({r0})+, {r1}")
},
});
}
0b1001_000_000_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b -({r0}), {r1}")
},
});
}
0b1001_000_001_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, {r1}")
},
});
}
0b1001_000_001_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, {r1}")
},
});
}
0b1001_000_001_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w ({r0}), {r1}")
},
});
}
0b1001_000_001_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w ({r0})+, {r1}")
},
});
}
0b1001_000_001_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w -{r0}, {r1}")
},
});
}
0b1001_000_010_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, {r1}")
},
});
}
0b1001_000_010_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, {r1}")
},
});
}
0b1001_000_010_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l ({r0})+, {r1}")
},
});
}
0b1001_000_010_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l ({r0})+, {r1}")
},
});
}
0b1001_000_010_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l -({r0}), {r1}")
},
});
}
0b1001_000_011_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.w {r0}, {r1}")
},
});
}
0b1001_000_011_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.w {r0}, {r1}")
},
});
}
0b1001_000_011_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.w ({r0}), {r1}")
},
});
}
0b1001_000_011_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.w ({r0})+, {r1}")
},
});
}
0b1001_000_011_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.w -({r0}), {r1}")
},
});
}
0b1001_000_100_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b {r0}, {r1}")
},
});
}
0b1001_000_100_001_000 => {
return None;
}
0b1001_000_100_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b {r0}, ({r1})")
},
});
}
0b1001_000_100_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b {r0}, ({r1})+")
},
});
}
0b1001_000_100_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.b {r0}, -({r1})")
},
});
}
0b1001_000_101_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, {r1}")
},
});
}
0b1001_000_101_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, {r1}")
},
});
}
0b1001_000_101_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, ({r1})")
},
});
}
0b1001_000_101_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, ({r1})+")
},
});
}
0b1001_000_101_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.w {r0}, -({r1})")
},
});
}
0b1001_000_110_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, {r1}")
},
});
}
0b1001_000_110_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, {r1}")
},
});
}
0b1001_000_110_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, ({r1})")
},
});
}
0b1001_000_110_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, ({r1})+")
},
});
}
0b1001_000_110_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "sub.l {r0}, -({r1})")
},
});
}
0b1001_000_111_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.l {r0}, {r1}")
},
});
}
0b1001_000_111_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.l {r0}, {r1}")
},
});
}
0b1001_000_111_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.l ({r0}), {r1}")
},
});
}
0b1001_000_111_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.l ({r0})+, {r1}")
},
});
}
0b1001_000_111_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "suba.l -({r0}), {r1}")
},
});
}
0b1100_000_000_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.b {r0}, {r1}")
},
});
}
0b1100_000_000_001_000 => {
return None;
}
0b1100_000_000_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.b ({r0}), {r1}")
},
});
}
0b1100_000_000_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.b ({r0})+, {r1}")
},
});
}
0b1100_000_000_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.b -({r0}), {r1}")
},
});
}
0b1100_000_001_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.w {r0}, {r1}")
},
});
}
0b1100_000_001_001_000 => {
return None;
}
0b1100_000_001_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.w ({r0}), {r1}")
},
});
}
0b1100_000_001_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.w ({r0})+, {r1}")
},
});
}
0b1100_000_001_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.w -({r0}), {r1}")
},
});
}
0b1100_000_010_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r0}, {r1}")
},
});
}
0b1100_000_010_001_000 => {
return None;
}
0b1100_000_010_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.l ({r0}), {r1}")
},
});
}
0b1100_000_010_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.l ({r0})+, {r1}")
},
});
}
0b1100_000_010_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "and.l -({r0}), {r1}")
},
});
}
0b1100_000_100_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.b {r1}, {r0}")
},
});
}
0b1100_000_100_001_000 => {
return None;
}
0b1100_000_100_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r1}, ({r0})")
},
});
}
0b1100_000_100_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.b {r1}, ({r0})+")
},
});
}
0b1100_000_100_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.b {r1}, -({r0})")
},
});
}
0b1100_000_101_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.w {r1}, {r0}")
},
});
}
0b1100_000_101_001_000 => {
return None;
}
0b1100_000_101_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.w {r1}, ({r0})")
},
});
}
0b1100_000_101_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.w {r1}, ({r0})+")
},
});
}
0b1100_000_101_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.w {r1}, -({r0})")
},
});
}
0b1100_000_110_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r1}, {r0}")
},
});
}
0b1100_000_110_001_000 => {
return None;
}
0b1100_000_110_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r1}, ({r0})")
},
});
}
0b1100_000_110_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r1}, ({r0})+")
},
});
}
0b1100_000_110_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "and.l {r1}, -({r0})")
},
});
}
0b1101_000_000_001_000 => {
return None;
}
0b1101_000_000_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.b ({r0}), {r1}")
},
});
}
0b1101_000_000_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.b ({r0})+, {r1}")
},
});
}
0b1101_000_000_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.b -({r0}), {r1}")
},
});
}
0b1101_000_001_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_001_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_001_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w ({r0}), {r1}")
},
});
}
0b1101_000_001_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w ({r0})+, {r1}")
},
});
}
0b1101_000_001_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w -{r0}, {r1}")
},
});
}
0b1101_000_010_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_010_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_010_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l ({r0})+, {r1}")
},
});
}
0b1101_000_010_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l ({r0})+, {r1}")
},
});
}
0b1101_000_010_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l -({r0}), {r1}")
},
});
}
0b1101_000_011_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_011_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_011_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w ({r0}), {r1}")
},
});
}
0b1101_000_011_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w ({r0})+, {r1}")
},
});
}
0b1101_000_011_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w -({r0}), {r1}")
},
});
}
0b1101_000_100_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.b {r0}, {r1}")
},
});
}
0b1101_000_100_001_000 => {
return None;
}
0b1101_000_100_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.b {r0}, ({r1})")
},
});
}
0b1101_000_100_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.b {r0}, ({r1})+")
},
});
}
0b1101_000_100_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.b {r0}, -({r1})")
},
});
}
0b1101_000_101_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_101_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, {r1}")
},
});
}
0b1101_000_101_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, ({r1})")
},
});
}
0b1101_000_101_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, ({r1})+")
},
});
}
0b1101_000_101_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.w {r0}, -({r1})")
},
});
}
0b1101_000_110_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = Dn::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_110_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_110_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, ({r1})")
},
});
}
0b1101_000_110_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, ({r1})+")
},
});
}
0b1101_000_110_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, -({r1})")
},
});
}
0b1101_000_111_000_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = Dn::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_111_001_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l {r0}, {r1}")
},
});
}
0b1101_000_111_010_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l ({r0}), {r1}")
},
});
}
0b1101_000_111_011_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l ({r0})+, {r1}")
},
});
}
0b1101_000_111_100_000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let r0 = An::from_u16(instruction.data[0] >> 9);
let r1 = An::from_u16(instruction.data[0] >> 3);
write!(f, "add.l -({r0}), {r1}")
},
});
}
_ => {}
}
#[expect(clippy::single_match)]
match word & 0b1111_1111_0000_0000 {
0b0110_0000_0000_0000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |instruction, vm| {
let disp = i32::from((instruction.data[0] & 0b1111_1111) as i8);
let mut dest = vm.regs().pc().as_u32();
dest = dest.wrapping_add(2);
dest = dest.wrapping_add_signed(disp);
*vm.regs_mut().pc_mut() = Long::from_u32(dest);
Ok(())
},
fmt: |instruction, f| {
let disp = (instruction.data[0] & 0b1111_1111) as i8;
write!(f, "bra #{disp}.b")
},
});
}
_ => {}
}
#[expect(clippy::single_match)]
match word & 0b1111_1111_1111_0000 {
0b0100_1110_0100_1111 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let vector = instruction.data[0] & 0b1111;
write!(f, "trap #{vector}")
},
});
}
_ => {}
}
match word {
0b0100_1110_0111_0001 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |_instruction, f| {
write!(f, "nop")
},
});
}
0b0100_1110_0111_0101 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |_instruction, f| {
write!(f, "rts")
},
});
}
0b0100_1110_0111_0111 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(1).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |_instruction, f| {
write!(f, "rtr")
},
});
}
0b0110_0000_0000_0000 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(2).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let disp = instruction.data[1] as i16;
write!(f, "bra #{disp}.w")
},
});
}
0b0110_0000_1111_1111 => {
return Some(&InstructionVtable {
len: const { InstructionLen::new(3).unwrap() },
exec: |_instruction, _vm| {
Ok(())
},
fmt: |instruction, f| {
let mut disp = i32::from(instruction.data[1]) << u16::BITS;
disp |= i32::from(instruction.data[2]);
write!(f, "bra #{disp}.l")
},
});
}
_ => {}
}
None
}
}