Improve Debug and Display implementations
This commit is contained in:
parent
49df6c9ed9
commit
d5daaa0e87
@ -44,7 +44,7 @@ pub struct InstructionHolder {
|
||||
pub(crate) data: InstructionData,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
#[derive(Clone)]
|
||||
pub struct Builder {
|
||||
modules: Rc<RefCell<Vec<ModuleHolder>>>,
|
||||
}
|
||||
|
@ -1,11 +1,17 @@
|
||||
use std::fmt::Debug;
|
||||
use std::fmt::{Debug, Write};
|
||||
|
||||
use crate::{CmpPredicate, InstructionData, InstructionKind, TerminatorKind, builder::*};
|
||||
|
||||
impl Debug for Builder {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
f.debug_list().entries(self.get_modules().borrow().iter());
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl Debug for ModuleHolder {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
f.debug_tuple(&format!("Module({})", self.data.name))
|
||||
.field(&self.value)
|
||||
f.debug_tuple(&format!("{}({:#?}) ", self.data.name, self.value))
|
||||
.field(&self.functions)
|
||||
.finish()
|
||||
}
|
||||
@ -14,7 +20,7 @@ impl Debug for ModuleHolder {
|
||||
impl Debug for FunctionHolder {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
f.debug_tuple(&format!(
|
||||
"{}({:?}) -> {:?}",
|
||||
"{}({:?}) -> {:?} ",
|
||||
self.data.name, self.data.params, self.data.ret
|
||||
))
|
||||
.field(&self.blocks)
|
||||
@ -24,8 +30,7 @@ impl Debug for FunctionHolder {
|
||||
|
||||
impl Debug for BlockHolder {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
f.debug_tuple(&format!("Block({})", self.data.name))
|
||||
.field(&self.value)
|
||||
f.debug_tuple(&format!("{}[{:?}]", &self.data.name, &self.value))
|
||||
.field(&self.instructions)
|
||||
.field(&self.data.terminator)
|
||||
.finish()
|
||||
@ -34,7 +39,9 @@ impl Debug for BlockHolder {
|
||||
|
||||
impl Debug for InstructionHolder {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "{:?} = {:?}", &self.value, &self.data)
|
||||
self.value.fmt(f)?;
|
||||
f.write_str(" = ")?;
|
||||
self.data.fmt(f)
|
||||
}
|
||||
}
|
||||
|
||||
@ -46,19 +53,19 @@ impl Debug for InstructionData {
|
||||
|
||||
impl Debug for ModuleValue {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "M[{}]", &self.0)
|
||||
write!(f, "M[{:0>2}]", self.0)
|
||||
}
|
||||
}
|
||||
|
||||
impl Debug for FunctionValue {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "F[{}, {}]", &self.0.0, &self.1,)
|
||||
write!(f, "F[{:0>2}-{:0>2}]", &self.0.0, self.1)
|
||||
}
|
||||
}
|
||||
|
||||
impl Debug for BlockValue {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "B[{}, {}, {}]", &self.0.0.0, &self.0.1, self.1)
|
||||
write!(f, "B[{:0>2}-{:0>2}-{:0>2}]", &self.0.0.0, &self.0.1, self.1)
|
||||
}
|
||||
}
|
||||
|
||||
@ -66,7 +73,7 @@ impl Debug for InstructionValue {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"I<{}-{}-{}-{}>",
|
||||
"I[{:0>2}-{:0>2}-{:0>2}-{:0>2}]",
|
||||
&self.0.0.0.0, &self.0.0.1, &self.0.1, self.1
|
||||
)
|
||||
}
|
||||
@ -75,17 +82,41 @@ impl Debug for InstructionValue {
|
||||
impl Debug for InstructionKind {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Param(nth) => write!(f, "Param({})", &nth),
|
||||
Self::Constant(c) => write!(f, "{:?}", &c),
|
||||
Self::Add(lhs, rhs) => write!(f, "{:?} + {:?}", &lhs, &rhs),
|
||||
Self::Sub(lhs, rhs) => write!(f, "{:?} + {:?}", &lhs, &rhs),
|
||||
Self::Phi(val) => write!(f, "Phi: {:?}", &val),
|
||||
Self::ICmp(cmp, lhs, rhs) => write!(f, "{:?} {:?} {:?}", &lhs, &cmp, &rhs),
|
||||
Self::FunctionCall(fun, params) => write!(f, "{:?}({:?})", &fun, ¶ms),
|
||||
Self::Param(nth) => fmt_call(f, &"Param", &nth),
|
||||
Self::Constant(c) => c.fmt(f),
|
||||
Self::Add(lhs, rhs) => fmt_binop(f, lhs, &"+", rhs),
|
||||
Self::Sub(lhs, rhs) => fmt_binop(f, lhs, &"-", rhs),
|
||||
Self::Phi(val) => fmt_call(f, &"Phi", &val),
|
||||
Self::ICmp(cmp, lhs, rhs) => fmt_binop(f, lhs, cmp, rhs),
|
||||
Self::FunctionCall(fun, params) => fmt_call(f, fun, params),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn fmt_binop(
|
||||
f: &mut std::fmt::Formatter<'_>,
|
||||
lhs: &impl std::fmt::Debug,
|
||||
op: &impl std::fmt::Debug,
|
||||
rhs: &impl std::fmt::Debug,
|
||||
) -> std::fmt::Result {
|
||||
lhs.fmt(f)?;
|
||||
f.write_char(' ')?;
|
||||
op.fmt(f)?;
|
||||
f.write_char(' ')?;
|
||||
rhs.fmt(f)
|
||||
}
|
||||
|
||||
fn fmt_call(
|
||||
f: &mut std::fmt::Formatter<'_>,
|
||||
fun: &impl std::fmt::Debug,
|
||||
params: &impl std::fmt::Debug,
|
||||
) -> std::fmt::Result {
|
||||
fun.fmt(f)?;
|
||||
f.write_char('(')?;
|
||||
params.fmt(f)?;
|
||||
f.write_char(')')
|
||||
}
|
||||
|
||||
impl Debug for CmpPredicate {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
@ -102,9 +133,23 @@ impl Debug for CmpPredicate {
|
||||
impl Debug for TerminatorKind {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Ret(val) => write!(f, "Ret {:?}", &val),
|
||||
Self::Branch(val) => write!(f, "Br {:?}", &val),
|
||||
Self::CondBr(cond, b1, b2) => write!(f, "CondBr {:?} ? {:?} : {:?}", &cond, &b1, &b2),
|
||||
Self::Ret(val) => {
|
||||
write!(f, "Ret ")?;
|
||||
val.fmt(f)
|
||||
}
|
||||
Self::Branch(val) => {
|
||||
write!(f, "Br ")?;
|
||||
val.fmt(f)
|
||||
}
|
||||
Self::CondBr(cond, b1, b2) => {
|
||||
write!(f, "CondBr ")?;
|
||||
cond.fmt(f)?;
|
||||
write!(f, " ? ")?;
|
||||
b1.fmt(f)?;
|
||||
write!(f, " : ")?;
|
||||
b2.fmt(f)?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -91,7 +91,7 @@ pub struct IfExpression(
|
||||
pub struct LetStatement(pub String, pub Option<Type>, pub Expression, pub TokenRange);
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct ImportStatement(Vec<String>, pub TokenRange);
|
||||
pub struct ImportStatement(pub Vec<String>, pub TokenRange);
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct FunctionDefinition(pub FunctionSignature, pub Block, pub TokenRange);
|
||||
|
@ -7,6 +7,7 @@ mod ast;
|
||||
mod codegen;
|
||||
mod lexer;
|
||||
pub mod mir;
|
||||
mod pad_adapter;
|
||||
mod token_stream;
|
||||
mod util;
|
||||
|
||||
@ -39,7 +40,6 @@ pub fn compile(source: &str) -> Result<String, ReidError> {
|
||||
|
||||
while !matches!(token_stream.peek().unwrap_or(Token::Eof), Token::Eof) {
|
||||
let statement = token_stream.parse::<TopLevelStatement>()?;
|
||||
dbg!(&statement);
|
||||
statements.push(statement);
|
||||
}
|
||||
|
||||
@ -51,17 +51,15 @@ pub fn compile(source: &str) -> Result<String, ReidError> {
|
||||
dbg!(&ast_module);
|
||||
let mut mir_context = mir::Context::from(vec![ast_module]);
|
||||
|
||||
dbg!(&mir_context);
|
||||
|
||||
let state = mir_context.pass(&mut TypeCheck {});
|
||||
dbg!(&mir_context);
|
||||
dbg!(&state);
|
||||
|
||||
println!("{}", &mir_context);
|
||||
|
||||
if !state.errors.is_empty() {
|
||||
return Err(ReidError::TypeCheckErrors(state.errors));
|
||||
}
|
||||
|
||||
dbg!(&mir_context);
|
||||
|
||||
let mut context = Context::new();
|
||||
let codegen_modules = mir_context.codegen(&mut context);
|
||||
|
||||
|
200
reid/src/mir/display.rs
Normal file
200
reid/src/mir/display.rs
Normal file
@ -0,0 +1,200 @@
|
||||
use std::fmt::{write, Debug, Display, Write};
|
||||
|
||||
use crate::pad_adapter::PadAdapter;
|
||||
|
||||
use super::*;
|
||||
|
||||
impl Display for Context {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
for module in &self.modules {
|
||||
Display::fmt(&module, f)?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Module {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
writeln!(f, "Module({}) {{", self.name)?;
|
||||
|
||||
let mut state = Default::default();
|
||||
let mut inner_f = PadAdapter::wrap(f, &mut state);
|
||||
|
||||
for import in &self.imports {
|
||||
writeln!(inner_f, "{}", import)?;
|
||||
}
|
||||
for fun in &self.functions {
|
||||
writeln!(inner_f, "{}", fun)?;
|
||||
}
|
||||
writeln!(f, "}}")
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Import {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "import {}", self.0)
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for FunctionDefinition {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"fn {}({}) -> {} ",
|
||||
self.name,
|
||||
self.parameters
|
||||
.iter()
|
||||
.map(|(n, t)| format!("{}: {}", n, t))
|
||||
.collect::<Vec<_>>()
|
||||
.join(", "),
|
||||
self.return_type
|
||||
)?;
|
||||
Display::fmt(&self.kind, f)
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for FunctionDefinitionKind {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Local(block, _) => {
|
||||
write!(f, "{}", block)?;
|
||||
Ok(())
|
||||
}
|
||||
Self::Extern => write!(f, "<External>"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Block {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
writeln!(f, "{{")?;
|
||||
let mut state = Default::default();
|
||||
let mut inner_f = PadAdapter::wrap(f, &mut state);
|
||||
for statement in &self.statements {
|
||||
write!(inner_f, "{}", statement)?;
|
||||
}
|
||||
if let Some(ret) = &self.return_expression {
|
||||
match ret.0 {
|
||||
ReturnKind::Hard => writeln!(inner_f, "Return(Hard): {}", ret.1),
|
||||
ReturnKind::Soft => writeln!(inner_f, "Return(Hard): {}", ret.1),
|
||||
}?;
|
||||
} else {
|
||||
writeln!(inner_f, "No Return")?;
|
||||
}
|
||||
writeln!(f, "}}")
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Statement {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
writeln!(f, "{}", self.0)
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for StmtKind {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Let(var, block) => write!(f, "let {} = {}", var, block),
|
||||
Self::Import(n) => write!(f, "import {}", n),
|
||||
Self::Expression(exp) => Display::fmt(exp, f),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Expression {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
Display::fmt(&self.0, f)
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for ExprKind {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::Variable(var) => Display::fmt(var, f),
|
||||
Self::Literal(lit) => Display::fmt(lit, f),
|
||||
Self::BinOp(op, lhs, rhs) => write!(f, "{} {} {}", lhs, op, rhs),
|
||||
Self::FunctionCall(fc) => Display::fmt(fc, f),
|
||||
Self::If(if_exp) => Display::fmt(&if_exp, f),
|
||||
Self::Block(block) => Display::fmt(block, f),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for IfExpression {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "if {} ", self.0)?;
|
||||
Display::fmt(&self.1, f)?;
|
||||
if let Some(e) = &self.2 {
|
||||
Display::fmt(&e, f)?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for FunctionCall {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "{}<{}>(", self.name, self.return_type)?;
|
||||
for (i, param) in self.parameters.iter().enumerate() {
|
||||
Display::fmt(param, f)?;
|
||||
if i < (self.parameters.len() - 1) {
|
||||
write!(f, ", ")?;
|
||||
}
|
||||
}
|
||||
write!(f, ")")
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for VariableReference {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "v(\"{}\", {})", &self.1, &self.0)
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Literal {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
Self::I8(val) => write!(f, "{}i8", val),
|
||||
Self::I16(val) => write!(f, "{}i16", val),
|
||||
Self::I32(val) => write!(f, "{}i32", val),
|
||||
Self::I64(val) => write!(f, "{}i64", val),
|
||||
Self::I128(val) => write!(f, "{}i128", val),
|
||||
Self::U8(val) => write!(f, "{}u8", val),
|
||||
Self::U16(val) => write!(f, "{}u16", val),
|
||||
Self::U32(val) => write!(f, "{}u32", val),
|
||||
Self::U64(val) => write!(f, "{}u64", val),
|
||||
Self::U128(val) => write!(f, "{}u128", val),
|
||||
Self::Vague(val) => val.fmt(f),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for BinaryOperator {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
BinaryOperator::Add => write!(f, "+"),
|
||||
BinaryOperator::Minus => write!(f, "-"),
|
||||
BinaryOperator::Mult => write!(f, "*"),
|
||||
BinaryOperator::And => write!(f, "&&"),
|
||||
BinaryOperator::Logic(op) => Display::fmt(op, f),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for LogicOperator {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
match self {
|
||||
LogicOperator::LT => write!(f, "<"),
|
||||
LogicOperator::LE => write!(f, "<="),
|
||||
LogicOperator::GT => write!(f, ">"),
|
||||
LogicOperator::GE => write!(f, ">="),
|
||||
LogicOperator::EQ => write!(f, "=="),
|
||||
LogicOperator::NE => write!(f, "!="),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Display for Metadata {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "{:?}", self.range)
|
||||
}
|
||||
}
|
@ -3,21 +3,16 @@
|
||||
/// type-checked beforehand.
|
||||
use crate::token_stream::TokenRange;
|
||||
|
||||
mod display;
|
||||
pub mod pass;
|
||||
pub mod typecheck;
|
||||
pub mod types;
|
||||
|
||||
#[derive(Default, Debug, Clone, Copy)]
|
||||
#[derive(Debug, Default, Clone, Copy)]
|
||||
pub struct Metadata {
|
||||
pub range: TokenRange,
|
||||
}
|
||||
|
||||
impl std::fmt::Display for Metadata {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
write!(f, "{:?}", self.range)
|
||||
}
|
||||
}
|
||||
|
||||
impl std::ops::Add for Metadata {
|
||||
type Output = Metadata;
|
||||
|
||||
|
@ -141,8 +141,6 @@ impl Expression {
|
||||
) -> Result<TypeKind, ErrorKind> {
|
||||
match &mut self.0 {
|
||||
ExprKind::Variable(var_ref) => {
|
||||
dbg!(&state.scope);
|
||||
|
||||
let existing = state.or_else(
|
||||
state
|
||||
.scope
|
||||
|
72
reid/src/pad_adapter.rs
Normal file
72
reid/src/pad_adapter.rs
Normal file
@ -0,0 +1,72 @@
|
||||
// Copyright (c) The Rust Project Contributors
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any
|
||||
// person obtaining a copy of this software and associated
|
||||
// documentation files (the "Software"), to deal in the
|
||||
// Software without restriction, including without
|
||||
// limitation the rights to use, copy, modify, merge,
|
||||
// publish, distribute, sublicense, and/or sell copies of
|
||||
// the Software, and to permit persons to whom the Software
|
||||
// is furnished to do so, subject to the following
|
||||
// conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice
|
||||
// shall be included in all copies or substantial portions
|
||||
// of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF
|
||||
// ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
|
||||
// TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
|
||||
// PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
|
||||
// SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
||||
// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR
|
||||
// IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
use std::fmt;
|
||||
|
||||
pub struct PadAdapter<'buf, 'state> {
|
||||
buf: &'buf mut (dyn fmt::Write + 'buf),
|
||||
state: &'state mut PadAdapterState,
|
||||
}
|
||||
|
||||
pub struct PadAdapterState {
|
||||
on_newline: bool,
|
||||
}
|
||||
|
||||
impl Default for PadAdapterState {
|
||||
fn default() -> Self {
|
||||
PadAdapterState { on_newline: true }
|
||||
}
|
||||
}
|
||||
|
||||
impl<'buf, 'state> PadAdapter<'buf, 'state> {
|
||||
pub fn wrap<'slot, 'fmt: 'buf + 'slot>(
|
||||
fmt: &'fmt mut fmt::Formatter<'_>,
|
||||
state: &'state mut PadAdapterState,
|
||||
) -> Self {
|
||||
PadAdapter { buf: fmt, state }
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Write for PadAdapter<'_, '_> {
|
||||
fn write_str(&mut self, s: &str) -> fmt::Result {
|
||||
for s in s.split_inclusive('\n') {
|
||||
if self.state.on_newline {
|
||||
self.buf.write_str(" ")?;
|
||||
}
|
||||
self.state.on_newline = s.ends_with('\n');
|
||||
self.buf.write_str(s)?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn write_char(&mut self, c: char) -> fmt::Result {
|
||||
if self.state.on_newline {
|
||||
self.buf.write_str(" ")?;
|
||||
}
|
||||
self.state.on_newline = c == '\n';
|
||||
self.buf.write_char(c)
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user