From b72a857a8acdba64c52ed32eac0d581a0f19a646 Mon Sep 17 00:00:00 2001 From: Filipe Rodrigues Date: Mon, 11 Jan 2021 16:25:59 +0000 Subject: [PATCH] Added `pseudo::move_reg` instruction. --- dcb-exe/src/exe/inst/pseudo.rs | 20 ++++-- dcb-exe/src/exe/inst/pseudo/load_imm.rs | 2 +- dcb-exe/src/exe/inst/pseudo/move_reg.rs | 93 ++++++++++--------------- dcb-exe/src/exe/inst/pseudo/nop.rs | 3 +- 4 files changed, 51 insertions(+), 67 deletions(-) diff --git a/dcb-exe/src/exe/inst/pseudo.rs b/dcb-exe/src/exe/inst/pseudo.rs index da012b8..3aa0f87 100644 --- a/dcb-exe/src/exe/inst/pseudo.rs +++ b/dcb-exe/src/exe/inst/pseudo.rs @@ -9,7 +9,7 @@ pub mod alu_assign; pub mod load_imm; //pub mod jmp; //pub mod load; -//pub mod move_reg; +pub mod move_reg; pub mod nop; //pub mod store; @@ -28,6 +28,9 @@ pub enum Inst { /// No-op Nop(nop::Inst), + + /// Move register + MoveReg(move_reg::Inst), /* /// Load Load(LoadPseudoInst), @@ -35,8 +38,7 @@ pub enum Inst { /// Store Store(StorePseudoInst), - /// Move register - MoveRegPseudo(MoveRegPseudoInst), + /// Load immediate LoadImm(LoadImmInst), @@ -66,12 +68,13 @@ pub enum Inst { } impl Decodable for Inst { + #[rustfmt::skip] fn decode(insts: impl Iterator + Clone) -> Option { // Note: Order is important - load_imm::Inst::decode(insts.clone()) - .map(Self::LoadImm) - .or_else(|| alu_assign::Inst::decode(insts.clone()).map(Self::AluAssign)) - .or_else(move || nop::Inst::decode(insts).map(Self::Nop)) + load_imm ::Inst::decode(insts.clone()).map(Self::LoadImm ) + .or_else( || alu_assign::Inst::decode(insts.clone()).map(Self::AluAssign)) + .or_else( || nop ::Inst::decode(insts.clone()).map(Self::Nop )) + .or_else(move || move_reg ::Inst::decode( insts ).map(Self::MoveReg )) } } @@ -81,6 +84,7 @@ impl InstSize for Inst { Self::AluAssign(inst) => inst.size(), Self::LoadImm(inst) => inst.size(), Self::Nop(inst) => inst.size(), + Self::MoveReg(inst) => inst.size(), } } } @@ -91,6 +95,7 @@ impl InstFmt for Inst { Self::AluAssign(inst) => inst.mnemonic(), Self::LoadImm(inst) => inst.mnemonic(), Self::Nop(inst) => inst.mnemonic(), + Self::MoveReg(inst) => inst.mnemonic(), } } @@ -99,6 +104,7 @@ impl InstFmt for Inst { Self::AluAssign(inst) => inst.fmt(pos, f), Self::LoadImm(inst) => inst.fmt(pos, f), Self::Nop(inst) => inst.fmt(pos, f), + Self::MoveReg(inst) => inst.fmt(pos, f), } } } diff --git a/dcb-exe/src/exe/inst/pseudo/load_imm.rs b/dcb-exe/src/exe/inst/pseudo/load_imm.rs index 9853d75..47812af 100644 --- a/dcb-exe/src/exe/inst/pseudo/load_imm.rs +++ b/dcb-exe/src/exe/inst/pseudo/load_imm.rs @@ -18,7 +18,7 @@ pub enum Kind { /// Word /// - /// Alias for `lui $dst, {hi} / ori $dst, $dst, {imm-lo}` + /// Alias for `lui $dst, {hi} / ori $dst, $dst, {lo}` Word(u32), /// Unsigned half-word diff --git a/dcb-exe/src/exe/inst/pseudo/move_reg.rs b/dcb-exe/src/exe/inst/pseudo/move_reg.rs index 3165aee..6548877 100644 --- a/dcb-exe/src/exe/inst/pseudo/move_reg.rs +++ b/dcb-exe/src/exe/inst/pseudo/move_reg.rs @@ -1,30 +1,19 @@ //! Move register instruction // Imports -use crate::exe::inst::{ - basic::{ - alu_imm::AluImmKind, - special::{ - alu_reg::AluRegKind, - shift::{ShiftImmInst, ShiftRegInst}, - AluRegInst, ShiftInst, - }, - AluImmInst, InstIter, SpecialInst, - }, - BasicInst, Register, -}; +use std::convert::TryInto; + +use super::Decodable; +use crate::exe::inst::{basic, InstFmt, InstSize, Register}; /// Move register instruction /// /// Alias for /// ```mips -/// Alias for `{add|addu|sub|subu|and|or|xor|sllv|srlv|srav} $dst, $src, $zr` or -/// `{addi|addiu|andi|ori|xori|sll|srl|sra} $dst, $src, 0` +/// addu $dst, $src, $zr /// ``` #[derive(PartialEq, Eq, Clone, Copy, Debug)] -#[derive(derive_more::Display)] -#[display(fmt = "move {dst}, {src}")] -pub struct MoveRegPseudoInst { +pub struct Inst { /// Destination register pub dst: Register, @@ -32,46 +21,36 @@ pub struct MoveRegPseudoInst { pub src: Register, } -impl MoveRegPseudoInst { - /// Decodes this pseudo instruction - #[must_use] - pub fn decode(iter: InstIter<'_, impl Iterator + Clone>) -> Option { - let peeker = iter.peeker(); - let inst = match peeker.next()?? { - BasicInst::Special( - SpecialInst::Shift( - ShiftInst::Imm(ShiftImmInst { dst, lhs: src, rhs: 0, .. }) | - ShiftInst::Reg(ShiftRegInst { - dst, - lhs: src, - rhs: Register::Zr, - .. - }), - ) | - SpecialInst::Alu(AluRegInst { - dst, - lhs: src, - rhs: Register::Zr, - kind: - AluRegKind::Add | - AluRegKind::AddUnsigned | - AluRegKind::Sub | - AluRegKind::SubUnsigned | - AluRegKind::And | - AluRegKind::Or | - AluRegKind::Xor | - AluRegKind::Nor, - }), - ) | - BasicInst::AluImm(AluImmInst { - dst, - lhs: src, - kind: AluImmKind::Add(0) | AluImmKind::AddUnsigned(0) | AluImmKind::And(0) | AluImmKind::Or(0) | AluImmKind::Xor(0), - }) => Self { dst, src }, - _ => return None, - }; - peeker.apply(); - Some(inst) +impl Decodable for Inst { + fn decode(mut insts: impl Iterator + Clone) -> Option { + match insts.next()?.try_into().ok()? { + basic::alu::Inst::Reg(basic::alu::reg::Inst { + dst, + lhs, + rhs: Register::Zr, + kind: basic::alu::reg::Kind::AddUnsigned, + }) => Some(Self { dst, src: lhs }), + _ => None, + } + } +} + +impl InstSize for Inst { + fn size(&self) -> usize { + 4 + } +} + +impl InstFmt for Inst { + fn mnemonic(&self) -> &'static str { + "move" + } + + fn fmt(&self, _pos: crate::Pos, f: &mut std::fmt::Formatter) -> std::fmt::Result { + let Self { dst, src } = self; + let mnemonic = self.mnemonic(); + + write!(f, "{mnemonic} {dst}, {src}") } } diff --git a/dcb-exe/src/exe/inst/pseudo/nop.rs b/dcb-exe/src/exe/inst/pseudo/nop.rs index 7cb8cc6..947b997 100644 --- a/dcb-exe/src/exe/inst/pseudo/nop.rs +++ b/dcb-exe/src/exe/inst/pseudo/nop.rs @@ -1,9 +1,8 @@ //! Nop // Imports -use crate::exe::inst::{basic, InstFmt, InstSize, Register}; - use super::Decodable; +use crate::exe::inst::{basic, InstFmt, InstSize, Register}; /// No-op ///