mirror of
https://github.com/MorizzG/rlox.git
synced 2025-12-06 04:12:42 +00:00
replaced Box<str> with SmolStr
This commit is contained in:
parent
fb88595b6c
commit
da6a820638
21 changed files with 137 additions and 85 deletions
35
Cargo.lock
generated
35
Cargo.lock
generated
|
|
@ -362,6 +362,7 @@ version = "0.1.0"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"itertools",
|
"itertools",
|
||||||
"phf",
|
"phf",
|
||||||
|
"smol_str",
|
||||||
"thiserror",
|
"thiserror",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
@ -373,6 +374,7 @@ dependencies = [
|
||||||
"itertools",
|
"itertools",
|
||||||
"rlox2-frontend",
|
"rlox2-frontend",
|
||||||
"rustc-hash",
|
"rustc-hash",
|
||||||
|
"smol_str",
|
||||||
"thiserror",
|
"thiserror",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
@ -417,6 +419,26 @@ dependencies = [
|
||||||
"windows-sys 0.52.0",
|
"windows-sys 0.52.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "serde"
|
||||||
|
version = "1.0.209"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "99fce0ffe7310761ca6bf9faf5115afbc19688edd00171d81b1bb1b116c63e09"
|
||||||
|
dependencies = [
|
||||||
|
"serde_derive",
|
||||||
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "serde_derive"
|
||||||
|
version = "1.0.209"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "a5831b979fd7b5439637af1752d535ff49f4860c0f341d1baeb6faf0f4242170"
|
||||||
|
dependencies = [
|
||||||
|
"proc-macro2",
|
||||||
|
"quote",
|
||||||
|
"syn",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "siphasher"
|
name = "siphasher"
|
||||||
version = "0.3.11"
|
version = "0.3.11"
|
||||||
|
|
@ -429,6 +451,15 @@ version = "1.13.2"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3c5e1a9a646d36c3599cd173a41282daf47c44583ad367b8e6837255952e5c67"
|
checksum = "3c5e1a9a646d36c3599cd173a41282daf47c44583ad367b8e6837255952e5c67"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "smol_str"
|
||||||
|
version = "0.2.2"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "dd538fb6910ac1099850255cf94a94df6551fbdd602454387d0adb2d1ca6dead"
|
||||||
|
dependencies = [
|
||||||
|
"serde",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "strsim"
|
name = "strsim"
|
||||||
version = "0.11.1"
|
version = "0.11.1"
|
||||||
|
|
@ -437,9 +468,9 @@ checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "syn"
|
name = "syn"
|
||||||
version = "2.0.76"
|
version = "2.0.77"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "578e081a14e0cefc3279b0472138c513f37b41a08d5a3cca9b6e4e8ceb6cd525"
|
checksum = "9f35bcdf61fd8e7be6caf75f429fdca8beb3ed76584befb503b1569faee373ed"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"proc-macro2",
|
"proc-macro2",
|
||||||
"quote",
|
"quote",
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,6 @@ path = "interpreter"
|
||||||
# path = "vm"
|
# path = "vm"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
clap = { version = "4", features = ["derive"] }
|
clap = { version = "4.5.16", features = ["derive"] }
|
||||||
colored = "2.1.0"
|
colored = "2.1.0"
|
||||||
rustyline = "14.0.0"
|
rustyline = "14.0.0"
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,7 @@ edition = "2021"
|
||||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
phf = { version = "0.11", features = ["macros"] }
|
smol_str = "0.2.2"
|
||||||
thiserror = "1"
|
phf = { version = "0.11.2", features = ["macros"] }
|
||||||
itertools = "0.13"
|
thiserror = "1.0.63"
|
||||||
|
itertools = "0.13.0"
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,5 @@
|
||||||
use phf::phf_map;
|
use phf::phf_map;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use super::{CodePos, LexerError, Token, TokenType};
|
use super::{CodePos, LexerError, Token, TokenType};
|
||||||
|
|
||||||
|
|
@ -130,8 +131,9 @@ impl Lexer {
|
||||||
// advance until either source is empty or newline if found
|
// advance until either source is empty or newline if found
|
||||||
while !self.source_is_empty() && self.advance() != '\n' {}
|
while !self.source_is_empty() && self.advance() != '\n' {}
|
||||||
|
|
||||||
let comment: Box<str> =
|
let comment = SmolStr::from_iter(
|
||||||
self.source[self.start + 2..self.current].iter().collect();
|
self.source[self.start + 2..self.current].iter().cloned(),
|
||||||
|
);
|
||||||
|
|
||||||
self.push_token(TokenType::Comment(comment));
|
self.push_token(TokenType::Comment(comment));
|
||||||
} else if self.consume('*') {
|
} else if self.consume('*') {
|
||||||
|
|
@ -170,9 +172,11 @@ impl Lexer {
|
||||||
self.advance();
|
self.advance();
|
||||||
}
|
}
|
||||||
|
|
||||||
let comment: Box<str> = self.source[self.start + 2..self.current - 2]
|
let comment = SmolStr::from_iter(
|
||||||
.iter()
|
self.source[self.start + 2..self.current - 2]
|
||||||
.collect();
|
.iter()
|
||||||
|
.cloned(),
|
||||||
|
);
|
||||||
|
|
||||||
self.push_token(TokenType::Comment(comment));
|
self.push_token(TokenType::Comment(comment));
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -289,11 +293,6 @@ impl Lexer {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// let string_literal: Box<str> = self.source[self.start + 1..self.current - 1]
|
|
||||||
// .iter()
|
|
||||||
// .collect();
|
|
||||||
|
|
||||||
// Some(TokenType::String(Box::new(string_literal)))
|
|
||||||
self.tokens.push(Token::new_string(s, self.code_pos));
|
self.tokens.push(Token::new_string(s, self.code_pos));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,7 @@
|
||||||
use std::fmt::{Debug, Display};
|
use std::fmt::{Debug, Display};
|
||||||
|
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use super::CodePos;
|
use super::CodePos;
|
||||||
|
|
||||||
#[repr(u8)]
|
#[repr(u8)]
|
||||||
|
|
@ -17,13 +19,13 @@ pub enum TokenType {
|
||||||
Less, LessEqual,
|
Less, LessEqual,
|
||||||
|
|
||||||
// Identifier and literals
|
// Identifier and literals
|
||||||
Identifier(Box<str>), String(Box<str>), Number(f64),
|
Identifier(SmolStr), String(SmolStr), Number(f64),
|
||||||
|
|
||||||
// Keywords
|
// Keywords
|
||||||
And, Break, Class, Else, False, Fun, For, If, Nil, Or,
|
And, Break, Class, Else, False, Fun, For, If, Nil, Or,
|
||||||
Print, Return, Super, This, True, Var, While,
|
Print, Return, Super, This, True, Var, While,
|
||||||
|
|
||||||
Comment(Box<str>),
|
Comment(SmolStr),
|
||||||
|
|
||||||
#[allow(clippy::upper_case_acronyms)]
|
#[allow(clippy::upper_case_acronyms)]
|
||||||
EOF
|
EOF
|
||||||
|
|
@ -42,14 +44,14 @@ impl Token {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn new_string(s: impl Into<Box<str>>, code_pos: CodePos) -> Self {
|
pub fn new_string(s: impl Into<SmolStr>, code_pos: CodePos) -> Self {
|
||||||
Token {
|
Token {
|
||||||
token_type: TokenType::String(s.into()),
|
token_type: TokenType::String(s.into()),
|
||||||
code_pos,
|
code_pos,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn new_identifier(name: impl Into<Box<str>>, code_pos: CodePos) -> Self {
|
pub fn new_identifier(name: impl Into<SmolStr>, code_pos: CodePos) -> Self {
|
||||||
Token {
|
Token {
|
||||||
token_type: TokenType::Identifier(name.into()),
|
token_type: TokenType::Identifier(name.into()),
|
||||||
code_pos,
|
code_pos,
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,5 @@
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::lexer::{Token, TokenType};
|
use crate::lexer::{Token, TokenType};
|
||||||
use crate::parser::expr::BinaryOp;
|
use crate::parser::expr::BinaryOp;
|
||||||
|
|
||||||
|
|
@ -481,7 +483,7 @@ impl Parser {
|
||||||
Ok(Expr::function(name, param_names, body))
|
Ok(Expr::function(name, param_names, body))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn collect_params(&mut self) -> ParserResult<Vec<Box<str>>> {
|
fn collect_params(&mut self) -> ParserResult<Vec<SmolStr>> {
|
||||||
assert_eq!(self.next_token().token_type, TokenType::LeftParen);
|
assert_eq!(self.next_token().token_type, TokenType::LeftParen);
|
||||||
|
|
||||||
if self.peek_token().token_type == TokenType::RightParen {
|
if self.peek_token().token_type == TokenType::RightParen {
|
||||||
|
|
@ -825,7 +827,7 @@ impl Parser {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn identifier(&mut self, msg: &str) -> ParserResult<Box<str>> {
|
fn identifier(&mut self, msg: &str) -> ParserResult<SmolStr> {
|
||||||
match self.peek_token().token_type {
|
match self.peek_token().token_type {
|
||||||
TokenType::Identifier(_) => match self.next_token().token_type {
|
TokenType::Identifier(_) => match self.next_token().token_type {
|
||||||
TokenType::Identifier(s) => Ok(s),
|
TokenType::Identifier(s) => Ok(s),
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
use std::fmt::Display;
|
use std::fmt::Display;
|
||||||
|
|
||||||
use itertools::Itertools;
|
use itertools::Itertools;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use super::Stmt;
|
use super::Stmt;
|
||||||
|
|
||||||
|
|
@ -27,14 +28,14 @@ pub enum Expr {
|
||||||
expr: Box<Expr>,
|
expr: Box<Expr>,
|
||||||
},
|
},
|
||||||
Variable {
|
Variable {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
},
|
},
|
||||||
LocalVariable {
|
LocalVariable {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
level: usize,
|
level: usize,
|
||||||
},
|
},
|
||||||
GlobalVariable {
|
GlobalVariable {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
},
|
},
|
||||||
Assignment {
|
Assignment {
|
||||||
target: Box<Expr>,
|
target: Box<Expr>,
|
||||||
|
|
@ -46,21 +47,21 @@ pub enum Expr {
|
||||||
},
|
},
|
||||||
Get {
|
Get {
|
||||||
target: Box<Expr>,
|
target: Box<Expr>,
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
},
|
},
|
||||||
Set {
|
Set {
|
||||||
target: Box<Expr>,
|
target: Box<Expr>,
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
value: Box<Expr>,
|
value: Box<Expr>,
|
||||||
},
|
},
|
||||||
Function {
|
Function {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
param_names: Vec<Box<str>>,
|
param_names: Vec<SmolStr>,
|
||||||
closure_vars: Vec<(Box<str>, usize)>,
|
closure_vars: Vec<(SmolStr, usize)>,
|
||||||
body: Box<Stmt>,
|
body: Box<Stmt>,
|
||||||
},
|
},
|
||||||
Class {
|
Class {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
superclass: Option<Box<Expr>>,
|
superclass: Option<Box<Expr>>,
|
||||||
methods: Box<Vec<Expr>>,
|
methods: Box<Vec<Expr>>,
|
||||||
},
|
},
|
||||||
|
|
@ -68,12 +69,12 @@ pub enum Expr {
|
||||||
Super {
|
Super {
|
||||||
super_var: Box<Expr>,
|
super_var: Box<Expr>,
|
||||||
this_var: Box<Expr>,
|
this_var: Box<Expr>,
|
||||||
method: Box<str>,
|
method: SmolStr,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Expr {
|
impl Expr {
|
||||||
pub fn string(s: impl Into<Box<str>>) -> Self {
|
pub fn string(s: impl Into<SmolStr>) -> Self {
|
||||||
let s = s.into();
|
let s = s.into();
|
||||||
Expr::Literal {
|
Expr::Literal {
|
||||||
literal: Literal::String(s),
|
literal: Literal::String(s),
|
||||||
|
|
@ -120,17 +121,17 @@ impl Expr {
|
||||||
Expr::Grouping { expr }
|
Expr::Grouping { expr }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn variable(name: impl Into<Box<str>>) -> Self {
|
pub fn variable(name: impl Into<SmolStr>) -> Self {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
Expr::Variable { name }
|
Expr::Variable { name }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn local_variable(name: impl Into<Box<str>>, level: usize) -> Self {
|
pub fn local_variable(name: impl Into<SmolStr>, level: usize) -> Self {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
Expr::LocalVariable { name, level }
|
Expr::LocalVariable { name, level }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn global_variable(name: impl Into<Box<str>>) -> Self {
|
pub fn global_variable(name: impl Into<SmolStr>) -> Self {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
Expr::GlobalVariable { name }
|
Expr::GlobalVariable { name }
|
||||||
}
|
}
|
||||||
|
|
@ -146,13 +147,13 @@ impl Expr {
|
||||||
Expr::Call { callee, args }
|
Expr::Call { callee, args }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get(target: Expr, name: impl Into<Box<str>>) -> Self {
|
pub fn get(target: Expr, name: impl Into<SmolStr>) -> Self {
|
||||||
let target = Box::new(target);
|
let target = Box::new(target);
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
Expr::Get { target, name }
|
Expr::Get { target, name }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn function(name: impl Into<Box<str>>, param_names: Vec<Box<str>>, body: Stmt) -> Self {
|
pub fn function(name: impl Into<SmolStr>, param_names: Vec<SmolStr>, body: Stmt) -> Self {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
#[allow(clippy::box_default)]
|
#[allow(clippy::box_default)]
|
||||||
// let closure_vars = Box::new(Vec::new());
|
// let closure_vars = Box::new(Vec::new());
|
||||||
|
|
@ -166,7 +167,7 @@ impl Expr {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn class(name: impl Into<Box<str>>, methods: Vec<Expr>, superclass: Option<Expr>) -> Self {
|
pub fn class(name: impl Into<SmolStr>, methods: Vec<Expr>, superclass: Option<Expr>) -> Self {
|
||||||
let superclass = superclass.map(Box::new);
|
let superclass = superclass.map(Box::new);
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
let methods = Box::new(methods);
|
let methods = Box::new(methods);
|
||||||
|
|
@ -181,7 +182,7 @@ impl Expr {
|
||||||
pub fn super_(
|
pub fn super_(
|
||||||
super_var: impl Into<Box<Expr>>,
|
super_var: impl Into<Box<Expr>>,
|
||||||
this_var: impl Into<Box<Expr>>,
|
this_var: impl Into<Box<Expr>>,
|
||||||
method: impl Into<Box<str>>,
|
method: impl Into<SmolStr>,
|
||||||
) -> Self {
|
) -> Self {
|
||||||
let super_var = super_var.into();
|
let super_var = super_var.into();
|
||||||
let this_var = this_var.into();
|
let this_var = this_var.into();
|
||||||
|
|
@ -267,7 +268,7 @@ impl Display for Expr {
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub enum Literal {
|
pub enum Literal {
|
||||||
String(Box<str>),
|
String(SmolStr),
|
||||||
Number(f64),
|
Number(f64),
|
||||||
Bool(bool),
|
Bool(bool),
|
||||||
Nil,
|
Nil,
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,7 @@
|
||||||
use std::fmt::Display;
|
use std::fmt::Display;
|
||||||
|
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use super::misc::indent;
|
use super::misc::indent;
|
||||||
use super::Expr;
|
use super::Expr;
|
||||||
|
|
||||||
|
|
@ -18,7 +20,7 @@ pub enum Stmt {
|
||||||
body: Box<Stmt>,
|
body: Box<Stmt>,
|
||||||
},
|
},
|
||||||
VarDecl {
|
VarDecl {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
initializer: Box<Expr>,
|
initializer: Box<Expr>,
|
||||||
},
|
},
|
||||||
Block {
|
Block {
|
||||||
|
|
@ -62,7 +64,7 @@ impl Stmt {
|
||||||
Stmt::While { condition, body }
|
Stmt::While { condition, body }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn var_decl(name: impl Into<Box<str>>, initializer: impl Into<Box<Expr>>) -> Self {
|
pub fn var_decl(name: impl Into<SmolStr>, initializer: impl Into<Box<Expr>>) -> Self {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
|
|
||||||
let initializer = initializer.into();
|
let initializer = initializer.into();
|
||||||
|
|
|
||||||
|
|
@ -12,6 +12,7 @@ path = "../frontend"
|
||||||
glob = "0.3"
|
glob = "0.3"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
thiserror = "1"
|
itertools = "0.13.0"
|
||||||
itertools = "0.13"
|
rustc-hash = "2.0.0"
|
||||||
rustc-hash = "2"
|
smol_str = "0.2.2"
|
||||||
|
thiserror = "1.0.63"
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@ use std::rc::Rc;
|
||||||
|
|
||||||
use rlox2_frontend::parser::{Expr, Stmt};
|
use rlox2_frontend::parser::{Expr, Stmt};
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::{LoxFunction, LoxReference, Value};
|
use crate::{LoxFunction, LoxReference, Value};
|
||||||
|
|
||||||
|
|
@ -10,7 +11,7 @@ use crate::{LoxFunction, LoxReference, Value};
|
||||||
pub struct LoxClass {
|
pub struct LoxClass {
|
||||||
superclass: Option<Rc<LoxClass>>,
|
superclass: Option<Rc<LoxClass>>,
|
||||||
|
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
|
|
||||||
methods: FxHashMap<String, Value>,
|
methods: FxHashMap<String, Value>,
|
||||||
}
|
}
|
||||||
|
|
@ -18,7 +19,7 @@ pub struct LoxClass {
|
||||||
/// Representation of a class in Lox. Always behind an Rc to ensure uniqueness. Should never be handled raw.
|
/// Representation of a class in Lox. Always behind an Rc to ensure uniqueness. Should never be handled raw.
|
||||||
impl LoxClass {
|
impl LoxClass {
|
||||||
pub fn new(
|
pub fn new(
|
||||||
name: impl Into<Box<str>>,
|
name: impl Into<SmolStr>,
|
||||||
methods: FxHashMap<String, Value>,
|
methods: FxHashMap<String, Value>,
|
||||||
superclass: Option<Rc<LoxClass>>,
|
superclass: Option<Rc<LoxClass>>,
|
||||||
) -> Rc<Self> {
|
) -> Rc<Self> {
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@ use std::io::{Read, Write};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::error::RuntimeError;
|
use crate::error::RuntimeError;
|
||||||
|
|
||||||
|
|
@ -89,8 +90,8 @@ impl Display for ScopedValue {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
type Scope = FxHashMap<Box<str>, ScopedValue>;
|
type Scope = FxHashMap<SmolStr, ScopedValue>;
|
||||||
pub type ClosureScope = FxHashMap<Box<str>, HeapedValue>;
|
pub type ClosureScope = FxHashMap<SmolStr, HeapedValue>;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct Environment<'a> {
|
pub struct Environment<'a> {
|
||||||
|
|
@ -128,7 +129,7 @@ impl<'a> Environment<'a> {
|
||||||
std::mem::take(&mut self.arg_stack)
|
std::mem::take(&mut self.arg_stack)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn globals(&self) -> &FxHashMap<Box<str>, Value> {
|
pub fn globals(&self) -> &FxHashMap<SmolStr, Value> {
|
||||||
self.runtime.globals()
|
self.runtime.globals()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -219,7 +220,7 @@ impl<'a> Environment<'a> {
|
||||||
}) */
|
}) */
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn define(&mut self, name: impl Into<Box<str>>, value: Value) {
|
pub fn define(&mut self, name: impl Into<SmolStr>, value: Value) {
|
||||||
if self.has_scope() {
|
if self.has_scope() {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
self.current_scope_mut()
|
self.current_scope_mut()
|
||||||
|
|
@ -246,7 +247,7 @@ impl<'a> Environment<'a> {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn collect_closure(&mut self, closure_vars: &[(Box<str>, usize)]) -> ClosureScope {
|
pub fn collect_closure(&mut self, closure_vars: &[(SmolStr, usize)]) -> ClosureScope {
|
||||||
let mut closure_scope = ClosureScope::default();
|
let mut closure_scope = ClosureScope::default();
|
||||||
|
|
||||||
for (name, level) in closure_vars {
|
for (name, level) in closure_vars {
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@ use std::rc::Rc;
|
||||||
|
|
||||||
use rlox2_frontend::lexer::LexerError;
|
use rlox2_frontend::lexer::LexerError;
|
||||||
use rlox2_frontend::parser::{BinaryOp, ParserError, UnaryOp};
|
use rlox2_frontend::parser::{BinaryOp, ParserError, UnaryOp};
|
||||||
|
use smol_str::SmolStr;
|
||||||
use thiserror::Error;
|
use thiserror::Error;
|
||||||
|
|
||||||
use crate::Value;
|
use crate::Value;
|
||||||
|
|
@ -45,7 +46,7 @@ pub enum RuntimeError {
|
||||||
#[error("only objects have attributes")]
|
#[error("only objects have attributes")]
|
||||||
InvalidSetTarget,
|
InvalidSetTarget,
|
||||||
#[error("class {0} has no property {name}", class.name())]
|
#[error("class {0} has no property {name}", class.name())]
|
||||||
UndefinedAttribute { class: Rc<LoxClass>, name: Box<str> },
|
UndefinedAttribute { class: Rc<LoxClass>, name: SmolStr },
|
||||||
#[error("{value} is not a valid superclass")]
|
#[error("{value} is not a valid superclass")]
|
||||||
InvalidSuperclass { value: Value },
|
InvalidSuperclass { value: Value },
|
||||||
#[error("stack overflow")]
|
#[error("stack overflow")]
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@ use std::fmt::{Debug, Display};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
use rlox2_frontend::parser::Stmt;
|
use rlox2_frontend::parser::Stmt;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::environment::{ClosureScope, HeapedValue};
|
use crate::environment::{ClosureScope, HeapedValue};
|
||||||
|
|
||||||
|
|
@ -11,17 +12,17 @@ use super::{Runtime, Value};
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
pub struct LoxFunction {
|
pub struct LoxFunction {
|
||||||
name: Box<str>,
|
name: SmolStr,
|
||||||
closure: ClosureScope,
|
closure: ClosureScope,
|
||||||
param_names: Vec<Box<str>>,
|
param_names: Vec<SmolStr>,
|
||||||
body: Box<Stmt>,
|
body: Box<Stmt>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl LoxFunction {
|
impl LoxFunction {
|
||||||
pub fn new(
|
pub fn new(
|
||||||
name: impl Into<Box<str>>,
|
name: impl Into<SmolStr>,
|
||||||
closure: ClosureScope,
|
closure: ClosureScope,
|
||||||
param_names: Vec<Box<str>>,
|
param_names: Vec<SmolStr>,
|
||||||
body: Stmt,
|
body: Stmt,
|
||||||
) -> Rc<Self> {
|
) -> Rc<Self> {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
|
|
@ -43,7 +44,7 @@ impl LoxFunction {
|
||||||
&self.closure
|
&self.closure
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn param_names(&self) -> &[Box<str>] {
|
pub fn param_names(&self) -> &[SmolStr] {
|
||||||
&self.param_names
|
&self.param_names
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -55,7 +56,7 @@ impl LoxFunction {
|
||||||
self.param_names().len()
|
self.param_names().len()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn inject_closed_var(&mut self, name: impl Into<Box<str>>, value: Value) {
|
pub fn inject_closed_var(&mut self, name: impl Into<SmolStr>, value: Value) {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
let heaped_value = HeapedValue::new(value);
|
let heaped_value = HeapedValue::new(value);
|
||||||
self.closure.insert(name, heaped_value);
|
self.closure.insert(name, heaped_value);
|
||||||
|
|
|
||||||
|
|
@ -154,7 +154,8 @@ impl Eval for Expr {
|
||||||
if let Value::Object(object) = target {
|
if let Value::Object(object) = target {
|
||||||
object.get(name).ok_or_else(|| {
|
object.get(name).ok_or_else(|| {
|
||||||
let class = object.class();
|
let class = object.class();
|
||||||
let name = name.to_owned();
|
let name = name.clone();
|
||||||
|
|
||||||
RuntimeError::UndefinedAttribute { class, name }
|
RuntimeError::UndefinedAttribute { class, name }
|
||||||
})
|
})
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
|
|
@ -1,3 +1,5 @@
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::error::RuntimeError;
|
use crate::error::RuntimeError;
|
||||||
|
|
||||||
use super::function::{ExternFunClosure, LoxExternFunction};
|
use super::function::{ExternFunClosure, LoxExternFunction};
|
||||||
|
|
@ -47,7 +49,7 @@ fn clock() -> LoxExternFunction {
|
||||||
fn print_globals() -> LoxExternFunction {
|
fn print_globals() -> LoxExternFunction {
|
||||||
let closure: ExternFunClosure = |args, env| {
|
let closure: ExternFunClosure = |args, env| {
|
||||||
assert_eq!(args.len(), 0);
|
assert_eq!(args.len(), 0);
|
||||||
let mut globals: Vec<(&Box<str>, &Value)> = env.globals().iter().collect();
|
let mut globals: Vec<(&SmolStr, &Value)> = env.globals().iter().collect();
|
||||||
|
|
||||||
globals.sort_by_key(|&(name, _value)| name);
|
globals.sort_by_key(|&(name, _value)| name);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@ use std::fmt::Display;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::{LoxClass, Value};
|
use crate::{LoxClass, Value};
|
||||||
|
|
||||||
|
|
@ -12,7 +13,7 @@ use crate::{LoxClass, Value};
|
||||||
struct LoxObject {
|
struct LoxObject {
|
||||||
class: Rc<LoxClass>,
|
class: Rc<LoxClass>,
|
||||||
|
|
||||||
attrs: FxHashMap<Box<str>, Value>,
|
attrs: FxHashMap<SmolStr, Value>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl LoxObject {
|
impl LoxObject {
|
||||||
|
|
@ -35,7 +36,7 @@ impl LoxObject {
|
||||||
self.class.get_method(name, this)
|
self.class.get_method(name, this)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set(&mut self, name: impl Into<Box<str>>, value: Value) {
|
fn set(&mut self, name: impl Into<SmolStr>, value: Value) {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
self.attrs.insert(name, value);
|
self.attrs.insert(name, value);
|
||||||
}
|
}
|
||||||
|
|
@ -75,7 +76,7 @@ impl LoxReference {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set(&mut self, name: impl Into<Box<str>>, value: Value) {
|
pub fn set(&mut self, name: impl Into<SmolStr>, value: Value) {
|
||||||
unsafe {
|
unsafe {
|
||||||
let ptr = self.inner.get();
|
let ptr = self.inner.get();
|
||||||
let object = &mut *ptr;
|
let object = &mut *ptr;
|
||||||
|
|
|
||||||
|
|
@ -1,12 +1,13 @@
|
||||||
use rlox2_frontend::parser::{Expr, Stmt};
|
use rlox2_frontend::parser::{Expr, Stmt};
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::Runtime;
|
use crate::Runtime;
|
||||||
use crate::{LoxError, ResolverError};
|
use crate::{LoxError, ResolverError};
|
||||||
|
|
||||||
/*====================================================================================================================*/
|
/*====================================================================================================================*/
|
||||||
|
|
||||||
type ResolverScope = FxHashMap<Box<str>, ResolveStatus>;
|
type ResolverScope = FxHashMap<SmolStr, ResolveStatus>;
|
||||||
type ResolverFrame = Vec<ResolverScope>;
|
type ResolverFrame = Vec<ResolverScope>;
|
||||||
|
|
||||||
type ResolverResult<T> = Result<T, ResolverError>;
|
type ResolverResult<T> = Result<T, ResolverError>;
|
||||||
|
|
@ -37,11 +38,11 @@ struct Resolver {
|
||||||
// local_scopes: Vec<ResolverScope>,
|
// local_scopes: Vec<ResolverScope>,
|
||||||
frames: Vec<ResolverFrame>,
|
frames: Vec<ResolverFrame>,
|
||||||
|
|
||||||
closure_vars: FxHashMap<Box<str>, usize>,
|
closure_vars: FxHashMap<SmolStr, usize>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Resolver {
|
impl Resolver {
|
||||||
fn new(global_names: impl Iterator<Item = Box<str>>) -> Self {
|
fn new(global_names: impl Iterator<Item = SmolStr>) -> Self {
|
||||||
let mut global_scope = ResolverScope::default();
|
let mut global_scope = ResolverScope::default();
|
||||||
|
|
||||||
for name in global_names {
|
for name in global_names {
|
||||||
|
|
@ -83,7 +84,7 @@ impl Resolver {
|
||||||
.expect("Tried to pop non-existant ResolverFrame");
|
.expect("Tried to pop non-existant ResolverFrame");
|
||||||
}
|
}
|
||||||
|
|
||||||
fn declare(&mut self, name: impl Into<Box<str>>) -> ResolverResult<()> {
|
fn declare(&mut self, name: impl Into<SmolStr>) -> ResolverResult<()> {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
|
|
||||||
if let Some(local_scope) = self.local_scopes_mut().last_mut() {
|
if let Some(local_scope) = self.local_scopes_mut().last_mut() {
|
||||||
|
|
@ -100,7 +101,7 @@ impl Resolver {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
fn define(&mut self, name: impl Into<Box<str>>) {
|
fn define(&mut self, name: impl Into<SmolStr>) {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
|
|
||||||
if let Some(local_scope) = self.local_scopes_mut().last_mut() {
|
if let Some(local_scope) = self.local_scopes_mut().last_mut() {
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,12 @@
|
||||||
|
use smol_str::SmolStr;
|
||||||
use thiserror::Error;
|
use thiserror::Error;
|
||||||
|
|
||||||
#[derive(Error, Debug)]
|
#[derive(Error, Debug)]
|
||||||
pub enum ResolverError {
|
pub enum ResolverError {
|
||||||
#[error("can't read variable {name} in its own initializer.")]
|
#[error("can't read variable {name} in its own initializer.")]
|
||||||
VarInOwnInitializer { name: Box<str> },
|
VarInOwnInitializer { name: SmolStr },
|
||||||
#[error("variable {name} not defined")]
|
#[error("variable {name} not defined")]
|
||||||
UnresolvableVariable { name: Box<str> },
|
UnresolvableVariable { name: SmolStr },
|
||||||
#[error("return outside of function definition")]
|
#[error("return outside of function definition")]
|
||||||
ReturnOutsideFunction,
|
ReturnOutsideFunction,
|
||||||
#[error("this outside of method")]
|
#[error("this outside of method")]
|
||||||
|
|
@ -13,5 +14,5 @@ pub enum ResolverError {
|
||||||
#[error("super outside of subclass method")]
|
#[error("super outside of subclass method")]
|
||||||
SuperOutsideMethod,
|
SuperOutsideMethod,
|
||||||
#[error("local variable {name} declares multiple times")]
|
#[error("local variable {name} declares multiple times")]
|
||||||
LocalMulipleDeclarations { name: Box<str> },
|
LocalMulipleDeclarations { name: SmolStr },
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@ use std::io::{stdin, stdout, Read, Write};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::error::RuntimeError;
|
use crate::error::RuntimeError;
|
||||||
|
|
||||||
|
|
@ -11,7 +12,7 @@ use super::lox_std::init_std;
|
||||||
use super::Value;
|
use super::Value;
|
||||||
|
|
||||||
pub struct Runtime {
|
pub struct Runtime {
|
||||||
globals: FxHashMap<Box<str>, Value>,
|
globals: FxHashMap<SmolStr, Value>,
|
||||||
|
|
||||||
in_stream: Rc<RefCell<dyn std::io::Read>>,
|
in_stream: Rc<RefCell<dyn std::io::Read>>,
|
||||||
out_stream: Rc<RefCell<dyn std::io::Write>>,
|
out_stream: Rc<RefCell<dyn std::io::Write>>,
|
||||||
|
|
@ -53,7 +54,7 @@ impl Runtime {
|
||||||
self.out_stream.as_ref().borrow_mut()
|
self.out_stream.as_ref().borrow_mut()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn globals(&self) -> &FxHashMap<Box<str>, Value> {
|
pub fn globals(&self) -> &FxHashMap<SmolStr, Value> {
|
||||||
&self.globals
|
&self.globals
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -66,7 +67,7 @@ impl Runtime {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn define_global(&mut self, name: impl Into<Box<str>>, value: Value) {
|
pub fn define_global(&mut self, name: impl Into<SmolStr>, value: Value) {
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
self.globals.insert(name, value);
|
self.globals.insert(name, value);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,8 @@
|
||||||
use std::fmt::{Debug, Display};
|
use std::fmt::{Debug, Display};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
|
use smol_str::SmolStr;
|
||||||
|
|
||||||
use crate::{LoxClass, LoxReference};
|
use crate::{LoxClass, LoxReference};
|
||||||
|
|
||||||
use super::function::LoxExternFunction;
|
use super::function::LoxExternFunction;
|
||||||
|
|
@ -12,7 +14,7 @@ pub enum Value {
|
||||||
Class(Rc<LoxClass>),
|
Class(Rc<LoxClass>),
|
||||||
Function(Rc<LoxFunction>),
|
Function(Rc<LoxFunction>),
|
||||||
ExternFunction(Rc<LoxExternFunction>),
|
ExternFunction(Rc<LoxExternFunction>),
|
||||||
String(Box<str>),
|
String(SmolStr),
|
||||||
Number(f64),
|
Number(f64),
|
||||||
Bool(bool),
|
Bool(bool),
|
||||||
#[default]
|
#[default]
|
||||||
|
|
@ -34,7 +36,7 @@ impl Value {
|
||||||
Value::ExternFunction(fun)
|
Value::ExternFunction(fun)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn string(s: impl Into<Box<str>>) -> Self {
|
pub fn string(s: impl Into<SmolStr>) -> Self {
|
||||||
let s = s.into();
|
let s = s.into();
|
||||||
Value::String(s)
|
Value::String(s)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -9,10 +9,10 @@ path = "../frontend"
|
||||||
|
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
itertools = "0.13"
|
itertools = "0.13.0"
|
||||||
lazy_static = "1"
|
lazy_static = "1.5.0"
|
||||||
num-derive = "0.4"
|
num-derive = "0.4.2"
|
||||||
num-traits = "0.2"
|
num-traits = "0.2.19"
|
||||||
regex = "1"
|
regex = "1.10.6"
|
||||||
thiserror = "1"
|
static_assertions = "1.1.0"
|
||||||
static_assertions = "1"
|
thiserror = "1.0.63"
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue