Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Optimise type comparisons #441

Merged
merged 58 commits into from
Jun 10, 2020
Merged
Show file tree
Hide file tree
Changes from 55 commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
c4fb91c
Merge pull request #4 from boa-dev/master
May 26, 2020
7ffc0c8
Adding Object Execution trait
May 26, 2020
57fa83d
Moved Object AST related parts into their own files
May 26, 2020
88a5ba3
Rustfmt
May 26, 2020
e51d8be
Make clippy happier
May 26, 2020
4c058c0
Starting to reimplement switch
May 26, 2020
744dee8
Remove extra newline
May 27, 2020
dc6b371
Replaced AST object new with From
May 27, 2020
8995fb2
Merge branch 'divide_run' of https://github.com/Lan2u/boa into divide…
May 27, 2020
d91ac61
Rustfmt
May 27, 2020
274910a
Merge pull request #5 from Lan2u/divide_run
May 27, 2020
4b0bed1
Starting to move switch AST into seperate files
May 27, 2020
8ff5590
Seperated switch AST node into seperate files
May 27, 2020
d0e82b5
Merge: Seperated switch AST node into seperate files
May 27, 2020
6851036
Started moving GetConstField related parts into own file
May 27, 2020
153f0b1
Correcting various references to Node::GetConstField to use new signa…
May 28, 2020
c0404f3
Extracted GetField code
May 29, 2020
e33a1a5
Fmt, clippy
May 29, 2020
9969748
Merge pull request #7 from Lan2u/divide_run_get_const_field
May 29, 2020
4937dc3
WhileLoop
May 29, 2020
ad07527
Impl fmt::display for WhileLoop
May 29, 2020
be04070
DoWhileLoop struct created
May 29, 2020
58f83f7
Seperated out do while loop
May 29, 2020
26fdf9d
Merge pull request #8 from Lan2u/divide_run_dowhile
May 30, 2020
13daec1
Created Return struct
May 30, 2020
2116152
Seperated Return statement out
May 30, 2020
cc7261a
Seperated IF statement out
May 30, 2020
c858a79
Removed unused imports, fmt
May 30, 2020
b5ca4b8
Created Break struct
May 30, 2020
94dcacc
Break impl
May 31, 2020
5c90059
Conditional Op impl
May 31, 2020
4e267c3
Continue impl
May 31, 2020
e3882d7
Throw impl
May 31, 2020
bb33532
Spread impl
May 31, 2020
022b48e
Object initalizer now returns Object in result rather than Node
May 31, 2020
57cace0
Update boa/src/exec/throw/mod.rs
Jun 1, 2020
e96f79c
Update boa/src/syntax/ast/node/break_node.rs
Jun 1, 2020
44da6aa
Update boa/src/syntax/ast/node/conditional.rs
Jun 1, 2020
43a046f
Update boa/src/syntax/ast/node/iteration.rs
Jun 1, 2020
7604c0f
Made Switch::new() more generic, added TODO for break in Switch::run()
Jun 1, 2020
ba5a63b
Merge branch 'divide_run' of https://github.com/Lan2u/boa into divide…
Jun 1, 2020
b7a641b
Making parse functions return the actual result of the parse rather t…
Jun 1, 2020
ea45b26
Reworked switch::new, added Case struct
Jun 1, 2020
7733da2
Switch::run() refractored, rustfmt
Jun 1, 2020
a96eef4
Replaced str return for get_type() with a Type enum
Jun 1, 2020
67a4364
Updated usages of get_type
Jun 1, 2020
6607674
Merge branch 'master' into optimise_type_comparisons
Jun 1, 2020
75ba7f6
Renamed Type:Str to Type:String
Jun 1, 2020
93273ae
Removed fmt::Display and replaced with as_str
Jun 1, 2020
d4f5b72
Merge branch 'master' into optimise_type_comparisons
Jun 3, 2020
7a27f52
Merge branch 'master' into optimise_type_comparisons
Jun 5, 2020
4b1a5c2
Fixed merge problems
Jun 5, 2020
7056c90
Merge branch 'master' into optimise_type_comparisons
Jun 6, 2020
ef22dd3
Fixed merge issues
Jun 6, 2020
7526e40
Addressed PR comments
Jun 7, 2020
35aab1d
Added some tests
Jun 7, 2020
4df529f
Merge branch 'master' into optimise_type_comparisons
Jun 10, 2020
f9d692d
Fixed merge conflict
Jun 10, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 5 additions & 10 deletions boa/src/builtins/value/equality.rs
Original file line number Diff line number Diff line change
Expand Up @@ -200,16 +200,11 @@ pub fn same_value_zero(x: &Value, y: &Value) -> bool {
pub fn same_value_non_numeric(x: &Value, y: &Value) -> bool {
debug_assert!(x.get_type() == y.get_type());
match x.get_type() {
"undefined" => true,
"null" => true,
"string" => {
if x.to_string() == y.to_string() {
return true;
}
false
}
"boolean" => bool::from(x) == bool::from(y),
"object" => std::ptr::eq(x, y),
Type::Undefined => true,
Type::Null => true,
Type::String => x.to_string() == y.to_string(),
Type::Boolean => bool::from(x) == bool::from(y),
Type::Object => std::ptr::eq(x, y),
_ => false,
}
}
27 changes: 4 additions & 23 deletions boa/src/builtins/value/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@
#[cfg(test)]
mod tests;

pub mod val_type;

pub use crate::builtins::value::val_type::Type;

use crate::builtins::{
object::{
internal_methods_trait::ObjectInternalMethods, InternalState, InternalStateCell, Object,
Expand Down Expand Up @@ -759,29 +763,6 @@ impl ValueData {
}
}
}

/// Get the type of the value
///
/// https://tc39.es/ecma262/#sec-typeof-operator
pub fn get_type(&self) -> &'static str {
let _timer = BoaProfiler::global().start_event("Value::get_type", "value");
match *self {
Self::Rational(_) | Self::Integer(_) => "number",
Self::String(_) => "string",
Self::Boolean(_) => "boolean",
Self::Symbol(_) => "symbol",
Self::Null => "object",
Self::Undefined => "undefined",
Self::Object(ref o) => {
if o.deref().borrow().is_callable() {
"function"
} else {
"object"
}
}
Self::BigInt(_) => "bigint",
}
}
}

impl Default for ValueData {
Expand Down
2 changes: 1 addition & 1 deletion boa/src/builtins/value/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ fn check_string_to_value() {
#[test]
fn check_undefined() {
let u = ValueData::Undefined;
assert_eq!(u.get_type(), "undefined");
assert_eq!(u.get_type(), Type::Undefined);
assert_eq!(u.to_string(), "undefined");
}

Expand Down
59 changes: 59 additions & 0 deletions boa/src/builtins/value/val_type.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
use crate::builtins::value::ValueData;
use std::ops::Deref;

/// Possible types of val as defined at https://tc39.es/ecma262/#sec-typeof-operator.
/// Note that an object which implements call is referred to here as 'Function'.
#[derive(Eq, PartialEq, Debug, Clone, Copy)]
pub enum Type {
Undefined,
Null,
Boolean,
Number,
String,
Symbol,
BigInt,
Object,
Function,
}

impl Type {
pub fn as_str(&self) -> &str {
match self {
Self::Number => "number",
Self::String => "string",
Self::Boolean => "boolean",
Self::Symbol => "symbol",
Self::Null => "object",
Self::Undefined => "undefined",
Self::Function => "function",
Self::Object => "object",
Self::BigInt => "bigint",
}
}
}

impl ValueData {
/// Get the type of the value.
///
/// This is similar to typeof as described at https://tc39.es/ecma262/#sec-typeof-operator but instead of
/// returning a string it returns a Type enum which implements fmt::Display to allow getting the string if
/// required using to_string().
pub fn get_type(&self) -> Type {
match *self {
Self::Rational(_) | Self::Integer(_) => Type::Number,
Self::String(_) => Type::String,
Self::Boolean(_) => Type::Boolean,
Self::Symbol(_) => Type::Symbol,
Self::Null => Type::Null,
Self::Undefined => Type::Undefined,
Self::Object(ref o) => {
if o.deref().borrow().is_callable() {
Type::Function
} else {
Type::Object
}
}
Self::BigInt(_) => Type::BigInt,
}
}
}
7 changes: 3 additions & 4 deletions boa/src/exec/conditional/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,10 @@ impl Executable for If {
fn run(&self, interpreter: &mut Interpreter) -> ResultValue {
Ok(if self.cond().run(interpreter)?.borrow().is_true() {
self.body().run(interpreter)?
} else if let Some(ref else_e) = self.else_node() {
else_e.run(interpreter)?
} else {
match self.else_node() {
Some(ref else_e) => else_e.run(interpreter)?,
None => Value::undefined(),
}
Value::undefined()
})
}
}
4 changes: 2 additions & 2 deletions boa/src/exec/expression/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ use super::{Executable, Interpreter};
use crate::{
builtins::{
object::{INSTANCE_PROTOTYPE, PROTOTYPE},
value::{ResultValue, Value, ValueData},
value::{ResultValue, Type, Value, ValueData},
},
syntax::ast::node::{Call, New, Node},
BoaProfiler,
Expand All @@ -16,7 +16,7 @@ impl Executable for Call {
let (mut this, func) = match self.expr() {
Node::GetConstField(ref get_const_field) => {
let mut obj = get_const_field.obj().run(interpreter)?;
if obj.get_type() != "object" || obj.get_type() != "symbol" {
if obj.get_type() != Type::Object || obj.get_type() != Type::Symbol {
obj = interpreter
.to_object(&obj)
.expect("failed to convert to object");
Expand Down
4 changes: 2 additions & 2 deletions boa/src/exec/field/mod.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
use super::{Executable, Interpreter};
use crate::{
builtins::value::ResultValue,
builtins::value::{ResultValue, Type},
syntax::ast::node::{GetConstField, GetField},
};

impl Executable for GetConstField {
fn run(&self, interpreter: &mut Interpreter) -> ResultValue {
let mut obj = self.obj().run(interpreter)?;
if obj.get_type() != "object" || obj.get_type() != "symbol" {
if obj.get_type() != Type::Object || obj.get_type() != Type::Symbol {
obj = interpreter
.to_object(&obj)
.expect("failed to convert to object");
Expand Down
4 changes: 2 additions & 2 deletions boa/src/exec/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ use crate::{
PROTOTYPE,
},
property::Property,
value::{ResultValue, Value, ValueData},
value::{ResultValue, Type, Value, ValueData},
BigInt, Number,
},
realm::Realm,
Expand Down Expand Up @@ -222,7 +222,7 @@ impl Interpreter {

/// <https://tc39.es/ecma262/#sec-ordinarytoprimitive>
pub(crate) fn ordinary_to_primitive(&mut self, o: &mut Value, hint: &str) -> Value {
debug_assert!(o.get_type() == "object");
debug_assert!(o.get_type() == Type::Object);
debug_assert!(hint == "string" || hint == "number");
let method_names: Vec<&str> = if hint == "string" {
vec!["toString", "valueOf"]
Expand Down
4 changes: 2 additions & 2 deletions boa/src/exec/operator/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ impl Executable for BinOp {
if !v_b.is_object() {
return interpreter.throw_type_error(format!(
"right-hand side of 'in' should be an object, got {}",
v_b.get_type()
v_b.get_type().as_str()
));
}
let key = interpreter.to_property_key(&mut v_a)?;
Expand Down Expand Up @@ -219,7 +219,7 @@ impl Executable for UnaryOp {
| Node::UnaryOp(_) => Value::boolean(true),
_ => panic!("SyntaxError: wrong delete argument {}", self),
},
op::UnaryOp::TypeOf => Value::from(v_a.get_type()),
op::UnaryOp::TypeOf => Value::from(v_a.get_type().as_str()),
})
}
}
1 change: 1 addition & 0 deletions boa/src/syntax/parser/statement/break_stm/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
mod tests;

use super::LabelIdentifier;

use crate::{
syntax::{
ast::{node::Break, Keyword, Punctuator, TokenKind},
Expand Down
5 changes: 3 additions & 2 deletions boa/src/syntax/parser/statement/continue_stm/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,12 @@
#[cfg(test)]
mod tests;

use super::LabelIdentifier;
use crate::{
syntax::{
ast::{node::Continue, Keyword, Punctuator, TokenKind},
parser::{AllowAwait, AllowYield, Cursor, ParseError, TokenParser},
parser::{
statement::LabelIdentifier, AllowAwait, AllowYield, Cursor, ParseError, TokenParser,
},
},
BoaProfiler,
};
Expand Down
1 change: 1 addition & 0 deletions boa/src/syntax/parser/statement/declaration/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ mod lexical;
mod tests;

use self::{hoistable::HoistableDeclaration, lexical::LexicalDeclaration};

Razican marked this conversation as resolved.
Show resolved Hide resolved
use crate::{
syntax::{
ast::{Keyword, Node, TokenKind},
Expand Down
1 change: 1 addition & 0 deletions boa/src/syntax/parser/statement/if_stm/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
mod tests;

use super::Statement;

Razican marked this conversation as resolved.
Show resolved Hide resolved
use crate::{
syntax::{
ast::{node::If, Keyword, Node, Punctuator, TokenKind},
Expand Down