Support assignment expressions for registers!

This commit is contained in:
Michel Heily 2019-06-26 16:34:42 +03:00
parent f1f33d8586
commit f45a856835
2 changed files with 27 additions and 17 deletions

View file

@ -158,7 +158,7 @@ impl Debugger {
} }
fn decode_register(&self, s: &str) -> DebuggerResult<usize> { fn decode_reg(&self, s: &str) -> DebuggerResult<usize> {
let reg_names = vec![ let reg_names = vec![
"r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "fp", "ip", "sp", "lr", "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "fp", "ip", "sp", "lr",
"pc"]; "pc"];
@ -169,28 +169,27 @@ impl Debugger {
} }
} }
fn arg_reg(&self, arg: &Value) -> DebuggerResult<u32> { fn val_reg(&self, arg: &Value) -> DebuggerResult<usize> {
match arg { match arg {
Value::Name(reg) => { Value::Name(reg) => {
let reg = self.decode_register(&reg)?; self.decode_reg(&reg)
Ok(self.cpu.get_reg(reg))
}, },
v => Err(DebuggerError::InvalidArgument(format!("expected a number, got {:?}", v))) v => Err(DebuggerError::InvalidArgument(format!("expected a number, got {:?}", v)))
} }
} }
fn arg_number(&self, arg: &Value) -> DebuggerResult<u32> { fn val_number(&self, arg: &Value) -> DebuggerResult<u32> {
match arg { match arg {
Value::Num(n) => Ok(*n), Value::Num(n) => Ok(*n),
v => Err(DebuggerError::InvalidArgument(format!("expected a number, got {:?}", v))) v => Err(DebuggerError::InvalidArgument(format!("expected a number, got {:?}", v)))
} }
} }
fn arg_address(&self, arg: &Value) -> DebuggerResult<u32> { fn val_address(&self, arg: &Value) -> DebuggerResult<u32> {
match arg { match arg {
Value::Num(n) => Ok(*n), Value::Num(n) => Ok(*n),
Value::Name(reg) => { Value::Name(reg) => {
let reg = self.decode_register(&reg)?; let reg = self.decode_reg(&reg)?;
Ok(self.cpu.get_reg(reg)) Ok(self.cpu.get_reg(reg))
} }
v => Err(DebuggerError::InvalidArgument(format!("addr: expected a number or register, got {:?}", v))) v => Err(DebuggerError::InvalidArgument(format!("addr: expected a number or register, got {:?}", v)))
@ -210,20 +209,20 @@ impl Debugger {
"s" | "step" => Ok(Command::SingleStep), "s" | "step" => Ok(Command::SingleStep),
"c" | "continue" => Ok(Command::Continue), "c" | "continue" => Ok(Command::Continue),
"xxd" => { "xxd" => {
let addr = self.arg_address(&args[0])?; let addr = self.val_address(&args[0])?;
let nbytes = self.arg_number(&args[1])?; let nbytes = self.val_number(&args[1])?;
Ok(Command::HexDump(addr, nbytes as usize)) Ok(Command::HexDump(addr, nbytes as usize))
} }
"d" | "disass" => { "d" | "disass" => {
let (addr, n) = match args.len() { let (addr, n) = match args.len() {
2 => { 2 => {
let addr = self.arg_address(&args[0])?; let addr = self.val_address(&args[0])?;
let n = self.arg_number(&args[1])?; let n = self.val_number(&args[1])?;
(addr, n as usize) (addr, n as usize)
} }
1 => { 1 => {
let addr = self.arg_address(&args[0])?; let addr = self.val_address(&args[0])?;
(addr, 10) (addr, 10)
} }
@ -243,7 +242,7 @@ impl Debugger {
"disass <addr>".to_string(), "disass <addr>".to_string(),
)) ))
} else { } else {
let addr = self.arg_address(&args[0])?; let addr = self.val_address(&args[0])?;
Ok(Command::AddBreakpoint(addr)) Ok(Command::AddBreakpoint(addr))
} }
} }
@ -254,6 +253,14 @@ impl Debugger {
} }
} }
fn eval_assignment(&mut self, lvalue: Value, rvalue: Value) -> DebuggerResult<()> {
let lvalue = self.val_reg(&lvalue)?;
let rvalue = self.val_address(&rvalue)?;
self.cpu.set_reg(lvalue, rvalue);
Ok(())
}
fn eval_expr(&mut self, expr: Expr) { fn eval_expr(&mut self, expr: Expr) {
match expr { match expr {
Expr::Command(c, a) => match self.eval_command(c, a) { Expr::Command(c, a) => match self.eval_command(c, a) {
@ -269,7 +276,10 @@ impl Debugger {
} }
Err(e) => println!("{} {:?}", "failed to build command".red(), e), Err(e) => println!("{} {:?}", "failed to build command".red(), e),
}, },
Expr::Assignment(_, _) => unimplemented!("assignments are not implemented"), Expr::Assignment(lvalue, rvalue) => match self.eval_assignment(lvalue, rvalue) {
Err(DebuggerError::InvalidArgument(m)) => println!("{}: {}", "assignment error".red(), m),
_ => ()
}
Expr::Empty => println!("Got empty expr"), Expr::Empty => println!("Got empty expr"),
} }
} }

View file

@ -4,10 +4,10 @@ use nom;
use nom::branch::alt; use nom::branch::alt;
use nom::bytes::complete::{tag, take_while_m_n}; use nom::bytes::complete::{tag, take_while_m_n};
use nom::character::complete::{alphanumeric1, char, digit1, multispace0, multispace1}; use nom::character::complete::{alphanumeric1, char, digit1, multispace0, multispace1};
use nom::combinator::{cut, map, map_res, opt}; use nom::combinator::{map, map_res};
use nom::error::{context, convert_error, ParseError, VerboseError}; use nom::error::{context, convert_error, ParseError, VerboseError};
use nom::multi::{many0, separated_list}; use nom::multi::separated_list;
use nom::sequence::{delimited, preceded, separated_pair, terminated, tuple}; use nom::sequence::{preceded, separated_pair, terminated, tuple};
use nom::IResult; use nom::IResult;
use super::{DebuggerError, DebuggerResult}; use super::{DebuggerError, DebuggerResult};