From f7fcc6aa17b5528e2cecce40d36fd37840f80dd1 Mon Sep 17 00:00:00 2001 From: dave caruso Date: Fri, 2 Feb 2024 22:30:49 -0800 Subject: [PATCH] chore: rename tokenizer::Loc -> log::Range (#15) --- Cargo.lock | 82 ++++++++++++++++- Cargo.toml | 4 +- crates/ast/Cargo.toml | 3 +- crates/ast/ast.rs | 36 ++++---- crates/ast/types.rs | 74 ---------------- crates/cli/Cargo.toml | 1 + crates/js_ast/Cargo.toml | 3 +- .../js_ast/convert/block_convert_context.rs | 16 ++-- crates/js_ast/convert/convert_valid_block.rs | 13 ++- crates/js_ast/convert/convert_valid_expr.rs | 28 +++--- crates/js_ast/convert/convert_valid_if.rs | 12 +-- .../js_ast/convert/convert_valid_statement.rs | 4 +- crates/js_ast/convert/hoist_block_to_expr.rs | 10 +-- .../js_ast/convert/hoist_block_to_js_block.rs | 12 +-- crates/js_ast/convert/hoist_expr.rs | 24 ++--- crates/js_ast/convert/hoist_if.rs | 18 ++-- .../js_ast/convert/is_valid_js_expression.rs | 2 +- crates/js_ast/convert/process_function.rs | 10 +-- crates/js_ast/convert/process_statement.rs | 12 +-- crates/js_ast/convert/side_effects.rs | 2 +- crates/js_ast/js_ast.rs | 28 +++--- crates/log/Cargo.toml | 11 +++ crates/log/log.rs | 88 +++++++++++++++++++ crates/parser/Cargo.toml | 1 + crates/parser/parse_declaration.rs | 5 +- crates/parser/parse_doc_comment.rs | 5 +- crates/parser/parse_expr.rs | 4 +- crates/parser/parse_expr_basic.rs | 37 ++++---- crates/parser/parse_expr_if.rs | 15 ++-- crates/parser/parse_fn_declaration.rs | 7 +- crates/parser/parse_statement.rs | 4 +- crates/parser/parser.rs | 15 ++-- crates/tokenizer/Cargo.toml | 2 + crates/tokenizer/tokenizer.rs | 29 +----- 34 files changed, 362 insertions(+), 255 deletions(-) create mode 100644 crates/log/Cargo.toml create mode 100644 crates/log/log.rs diff --git a/Cargo.lock b/Cargo.lock index e11d7608f4d0b1da5e46afd069efbe460f5c5b0c..bc884459d74ada74428241bd211efc2c04a4dda8 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -69,6 +69,7 @@ dependencies = [ name = "ast" version = "0.1.0" dependencies = [ + "log", "miette", "num", "thiserror", @@ -174,6 +175,7 @@ dependencies = [ "clap", "js_ast", "js_printer", + "log", "miette", "parser", "sema", @@ -197,6 +199,15 @@ dependencies = [ "windows-sys", ] +[[package]] +name = "form_urlencoded" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e13624c2627564efccf4934284bdd98cbaa14e79b0b5a141218e507b3a823456" +dependencies = [ + "percent-encoding", +] + [[package]] name = "gimli" version = "0.28.1" @@ -215,6 +226,16 @@ version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d77f7ec81a6d05a3abb01ab6eb7590f6083d08449fe5a1c8b1e620283546ccb7" +[[package]] +name = "idna" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "634d9b1461af396cad843f47fdba5597a4f9e6ddd4bfb6ff5d85028c25cb12f6" +dependencies = [ + "unicode-bidi", + "unicode-normalization", +] + [[package]] name = "is-terminal" version = "0.4.10" @@ -237,11 +258,10 @@ name = "js_ast" version = "0.1.0" dependencies = [ "ast", + "log", "miette", "num", - "parser", "thiserror", - "tokenizer", ] [[package]] @@ -266,6 +286,15 @@ version = "0.4.12" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c4cd1a83af159aa67994778be9070f0ae1bd732942279cabb14f86f986a21456" +[[package]] +name = "log" +version = "0.0.0" +dependencies = [ + "miette", + "thiserror", + "url", +] + [[package]] name = "memchr" version = "2.7.1" @@ -415,12 +444,19 @@ name = "parser" version = "0.1.0" dependencies = [ "ast", + "log", "miette", "num", "thiserror", "tokenizer", ] +[[package]] +name = "percent-encoding" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" + [[package]] name = "proc-macro2" version = "1.0.76" @@ -560,14 +596,36 @@ dependencies = [ "syn", ] +[[package]] +name = "tinyvec" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" +dependencies = [ + "tinyvec_macros", +] + +[[package]] +name = "tinyvec_macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" + [[package]] name = "tokenizer" version = "0.1.0" dependencies = [ + "log", "miette", "thiserror", ] +[[package]] +name = "unicode-bidi" +version = "0.3.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08f95100a766bf4f8f28f90d77e0a5461bbdb219042e7679bebe79004fed8d75" + [[package]] name = "unicode-ident" version = "1.0.12" @@ -580,12 +638,32 @@ version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3b09c83c3c29d37506a3e260c08c03743a6bb66a9cd432c6934ab501a190571f" +[[package]] +name = "unicode-normalization" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" +dependencies = [ + "tinyvec", +] + [[package]] name = "unicode-width" version = "0.1.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e51733f11c9c4f72aa0c160008246859e340b00807569a0da0e7a1079b27ba85" +[[package]] +name = "url" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31e6302e3bb753d46e83516cae55ae196fc0c309407cf11ab35cc51a4c2a4633" +dependencies = [ + "form_urlencoded", + "idna", + "percent-encoding", +] + [[package]] name = "utf8parse" version = "0.2.1" diff --git a/Cargo.toml b/Cargo.toml index a1fb3c69c966fc3a4eeefa9afb84d0c02ba31b08..b0fa3a900bc6c3c38e33d6b3e6aa87a394d8667c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -9,11 +9,12 @@ repository = "https://github.com/lino-levan/blight" resolver = "2" members = [ "crates/ast", - "crates/sema", "crates/cli", "crates/js_ast", "crates/js_printer", + "crates/log", "crates/parser", + "crates/sema", "crates/tokenizer", ] @@ -22,3 +23,4 @@ clap = { version = "4.4.12", features = ["derive"] } miette = { version = "5.10.0", features = ["fancy"] } thiserror = "1.0.53" num = "0.4.1" +url = "2.2.2" diff --git a/crates/ast/Cargo.toml b/crates/ast/Cargo.toml index fc7837e1d94befad96581f8d202330bb79e732d8..fe49e948853cee5c92a9a0ca399f13ed8b2ec4ed 100644 --- a/crates/ast/Cargo.toml +++ b/crates/ast/Cargo.toml @@ -11,4 +11,5 @@ miette.workspace = true thiserror.workspace = true num.workspace = true -tokenizer = { path = "../tokenizer" } +tokenizer = { path = "../tokenizer" } # Do not depend on the tokenizer +log = { path = "../log" } diff --git a/crates/ast/ast.rs b/crates/ast/ast.rs index d8c2939268152f08a1e1253f5150076564eaa608..f97d109f4f0d4c0f85e9e1bc2a85c3f185c3a74a 100644 --- a/crates/ast/ast.rs +++ b/crates/ast/ast.rs @@ -1,9 +1,7 @@ -use tokenizer::Loc; +use log::Range; -use crate::{ - types::{Literal, Type}, - BinaryOperator, UnaryOperator, -}; +use crate::types::{Literal, Type}; +use crate::{BinaryOperator, UnaryOperator}; #[derive(Debug, Clone)] pub enum BuiltinId { @@ -36,7 +34,7 @@ pub struct VarDecl { pub init: Expr, pub is_constant: bool, pub is_pub: bool, - pub loc: Loc, + pub range: Range, pub comment: Option, } @@ -47,27 +45,31 @@ pub struct FnDecl { pub params: Vec, pub body: Expr, pub is_pub: bool, - pub loc: Loc, + pub range: Range, pub comment: Option, } #[derive(Debug, Clone)] pub struct Expr { pub data: ExprData, - pub loc: Loc, + pub range: Range, pub comment: Option, } impl Expr { - pub fn new(data: ExprData, loc: Loc, comment: Option) -> Self { - Self { data, loc, comment } + pub fn new(data: ExprData, range: Range, comment: Option) -> Self { + Self { + data, + range, + comment, + } } } #[derive(Debug, Clone)] pub struct DocComment { pub data: String, - pub loc: Loc, + pub range: Range, } #[derive(Debug, PartialEq, Clone)] @@ -86,10 +88,10 @@ impl Comment { result } - pub fn to_doc_comment(self, loc: Loc) -> DocComment { + pub fn to_doc_comment(self, range: Range) -> DocComment { DocComment { data: self.data, - loc, + range, } } } @@ -113,21 +115,21 @@ impl DocComment { } #[derive(Debug, Clone)] -pub struct BlockWithLoc { +pub struct BlockWithRange { pub block: Block, - pub loc: Loc, + pub range: Range, } #[derive(Debug, Clone)] pub struct If { pub condition: Box, - pub yes: BlockWithLoc, + pub yes: BlockWithRange, pub no: Option, } #[derive(Debug, Clone)] pub enum BlockOrIf { - Block(BlockWithLoc), + Block(BlockWithRange), If(Box), } diff --git a/crates/ast/types.rs b/crates/ast/types.rs index e65220300f5e78fceec6f68eef1fdf5ef51dc984..d1afb35a3848d2331616da58398410b440a2af6c 100644 --- a/crates/ast/types.rs +++ b/crates/ast/types.rs @@ -120,80 +120,6 @@ pub fn merge_types(a: Type, b: Type) -> Result { Err(TypeError::new(format!("TODO: Implement type merging for {} and {}", a, b)).into()) } -// pub fn coerce_type(target: Type, source: Type) -> Result { -// match source { -// Type::Any => return Ok(target), -// _ => {} -// } -// match target { -// Type::Infer => Ok(source), -// Type::Any => Ok(Type::Any), - -// Type::Literal(_) => unreachable!(), - -// Type::Int => match source { -// Type::Int => Ok(Type::Int), -// Type::Float => Ok(Type::Int), -// Type::Literal(value) => { -// if value.fract() != 0.0 { -// Err( -// TypeError::new(format!("Numeric Literal '{}' is not an integer", value)) -// .into(), -// ) -// } else if value > i32::MAX.into() || value < i32::MIN.into() { -// Err(TypeError::new(format!( -// "Numeric Literal '{}' is out of range for an integer ({}..{})", -// value, -// i32::MIN, -// i32::MAX -// )) -// .into()) -// } else { -// Ok(Type::Int) -// } -// } -// t => Err(TypeError::new(format!("Cannot coerce {} to int", t)).into()), -// }, - -// Type::BigInt => match source { -// Type::Int => Ok(Type::Int), -// Type::Float => Ok(Type::Int), -// Type::NumberLiteral(value) => { -// if value.fract() != 0.0 { -// Err( -// TypeError::new(format!("Numeric Literal '{}' is not an integer", value)) -// .into(), -// ) -// } else { -// Ok(Type::BigInt) -// } -// } -// t => Err(TypeError::new(format!("Cannot coerce {} to int", t)).into()), -// }, - -// Type::Float => match source { -// Type::Int => Ok(Type::Float), -// Type::Float => Ok(Type::Float), -// Type::NumberLiteral(value) => { -// if value.fract() == 0.0 && value <= f64::MAX.into() && value >= f64::MIN.into() { -// Ok(Type::Float) -// } else { -// Err(TypeError::new(format!("Numeric Literal")).into()) -// } -// } -// _ => Err(TypeError::new(format!("Cannot coerce int to float")).into()), -// }, - -// other => { -// if other == source { -// Ok(other) -// } else { -// Err(TypeError::new(format!("Cannot coerce {} to {}", source, other)).into()) -// } -// } -// } -// } - #[derive(Error, Diagnostic, Debug)] #[error("TypeError")] pub struct TypeError { diff --git a/crates/cli/Cargo.toml b/crates/cli/Cargo.toml index 00920ac78a6265cf80755f257b26c88e56c2d8dd..1bd4c0904e6ee693867b2cde0353948f1fbb46fe 100644 --- a/crates/cli/Cargo.toml +++ b/crates/cli/Cargo.toml @@ -18,3 +18,4 @@ parser = { path = "../parser" } js_ast = { path = "../js_ast" } js_printer = { path = "../js_printer" } sema = { path = "../sema" } +log = { path = "../log" } diff --git a/crates/js_ast/Cargo.toml b/crates/js_ast/Cargo.toml index 68087cf32a5792a7ae7f6ecac80399eb5883fdba..586042092d15e767b3355095c3459c3f209ad1ce 100644 --- a/crates/js_ast/Cargo.toml +++ b/crates/js_ast/Cargo.toml @@ -12,5 +12,4 @@ thiserror.workspace = true num.workspace = true ast = { path = "../ast" } -tokenizer = { path = "../tokenizer" } # TODO: move Loc out of the tokenizer -parser = { path = "../parser" } # TODO: move Loc out of the tokenizer +log = { path = "../log" } diff --git a/crates/js_ast/convert/block_convert_context.rs b/crates/js_ast/convert/block_convert_context.rs index de41e77cae5f13c2d98b6215e925fd637a9bebb6..01abce4a2631eabad654d1e31c99a6c8e37d4e30 100644 --- a/crates/js_ast/convert/block_convert_context.rs +++ b/crates/js_ast/convert/block_convert_context.rs @@ -1,8 +1,8 @@ use crate::js_ast::*; use ast::*; +use log::Range; use std::collections::{HashMap, HashSet}; use std::vec; -use tokenizer::Loc; use super::tree_shake_statement_list; @@ -198,33 +198,33 @@ impl BlockConvertContext { } } -pub fn new_js_assignment_statement(expr: JsExpr, target: String, loc: Loc) -> JsStatement { +pub fn new_js_assignment_statement(expr: JsExpr, target: String, range: Range) -> JsStatement { JsStatement::new( - JsStatementData::Expression(new_js_assignment_expr(expr, target, loc.clone())), - loc, + JsStatementData::Expression(new_js_assignment_expr(expr, target, range.clone())), + range, None, ) } -pub fn new_js_assignment_expr(expr: JsExpr, target: String, loc: Loc) -> JsExpr { +pub fn new_js_assignment_expr(expr: JsExpr, target: String, range: Range) -> JsExpr { JsExpr::new( JsExprData::Binary { op: BinaryOperator::Assign, left: Box::new(JsExpr::new( JsExprData::Identifier(target), - loc.clone(), + range.clone(), None, )), right: Box::new(expr), }, - loc, + range, None, ) } impl Into for BlockConvertContext { fn into(self) -> JsBlock { - JsBlock::new(self.into(), Loc::EMPTY) + JsBlock::new(self.into(), Range::EMPTY) } } diff --git a/crates/js_ast/convert/convert_valid_block.rs b/crates/js_ast/convert/convert_valid_block.rs index dcfb761cb34985d1376b79ebf13ddd843c6ef94e..29ef59c7ccf294682f376ea3afe77d113592ed4f 100644 --- a/crates/js_ast/convert/convert_valid_block.rs +++ b/crates/js_ast/convert/convert_valid_block.rs @@ -3,18 +3,18 @@ use super::BlockConvertContext; use super::IsValidJSExpression; use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; -pub fn convert_valid_block(ctx: &mut BlockConvertContext, block: Block, loc: Loc) -> JsExpr { +pub fn convert_valid_block(ctx: &mut BlockConvertContext, block: Block, range: Range) -> JsExpr { debug_assert!( block.is_valid_js_expression(), "must call convert_valid_block with valid js expression" ); let len = block.statements.len(); - let loc = loc; + let range = range; let block_expr = match len { - 0 => JsExpr::new(JsExprData::Null, loc.clone(), None), + 0 => JsExpr::new(JsExprData::Null, range.clone(), None), // a block expression with a single expression is just that expression 1 => convert_valid_statement_to_expr(ctx, block.statements.into_iter().next().unwrap()), // Since blocks are not valid expressions in JS, we create a @@ -24,14 +24,13 @@ pub fn convert_valid_block(ctx: &mut BlockConvertContext, block: Block, loc: Loc for statement in block.statements.into_iter() { items.push(convert_valid_statement_to_expr(ctx, statement)); } - JsExpr::new(JsExprData::Comma { items }, loc.clone(), None) + JsExpr::new(JsExprData::Comma { items }, range.clone(), None) } - _ => todo!(), }; // a block without implicit return is to be type void, so we wrap in a void expression if !block.has_implicit_return && len > 0 { - JsExpr::new(JsExprData::Void(Box::new(block_expr)), loc, None) + JsExpr::new(JsExprData::Void(Box::new(block_expr)), range, None) } else { block_expr } diff --git a/crates/js_ast/convert/convert_valid_expr.rs b/crates/js_ast/convert/convert_valid_expr.rs index 8ba30c694c43c60d8c543c4b64be40ac6c7a32c6..3e6c29e1d557d6ec835854d34225a21979192e0a 100644 --- a/crates/js_ast/convert/convert_valid_expr.rs +++ b/crates/js_ast/convert/convert_valid_expr.rs @@ -16,28 +16,28 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { "must call convert_valid_expr with valid js expression (use hoist instead)" ); - let loc = expr.loc; + let range = expr.range; let comment = expr.comment; match expr.data { ExprData::Identifier(str) => JsExpr::new( JsExprData::Identifier(ctx.remap_identifier(&str)), - loc, + range, comment, ), ExprData::Literal(Literal::Bool(value)) => { - JsExpr::new(JsExprData::Bool(value), loc, comment) + JsExpr::new(JsExprData::Bool(value), range, comment) } ExprData::Literal(Literal::Number(value)) => { - JsExpr::new(JsExprData::Number(value), loc, comment) + JsExpr::new(JsExprData::Number(value), range, comment) } ExprData::Literal(Literal::String(value)) => { - JsExpr::new(JsExprData::String(value), loc, comment) + JsExpr::new(JsExprData::String(value), range, comment) } - ExprData::Literal(Literal::Void) => JsExpr::new(JsExprData::Null, loc, comment), + ExprData::Literal(Literal::Void) => JsExpr::new(JsExprData::Null, range, comment), - ExprData::Block(block) => convert_valid_block(ctx, block, loc), + ExprData::Block(block) => convert_valid_block(ctx, block, range), ExprData::Binary { op, left, right } => { let left = convert_valid_expr(ctx, *left); @@ -48,7 +48,7 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { left: Box::new(left), right: Box::new(right), }, - loc, + range, comment, ) } @@ -59,12 +59,12 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { op, value: Box::new(value), }, - loc, + range, comment, ) } ExprData::Fn { body, params, .. } => { - process_function_to_arrow(ctx, *body, params, loc, comment) + process_function_to_arrow(ctx, *body, params, range, comment) } ExprData::Builtin { id, arguments } => match id { BuiltinId::Raw => { @@ -74,10 +74,10 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { ExprData::Literal(Literal::String(s)) => s, _ => panic!("raw expects a string"), }; - JsExpr::new(JsExprData::Raw(str), loc, comment) + JsExpr::new(JsExprData::Raw(str), range, comment) } }, - ExprData::If(expr) => convert_valid_if(ctx, expr, loc, comment), + ExprData::If(expr) => convert_valid_if(ctx, expr, range, comment), ExprData::Call { base, arguments } => { let base = convert_valid_expr(ctx, *base); @@ -90,7 +90,7 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { base: Box::new(base), arguments, }, - loc, + range, comment, ) } @@ -106,7 +106,7 @@ pub fn convert_valid_expr(ctx: &mut BlockConvertContext, expr: Expr) -> JsExpr { index: Box::new(convert_valid_expr(ctx, *field)), }, }, - loc, + range, comment, ), diff --git a/crates/js_ast/convert/convert_valid_if.rs b/crates/js_ast/convert/convert_valid_if.rs index 1e71398123c950b76f1f1de7e6e3088f3995fb79..0b294194266e2b189be8d7398a7bcce60a337283 100644 --- a/crates/js_ast/convert/convert_valid_if.rs +++ b/crates/js_ast/convert/convert_valid_if.rs @@ -4,13 +4,13 @@ use super::BlockConvertContext; use crate::convert::IsValidJSExpression; use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; /// Convert a valid blight if statement to a JS expression pub fn convert_valid_if( ctx: &mut BlockConvertContext, expr: If, - loc: Loc, + range: Range, comment: Option, ) -> JsExpr { debug_assert!( @@ -19,10 +19,10 @@ pub fn convert_valid_if( ); let condition = convert_valid_expr(ctx, *expr.condition); - let yes = convert_valid_block(ctx, expr.yes.block, expr.yes.loc); + let yes = convert_valid_block(ctx, expr.yes.block, expr.yes.range); let no = match expr.no { - Some(BlockOrIf::Block(b)) => Some(convert_valid_block(ctx, b.block, b.loc)), - Some(BlockOrIf::If(else_if)) => Some(convert_valid_if(ctx, *else_if, Loc::EMPTY, None)), + Some(BlockOrIf::Block(b)) => Some(convert_valid_block(ctx, b.block, b.range)), + Some(BlockOrIf::If(else_if)) => Some(convert_valid_if(ctx, *else_if, Range::EMPTY, None)), None => None, }; @@ -32,7 +32,7 @@ pub fn convert_valid_if( yes: Box::new(yes), no: no.map(Box::new), }, - loc, + range, comment, ) } diff --git a/crates/js_ast/convert/convert_valid_statement.rs b/crates/js_ast/convert/convert_valid_statement.rs index f02fb4e407e920b50233e188a1f14fb6fbc72b24..ef0d6b5fb48c8cbe532a76df797c346fb4b915ac 100644 --- a/crates/js_ast/convert/convert_valid_statement.rs +++ b/crates/js_ast/convert/convert_valid_statement.rs @@ -27,6 +27,6 @@ pub fn convert_valid_statement_to_expr( /// TODO(@paperdave): Replace this with Into for JsExpr pub fn convert_valid_statement(ctx: &mut BlockConvertContext, statement: Statement) -> JsStatement { let expr = convert_valid_statement_to_expr(ctx, statement); - let loc = expr.loc.clone(); - JsStatement::new(JsStatementData::Expression(expr), loc, None) + let range = expr.range.clone(); + JsStatement::new(JsStatementData::Expression(expr), range, None) } diff --git a/crates/js_ast/convert/hoist_block_to_expr.rs b/crates/js_ast/convert/hoist_block_to_expr.rs index fa419cedde552f566140b6474ddf08bee0f84bbd..16ea9fab3f641f8b3c5c3dc8e571810e8fa47f90 100644 --- a/crates/js_ast/convert/hoist_block_to_expr.rs +++ b/crates/js_ast/convert/hoist_block_to_expr.rs @@ -3,7 +3,7 @@ use super::process_statement; use super::BlockConvertContext; use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; /// This block hoist is used when we have a block in an expression context. /// @@ -30,7 +30,7 @@ use tokenizer::Loc; pub fn hoist_block_to_expr( ctx: &mut BlockConvertContext, block: Block, - loc: Loc, + range: Range, comment: Option, ) -> Option { debug_assert!( @@ -57,7 +57,7 @@ pub fn hoist_block_to_expr( _ => unreachable!(), } } - _ => JsExpr::new(JsExprData::Null, loc.clone(), None), + _ => JsExpr::new(JsExprData::Null, range.clone(), None), }; ctx.add_statement(JsStatement::new( @@ -66,13 +66,13 @@ pub fn hoist_block_to_expr( init: Some(result), is_constant: false, }), - loc.clone(), + range.clone(), comment, )); Some(JsExpr::new( JsExprData::Identifier(temporary.get(&ctx)), - loc, + range, None, )) } diff --git a/crates/js_ast/convert/hoist_block_to_js_block.rs b/crates/js_ast/convert/hoist_block_to_js_block.rs index 22fcd4a5ea5a1d4d7bf80a2e169f1c8c1d7257d6..50fe974c9b851a8d49aca0fe6fe07d550d33b8ef 100644 --- a/crates/js_ast/convert/hoist_block_to_js_block.rs +++ b/crates/js_ast/convert/hoist_block_to_js_block.rs @@ -1,6 +1,6 @@ use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; use super::*; @@ -22,7 +22,7 @@ use super::*; pub fn hoist_block_to_js_block( ctx: &mut BlockConvertContext, block: Block, - loc: Loc, + range: Range, target: &TempId, did_assign: &mut bool, ) -> JsBlock { @@ -34,11 +34,11 @@ pub fn hoist_block_to_js_block( if block.is_valid_js_expression() { return JsBlock::new( vec![new_js_assignment_statement( - convert_valid_block(ctx, block, loc.clone()), + convert_valid_block(ctx, block, range.clone()), target.get(ctx), - loc.clone(), + range.clone(), )], - loc, + range, ); } @@ -59,7 +59,7 @@ pub fn hoist_block_to_js_block( child.add_statement(new_js_assignment_statement( expr, target.get(ctx), - loc.clone(), + range.clone(), )); } _ => {} diff --git a/crates/js_ast/convert/hoist_expr.rs b/crates/js_ast/convert/hoist_expr.rs index 3affb5c8e36e4105059bf1ff98989739bf4b5f88..376e1072961ddfc90a8713a3cae5bb7d1d8925f2 100644 --- a/crates/js_ast/convert/hoist_expr.rs +++ b/crates/js_ast/convert/hoist_expr.rs @@ -18,7 +18,7 @@ pub fn hoist_expr_if_needed(ctx: &mut BlockConvertContext, expr: Expr) -> Option let init = hoist_expr_contents(ctx, expr)?; let id = ctx.generate_temp_id("_"); - let loc = init.loc.clone(); + let range = init.range.clone(); ctx.add_statement(JsStatement::new( JsStatementData::Declaration(JSDeclaration { @@ -26,11 +26,15 @@ pub fn hoist_expr_if_needed(ctx: &mut BlockConvertContext, expr: Expr) -> Option init: Some(init), is_constant: true, }), - loc.clone(), + range.clone(), None, )); - Some(JsExpr::new(JsExprData::Identifier(id.get(&ctx)), loc, None)) + Some(JsExpr::new( + JsExprData::Identifier(id.get(&ctx)), + range, + None, + )) } /// Returning `None` from this means that the expression is noreturn, and that @@ -51,7 +55,7 @@ pub fn hoist_expr_contents(ctx: &mut BlockConvertContext, expr: Expr) -> Option< left: Box::new(left), right: Box::new(right), }, - expr.loc, + expr.range, expr.comment, )) } @@ -63,7 +67,7 @@ pub fn hoist_expr_contents(ctx: &mut BlockConvertContext, expr: Expr) -> Option< op, value: Box::new(value), }, - expr.loc, + expr.range, expr.comment, )) } @@ -85,24 +89,24 @@ pub fn hoist_expr_contents(ctx: &mut BlockConvertContext, expr: Expr) -> Option< index: Box::new(field), }, }, - expr.loc, + expr.range, expr.comment, )) } - ExprData::Block(block) => hoist_block_to_expr(ctx, block, expr.loc, expr.comment), + ExprData::Block(block) => hoist_block_to_expr(ctx, block, expr.range, expr.comment), ExprData::If(_) => hoist_if_expr(ctx, expr), ExprData::Return(maybe_expr) => { - let loc = expr.loc.clone(); + let range = expr.range.clone(); let return_value = match maybe_expr { Some(expr) => Some(hoist_expr_if_needed(ctx, *expr)?), None => None, }; ctx.add_statement(JsStatement::new( JsStatementData::Return(return_value), - loc, + range, None, )); None @@ -120,7 +124,7 @@ pub fn hoist_expr_contents(ctx: &mut BlockConvertContext, expr: Expr) -> Option< base: Box::new(base), arguments, }, - expr.loc, + expr.range, expr.comment, )) } diff --git a/crates/js_ast/convert/hoist_if.rs b/crates/js_ast/convert/hoist_if.rs index cbe2fffe3866392543f3d7c67f1fddf3b9fa44f0..734d0e712bcfecf32925fedd5dcc55b8f252a7c4 100644 --- a/crates/js_ast/convert/hoist_if.rs +++ b/crates/js_ast/convert/hoist_if.rs @@ -6,7 +6,7 @@ use super::IsValidJSExpression; use super::TempId; use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; pub fn hoist_if_expr(ctx: &mut BlockConvertContext, expr: Expr) -> Option { let data = match expr.data { @@ -22,7 +22,7 @@ pub fn hoist_if_expr(ctx: &mut BlockConvertContext, expr: Expr) -> Option Option, condition: JsExpr, did_assign: &mut bool, temporary: &TempId, ) -> JsIf { - let yes = hoist_block_to_js_block(ctx, yes.block, yes.loc, &temporary, did_assign); + let yes = hoist_block_to_js_block(ctx, yes.block, yes.range, &temporary, did_assign); let no = match no { Some(BlockOrIf::Block(no)) => Some(JsElse::Block(hoist_block_to_js_block( - ctx, no.block, no.loc, &temporary, did_assign, + ctx, no.block, no.range, &temporary, did_assign, ))), Some(BlockOrIf::If(else_if)) => { // If the condition of this block has a side effect, we need to @@ -99,7 +99,7 @@ pub fn hoist_if_branch( did_assign, temporary, )), - Loc::EMPTY, + Range::EMPTY, None, )); diff --git a/crates/js_ast/convert/is_valid_js_expression.rs b/crates/js_ast/convert/is_valid_js_expression.rs index feb2f206c2daf10b6be3f68358ad4097788adc08..344d817f4465cf366923d7498fbdb36034851958 100644 --- a/crates/js_ast/convert/is_valid_js_expression.rs +++ b/crates/js_ast/convert/is_valid_js_expression.rs @@ -75,7 +75,7 @@ impl IsValidJSExpression for BlockOrIf { } } -impl IsValidJSExpression for BlockWithLoc { +impl IsValidJSExpression for BlockWithRange { fn is_valid_js_expression(&self) -> bool { self.block.is_valid_js_expression() } diff --git a/crates/js_ast/convert/process_function.rs b/crates/js_ast/convert/process_function.rs index b451c3ac2881b7b28f3e2d63f5cbdef052b161d7..be0c92160efba916d2e08ff2e42ed9b07b7aa145 100644 --- a/crates/js_ast/convert/process_function.rs +++ b/crates/js_ast/convert/process_function.rs @@ -5,13 +5,13 @@ use super::BlockConvertContext; use super::IsValidJSExpression; use crate::js_ast::*; use ast::*; -use tokenizer::Loc; +use log::Range; pub fn process_function_to_arrow( ctx: &mut BlockConvertContext, body: Expr, params: Vec, - loc: Loc, + range: Range, comment: Option, ) -> JsExpr { // A block that is a valid expression will just become @@ -34,7 +34,7 @@ pub fn process_function_to_arrow( if let Some(expr) = child.take_last_statement_if_expr() { child.add_statement(JsStatement::new( JsStatementData::Return(Some(expr)), - loc.clone(), + range.clone(), None, )); } @@ -44,7 +44,7 @@ pub fn process_function_to_arrow( if let Some(expr) = hoist_expr_if_needed(&mut child, body) { child.add_statement(JsStatement::new( JsStatementData::Return(Some(expr)), - loc.clone(), + range.clone(), None, )); } @@ -59,7 +59,7 @@ pub fn process_function_to_arrow( params: params.into_iter().map(|x| x.name).collect(), body: Box::new(body), }, - loc.clone(), + range.clone(), comment.map(|x| x.into()), ) } diff --git a/crates/js_ast/convert/process_statement.rs b/crates/js_ast/convert/process_statement.rs index 6dbba248ca9167cc3e149c12069116aa2149ba85..56354366133421783e025ddd47bb70d8313c79ee 100644 --- a/crates/js_ast/convert/process_statement.rs +++ b/crates/js_ast/convert/process_statement.rs @@ -35,7 +35,7 @@ pub fn process_statement(ctx: &mut BlockConvertContext, statement: Statement) -> } else { JsStatementData::Declaration(decl_data) }, - decl.loc, + decl.range, decl.comment.map(|x| x.into()), ); @@ -45,10 +45,10 @@ pub fn process_statement(ctx: &mut BlockConvertContext, statement: Statement) -> } Statement::Expr(expr) => { if let Some(expr) = hoist_expr_contents(ctx, expr) { - let loc = expr.loc.clone(); + let range = expr.range.clone(); ctx.add_statement(JsStatement::new( JsStatementData::Expression(expr), - loc, + range, None, )); Some(()) @@ -60,7 +60,7 @@ pub fn process_statement(ctx: &mut BlockConvertContext, statement: Statement) -> name, params, body, - loc, + range, comment, is_pub, .. @@ -71,7 +71,7 @@ pub fn process_statement(ctx: &mut BlockConvertContext, statement: Statement) -> ctx, body, params, - loc.clone(), + range.clone(), None, )); @@ -87,7 +87,7 @@ pub fn process_statement(ctx: &mut BlockConvertContext, statement: Statement) -> } else { JsStatementData::Declaration(decl_data) }, - loc, + range, comment.map(|x| x.into()), )); diff --git a/crates/js_ast/convert/side_effects.rs b/crates/js_ast/convert/side_effects.rs index 5eeaea8a53069fe637943bc72add4cb5c202fcc5..b66d121fa925d72b2ee65a066da6915b7a644fc5 100644 --- a/crates/js_ast/convert/side_effects.rs +++ b/crates/js_ast/convert/side_effects.rs @@ -84,7 +84,7 @@ impl HasSideEffects for BlockOrIf { } } -impl HasSideEffects for BlockWithLoc { +impl HasSideEffects for BlockWithRange { fn has_side_effects(&self) -> bool { self.block.has_side_effects() } diff --git a/crates/js_ast/js_ast.rs b/crates/js_ast/js_ast.rs index 29bdcdfe339551d713456dd52330e5b24166bf50..ab09c672a4735e4eb6dd4138c0b92ba2089ee298 100644 --- a/crates/js_ast/js_ast.rs +++ b/crates/js_ast/js_ast.rs @@ -1,11 +1,11 @@ use ast::{BinaryOperator, Comment, UnaryOperator}; +use log::Range; use num::bigint::BigInt; -use tokenizer::Loc; #[derive(Debug, PartialEq, Clone)] pub struct JsExpr { pub data: JsExprData, - pub loc: Loc, + pub range: Range, pub comment: Option, } @@ -74,7 +74,7 @@ pub enum JsExprData { #[derive(Debug, PartialEq, Clone)] pub struct JsStatement { pub data: JsStatementData, - pub loc: Loc, + pub range: Range, pub comment: Option, } @@ -133,12 +133,16 @@ pub struct JSNamedExport { #[derive(Debug, PartialEq, Clone)] pub struct JsBlock { pub statements: Vec, - pub loc: Loc, + pub range: Range, } impl JsExpr { - pub fn new(data: JsExprData, loc: Loc, comment: Option) -> Self { - Self { data, loc, comment } + pub fn new(data: JsExprData, range: Range, comment: Option) -> Self { + Self { + data, + range, + comment, + } } pub fn is_literal(&self) -> bool { @@ -167,14 +171,18 @@ impl JsExprData { } impl JsBlock { - pub fn new(statements: Vec, loc: Loc) -> Self { - Self { statements, loc } + pub fn new(statements: Vec, range: Range) -> Self { + Self { statements, range } } } impl JsStatement { - pub fn new(data: JsStatementData, loc: Loc, comment: Option) -> Self { - Self { data, loc, comment } + pub fn new(data: JsStatementData, range: Range, comment: Option) -> Self { + Self { + data, + range, + comment, + } } } diff --git a/crates/log/Cargo.toml b/crates/log/Cargo.toml new file mode 100644 index 0000000000000000000000000000000000000000..1ec8e700cac532f571aea79f215f0ac610e6d9e4 --- /dev/null +++ b/crates/log/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "log" +edition = "2021" + +[lib] +path="./log.rs" + +[dependencies] +miette.workspace = true +thiserror.workspace = true +url.workspace = true diff --git a/crates/log/log.rs b/crates/log/log.rs new file mode 100644 index 0000000000000000000000000000000000000000..7d91cbbbdb54e2058e2807f3c699a48532d458b4 --- /dev/null +++ b/crates/log/log.rs @@ -0,0 +1,88 @@ +use std::{fs, path::Path, rc::Rc}; + +use miette::{IntoDiagnostic, Result}; +use url::Url; + +#[derive(Debug, PartialEq, Clone, Copy)] +pub struct Range { + pub start: usize, + pub length: usize, +} + +impl Range { + /// TODO(@paperdave): Remove this. every usage of this is incorrect. + pub const EMPTY: Range = Range { + start: 0, + length: 0, + }; + + pub fn new(start: usize, length: usize) -> Self { + Self { start, length } + } + + pub fn len(&self) -> usize { + self.length + } +} + +// TODO(@lino-levan): make this loggable nicely +#[derive(Debug, Clone)] +pub struct Message<'a> { + pub source: &'a Source, + pub range: Range, + pub message: String, + pub notes: Vec>, +} + +#[derive(Debug, Clone)] +pub struct Note<'a> { + pub location: Option>, + pub message: String, +} + +#[derive(Debug, Clone)] +pub struct RangeAndSource<'a> { + pub range: Range, + pub source: &'a Source, +} + +#[derive(Debug)] +pub struct Source { + pub url: Url, + pub code: String, +} + +impl Source { + pub fn new(url: Url, source_code: String) -> Rc { + Rc::new(Source { + url, + code: source_code, + }) + } + + pub fn from_file(path: &Path) -> Result> { + let source_code = fs::read_to_string(path).into_diagnostic()?; + let url = Url::from_file_path(path).unwrap(); + Ok(Rc::new(Source { + code: source_code, + url, + })) + } + + pub fn from_url(url: Url) -> Result> { + match url.scheme() { + "file" => { + // TODO: how to return this error, into_diagnostic() doesn't exist + let file_path = url.to_file_path().unwrap(); + let source_code = fs::read_to_string(file_path).into_diagnostic()?; + Ok(Rc::new(Source { + code: source_code, + url, + })) + } + _ => { + todo!("Fetch from URL: {}", url) + } + } + } +} diff --git a/crates/parser/Cargo.toml b/crates/parser/Cargo.toml index 220932c2a7189d96bb8a2b807c9d0c97292a2d0a..0a7ff98b649756ba9871e3dd13f63cfcc6abd6a5 100644 --- a/crates/parser/Cargo.toml +++ b/crates/parser/Cargo.toml @@ -13,3 +13,4 @@ num.workspace = true ast = { path = "../ast" } tokenizer = { path = "../tokenizer" } +log = { path = "../log" } diff --git a/crates/parser/parse_declaration.rs b/crates/parser/parse_declaration.rs index 1199f366ac02e86f2cd7f3039927698279792144..0d5ae7e9f33c978ca796bce72edaac57b8e72e91 100644 --- a/crates/parser/parse_declaration.rs +++ b/crates/parser/parse_declaration.rs @@ -1,6 +1,7 @@ use ast::{DocComment, Type, VarDecl}; +use log::Range; use miette::Result; -use tokenizer::{Loc, TokenType}; +use tokenizer::TokenType; use crate::parse_expr::parse_expr; use crate::parse_type::parse_type; @@ -45,6 +46,6 @@ pub fn parse_declaration( is_constant, is_pub, comment, - loc: Loc::new(start, p.index - start), + range: Range::new(start, p.index - start), }) } diff --git a/crates/parser/parse_doc_comment.rs b/crates/parser/parse_doc_comment.rs index d6ae34c376c12c5f18dcbcf15e489375275a1711..cb138e3abb6e12f97ef8f6ec4a01d7106004c5b7 100644 --- a/crates/parser/parse_doc_comment.rs +++ b/crates/parser/parse_doc_comment.rs @@ -1,5 +1,6 @@ use ast::DocComment; -use tokenizer::{Loc, TokenType}; +use log::Range; +use tokenizer::TokenType; use crate::Parser; @@ -10,7 +11,7 @@ pub fn maybe_read_doc_comment(p: &mut Parser) -> Option { p.next(); Some(DocComment { data, - loc: Loc::new(start, p.index - start), + range: Range::new(start, p.index - start), }) } _ => None, diff --git a/crates/parser/parse_expr.rs b/crates/parser/parse_expr.rs index dab8ffa3c4951c77fe1d3061921ef1ce79e71cdb..f1429fb898767e14792874af6559dbb9e6c0f1f6 100644 --- a/crates/parser/parse_expr.rs +++ b/crates/parser/parse_expr.rs @@ -1,7 +1,7 @@ use ast::Associativity::*; use ast::{BinaryOperator, Expr, ExprData, OperatorLevel}; +use log::Range; use miette::Result; -use tokenizer::Loc; use crate::parse_expr_basic::parse_expr_basic; use crate::Parser; @@ -94,7 +94,7 @@ fn parse_expr_binary( left: Box::new(left), right: Box::new(right), }, - Loc::new(start, p.index - start), + Range::new(start, p.index - start), None, )) } diff --git a/crates/parser/parse_expr_basic.rs b/crates/parser/parse_expr_basic.rs index 0bb680cedf2580f82335a12cb6b02dfa9f1e7ecc..037b6a1066985d0f188185a3dafb9b5c1362c37c 100644 --- a/crates/parser/parse_expr_basic.rs +++ b/crates/parser/parse_expr_basic.rs @@ -1,6 +1,7 @@ use ast::{BuiltinId, Expr, ExprData, Literal, UnaryOperator}; +use log::Range; use miette::Result; -use tokenizer::{Loc, TokenType}; +use tokenizer::TokenType; use crate::{ parse_block::parse_block, parse_call_arguments::parse_call_arguments, parse_expr::parse_expr, @@ -15,7 +16,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { _ = p.next(); Expr::new( ExprData::Literal(Literal::Number(number.clone())), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -23,7 +24,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { _ = p.next(); Expr::new( ExprData::Literal(Literal::String(string.clone())), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -31,7 +32,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { _ = p.next(); Expr::new( ExprData::Literal(Literal::Bool(true)), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -39,7 +40,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { _ = p.next(); Expr::new( ExprData::Literal(Literal::Bool(false)), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -47,7 +48,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { _ = p.next(); Expr::new( ExprData::Literal(Literal::Void), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -60,14 +61,14 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { let arguments = parse_call_arguments(p)?; Expr::new( ExprData::Builtin { id, arguments }, - Loc::new(identifier_start, p.index - identifier_start), + Range::new(identifier_start, p.index - identifier_start), comments, ) } else { return Err(p .error_at( format!("Built-in function '{}' must be called", name), - Loc::new(identifier_start, p.index - identifier_start), + Range::new(identifier_start, p.index - identifier_start), ) .into()); } @@ -75,14 +76,14 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { return Err(p .error_at( format!("Non-existant built-in: '{}'", name), - Loc::new(identifier_start, p.index - identifier_start), + Range::new(identifier_start, p.index - identifier_start), ) .into()); } } else { Expr::new( ExprData::Identifier(name), - Loc::new(identifier_start, p.index - identifier_start), + Range::new(identifier_start, p.index - identifier_start), comments, ) } @@ -99,7 +100,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { return Ok(Some(Expr::new( ExprData::Return(inner), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ))); } @@ -107,13 +108,13 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { Some(TokenType::If) => Expr::new( ExprData::If(parse_expr_if(p)?), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ), Some(TokenType::OpenBrace) => Expr::new( ExprData::Block(parse_block(p)?), - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ), @@ -142,7 +143,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { }, value: Box::new(parse_expr_basic(p)?), }, - Loc::new(start, p.index - start), + Range::new(start, p.index - start), comments, ) } @@ -162,7 +163,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { p.next(); Expr::new( ExprData::Literal(Literal::String(name)), - Loc::new(field_start, p.index - field_start), + Range::new(field_start, p.index - field_start), None, ) } @@ -175,7 +176,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { base: Box::new(expr), field: Box::new(field), }, - Loc::new(field_start, p.index - field_start), + Range::new(field_start, p.index - field_start), None, ); } @@ -188,7 +189,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { base: Box::new(expr), arguments, }, - Loc::new(expr_start, p.index - expr_start), + Range::new(expr_start, p.index - expr_start), None, ); } @@ -202,7 +203,7 @@ pub fn maybe_parse_expr_basic(p: &mut Parser) -> Result> { base: Box::new(expr), field: Box::new(index), }, - Loc::new(expr_start, p.index - expr_start), + Range::new(expr_start, p.index - expr_start), None, ); } else { diff --git a/crates/parser/parse_expr_if.rs b/crates/parser/parse_expr_if.rs index 12ccc2e5adbdb28bd18af2596342d46ab399d4eb..0bd246255677060afa1f44b0ebe100bc99b4ecc8 100644 --- a/crates/parser/parse_expr_if.rs +++ b/crates/parser/parse_expr_if.rs @@ -1,6 +1,7 @@ -use ast::{BlockOrIf, BlockWithLoc, If}; +use ast::{BlockOrIf, BlockWithRange, If}; +use log::Range; use miette::Result; -use tokenizer::{Loc, TokenType}; +use tokenizer::TokenType; use crate::parse_block::parse_block; use crate::parse_expr::parse_expr; @@ -30,9 +31,9 @@ pub fn parse_expr_if(p: &mut Parser) -> Result { let yes = match p.peek() { Some(TokenType::OpenBrace) => { let block_start = p.index; - BlockWithLoc { + BlockWithRange { block: parse_block(p)?, - loc: Loc::new(block_start, p.index - block_start), + range: Range::new(block_start, p.index - block_start), } } _ => { @@ -49,14 +50,14 @@ pub fn parse_expr_if(p: &mut Parser) -> Result { Some(TokenType::OpenBrace) => { let block_start = p.index; // let comments = p.take_comments(); - Some(BlockOrIf::Block(BlockWithLoc { + Some(BlockOrIf::Block(BlockWithRange { block: parse_block(p)?, - loc: Loc::new(block_start, p.index - block_start), + range: Range::new(block_start, p.index - block_start), })) } Some(TokenType::If) => { // TODO(@paperdave): Save location for the if - // let loc = p.loc(); + // let range = p.range(); // let comments = p.take_comments(); Some(BlockOrIf::If(Box::new(parse_expr_if(p)?))) } diff --git a/crates/parser/parse_fn_declaration.rs b/crates/parser/parse_fn_declaration.rs index 8a2c54e197e2e21d22169f6a2cd67fef29b242b4..9d1ccddba381832e9ccd2480af4bc4d862c552a4 100644 --- a/crates/parser/parse_fn_declaration.rs +++ b/crates/parser/parse_fn_declaration.rs @@ -1,6 +1,7 @@ use ast::{DocComment, Expr, ExprData, FnDecl, Type}; +use log::Range; use miette::Result; -use tokenizer::{Loc, TokenType}; +use tokenizer::TokenType; use crate::parse_block::parse_block; use crate::parse_expr::parse_expr; @@ -93,7 +94,7 @@ pub fn parse_fn_declaration( let block = parse_block(p)?; Expr::new( ExprData::Block(block), - Loc::new(block_start, p.index - block_start), + Range::new(block_start, p.index - block_start), None, ) } @@ -121,6 +122,6 @@ pub fn parse_fn_declaration( body, is_pub, comment, - loc: Loc::new(start, p.index - start), + range: Range::new(start, p.index - start), }) } diff --git a/crates/parser/parse_statement.rs b/crates/parser/parse_statement.rs index efe4eacd6c821556f025038de194ef8a72b81870..55fddecad16f51aa231b44ed3fe8448dd809ecd0 100644 --- a/crates/parser/parse_statement.rs +++ b/crates/parser/parse_statement.rs @@ -18,7 +18,7 @@ pub fn parse_statement(p: &mut Parser) -> Result { if p.has_comments() { // this implies that comments are immediately after the doc return Err(p - .error_at(format!("Unattached doc comment"), doc_comment.loc) + .error_at(format!("Unattached doc comment"), doc_comment.range) .into()); } } @@ -58,7 +58,7 @@ pub fn parse_statement(p: &mut Parser) -> Result { Some(_) => { if let Some(doc_comment) = m_doc_comment { Err(p - .error_at(format!("Unattached doc comment"), doc_comment.loc) + .error_at(format!("Unattached doc comment"), doc_comment.range) .into()) } else { Ok(Statement::Expr(parse_expr(p)?)) diff --git a/crates/parser/parser.rs b/crates/parser/parser.rs index 4c02df4b30a082730a615b0a98c2cbadac9e887b..12d58b41ee0d968f5b3ed722bed7e123b2ed4633 100644 --- a/crates/parser/parser.rs +++ b/crates/parser/parser.rs @@ -14,13 +14,14 @@ mod parse_type; use ast::Comment; use ast::Module; +use log::Range; use miette::Diagnostic; use miette::Result; use parse_module::parse_module; use thiserror::Error; use tokenizer::tokenize; +use tokenizer::Token; use tokenizer::TokenType; -use tokenizer::{Loc, Token}; pub fn parse(tokens: Vec) -> Result { let mut p = Parser::new(tokens); @@ -37,12 +38,12 @@ pub fn parse_from_string(string: String) -> Result { pub struct ParseError { #[help] error: String, - loc: Option, + range: Option, } impl ParseError { - pub fn new(error: String, loc: Option) -> ParseError { - ParseError { error, loc } + pub fn new(error: String, range: Option) -> ParseError { + ParseError { error, range } } } @@ -89,7 +90,7 @@ impl Parser { loop { let token = self.tokens[self.cursor].clone(); - self.index = token.loc.start; + self.index = token.range.start; match token.variant { TokenType::Comment(comment) => { self.comments.push(comment); @@ -144,7 +145,7 @@ impl Parser { ParseError::new(error, None) } - fn error_at(&self, error: String, loc: Loc) -> ParseError { - ParseError::new(error, Some(loc)) + fn error_at(&self, error: String, range: Range) -> ParseError { + ParseError::new(error, Some(range)) } } diff --git a/crates/tokenizer/Cargo.toml b/crates/tokenizer/Cargo.toml index 6e881084601ce5e033c79ce16949e3dc732880a2..5a51640ba63101310df8787cb92377295a1b0024 100644 --- a/crates/tokenizer/Cargo.toml +++ b/crates/tokenizer/Cargo.toml @@ -9,3 +9,5 @@ path="./tokenizer.rs" [dependencies] miette.workspace = true thiserror.workspace = true + +log = { path = "../log" } diff --git a/crates/tokenizer/tokenizer.rs b/crates/tokenizer/tokenizer.rs index 0b89bea7eb70503cad6885619945a13a4ed79c70..522a1896152d3494c16cee7ed207904927cd28a2 100644 --- a/crates/tokenizer/tokenizer.rs +++ b/crates/tokenizer/tokenizer.rs @@ -1,28 +1,7 @@ +use log::Range; use miette::{Diagnostic, Result}; use thiserror::Error; -#[derive(Debug, PartialEq, Clone)] -pub struct Loc { - pub start: usize, - pub length: usize, -} - -impl Loc { - /// TODO(@paperdave): Remove this. every usage of this is incorrect. - pub const EMPTY: Loc = Loc { - start: 0, - length: 0, - }; - - pub fn new(start: usize, length: usize) -> Self { - Self { start, length } - } - - pub fn len(&self) -> usize { - self.length - } -} - #[derive(Error, Diagnostic, Debug)] #[error("UnknownCharacter")] struct UnknownCharacter { @@ -162,19 +141,19 @@ impl std::fmt::Display for TokenType { #[derive(Debug, Clone)] pub struct Token { pub variant: TokenType, - pub loc: Loc, + pub range: Range, } impl Token { pub fn new(variant: TokenType, start: usize, length: usize) -> Self { Self { variant, - loc: Loc::new(start, length), + range: Range::new(start, length), } } } -// TODO(@paperdave): rewrite this to not use a Vec. we probably dont need it. also store Loc +// TODO(@paperdave): rewrite this to not use a Vec. we probably dont need it. also store Range pub fn tokenize(content: String) -> Result> { let mut tokens: Vec = Vec::new(); let mut chars = content.chars().enumerate().peekable(); -- 2.54.0