Skip to content

Commit

Permalink
Merge 222c5c7 into fb8c5cf
Browse files Browse the repository at this point in the history
  • Loading branch information
HalidOdat authored Mar 3, 2022
2 parents fb8c5cf + 222c5c7 commit 09d99dd
Show file tree
Hide file tree
Showing 57 changed files with 1,498 additions and 835 deletions.
13 changes: 12 additions & 1 deletion boa_engine/src/bigint.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
//! This module implements the JavaScript bigint primitive rust type.
use crate::{builtins::Number, Context, JsValue};
use crate::{builtins::Number, value::PointerType, Context, JsValue};
use boa_gc::{unsafe_empty_trace, Finalize, Trace};
use num_integer::Integer;
use num_traits::{pow::Pow, FromPrimitive, One, ToPrimitive, Zero};
use std::{
fmt::{self, Display},
mem::{self, ManuallyDrop},
ops::{Add, BitAnd, BitOr, BitXor, Div, Mul, Neg, Rem, Shl, Shr, Sub},
rc::Rc,
};
Expand All @@ -23,6 +24,16 @@ pub struct JsBigInt {
inner: Rc<RawBigInt>,
}

unsafe impl PointerType for JsBigInt {
unsafe fn from_void_ptr(ptr: *mut ()) -> ManuallyDrop<Self> {
ManuallyDrop::new(mem::transmute(ptr))
}

unsafe fn into_void_ptr(bigint: ManuallyDrop<Self>) -> *mut () {
mem::transmute(bigint)
}
}

// Safety: BigInt does not contain any objects which needs to be traced,
// so this is safe.
unsafe impl Trace for JsBigInt {
Expand Down
3 changes: 2 additions & 1 deletion boa_engine/src/builtins/array/array_iterator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,8 @@ impl ArrayIterator {
///
/// [spec]: https://tc39.es/ecma262/#sec-%arrayiteratorprototype%.next
pub(crate) fn next(this: &JsValue, _: &[JsValue], context: &mut Context) -> JsResult<JsValue> {
let mut array_iterator = this.as_object().map(JsObject::borrow_mut);
let array_iterator = this.as_object();
let mut array_iterator = array_iterator.as_ref().map(JsObject::borrow_mut);
let array_iterator = array_iterator
.as_mut()
.and_then(|obj| obj.as_array_iterator_mut())
Expand Down
20 changes: 9 additions & 11 deletions boa_engine/src/builtins/array/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ use crate::{
},
property::{Attribute, PropertyDescriptor, PropertyNameKind},
symbol::WellKnownSymbols,
value::{IntegerOrInfinity, JsValue},
value::{IntegerOrInfinity, JsValue, JsVariant},
Context, JsResult, JsString,
};
use std::cmp::{max, min, Ordering};
Expand Down Expand Up @@ -363,8 +363,7 @@ impl Array {
Ok(
c.construct(&[JsValue::new(length)], &c.clone().into(), context)?
.as_object()
.expect("constructing an object should always return an object")
.clone(),
.expect("constructing an object should always return an object"),
)
} else {
context.throw_type_error("Symbol.species must be a constructor")
Expand Down Expand Up @@ -416,7 +415,6 @@ impl Array {
Some(constructor) => constructor
.construct(&[len.into()], this, context)?
.as_object()
.cloned()
.ok_or_else(|| {
context.construct_type_error("object constructor didn't return an object")
})?,
Expand Down Expand Up @@ -1537,7 +1535,7 @@ impl Array {
source_len as u64,
0,
1,
Some(mapper_function),
Some(&mapper_function),
args.get_or_undefined(1),
context,
)?;
Expand Down Expand Up @@ -1627,7 +1625,7 @@ impl Array {
// 4. Set targetIndex to ? FlattenIntoArray(target, element, elementLen, targetIndex, newDepth)
target_index = Self::flatten_into_array(
target,
element,
&element,
element_len as u64,
target_index,
new_depth,
Expand Down Expand Up @@ -2164,9 +2162,9 @@ impl Array {
context: &mut Context,
) -> JsResult<JsValue> {
// 1. If comparefn is not undefined and IsCallable(comparefn) is false, throw a TypeError exception.
let comparefn = match args.get_or_undefined(0) {
JsValue::Object(ref obj) if obj.is_callable() => Some(obj),
JsValue::Undefined => None,
let comparefn = match args.get_or_undefined(0).variant() {
JsVariant::Object(obj) if obj.is_callable() => Some(obj),
JsVariant::Undefined => None,
_ => {
return context.throw_type_error(
"The comparison function must be either a function or undefined",
Expand All @@ -2193,11 +2191,11 @@ impl Array {
}

// 4. If comparefn is not undefined, then
if let Some(cmp) = comparefn {
if let Some(ref cmp) = comparefn {
let args = [x.clone(), y.clone()];
// a. Let v be ? ToNumber(? Call(comparefn, undefined, « x, y »)).
let v = cmp
.call(&JsValue::Undefined, &args, context)?
.call(&JsValue::undefined(), &args, context)?
.to_number(context)?;
// b. If v is NaN, return +0𝔽.
// c. Return v.
Expand Down
4 changes: 2 additions & 2 deletions boa_engine/src/builtins/array_buffer/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -236,7 +236,7 @@ impl ArrayBuffer {
let new = ctor.construct(&[new_len.into()], &ctor.clone().into(), context)?;

// 17. Perform ? RequireInternalSlot(new, [[ArrayBufferData]]).
let new_obj = new.as_object().cloned().ok_or_else(|| {
let new_obj = new.as_object().ok_or_else(|| {
context.construct_type_error("ArrayBuffer constructor returned non-object value")
})?;

Expand Down Expand Up @@ -324,7 +324,7 @@ impl ArrayBuffer {
obj.borrow_mut().data = ObjectData::array_buffer(Self {
array_buffer_data: Some(block),
array_buffer_byte_length: byte_length,
array_buffer_detach_key: JsValue::Undefined,
array_buffer_detach_key: JsValue::undefined(),
});

// 5. Return obj.
Expand Down
1 change: 0 additions & 1 deletion boa_engine/src/builtins/bigint/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,6 @@ impl BigInt {
value
// 1. If Type(value) is BigInt, return value.
.as_bigint()
.cloned()
// 2. If Type(value) is Object and value has a [[BigIntData]] internal slot, then
// a. Assert: Type(value.[[BigIntData]]) is BigInt.
// b. Return value.[[BigIntData]].
Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/boolean/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,6 @@ fn instances_have_correct_proto_set() {

assert_eq!(
&*bool_instance.as_object().unwrap().prototype(),
&bool_prototype.as_object().cloned()
&bool_prototype.as_object()
);
}
17 changes: 11 additions & 6 deletions boa_engine/src/builtins/dataview/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -167,7 +167,7 @@ impl DataView {
prototype,
ObjectData::data_view(Self {
// 11. Set O.[[ViewedArrayBuffer]] to buffer.
viewed_array_buffer: buffer_obj.clone(),
viewed_array_buffer: buffer_obj,
// 12. Set O.[[ByteLength]] to viewByteLength.
byte_length: view_byte_length,
// 13. Set O.[[ByteOffset]] to offset.
Expand Down Expand Up @@ -197,7 +197,8 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
let dataview = this.as_object().map(JsObject::borrow);
let dataview = this.as_object();
let dataview = dataview.as_ref().map(JsObject::borrow);
let dataview = dataview
.as_ref()
.and_then(|obj| obj.as_data_view())
Expand Down Expand Up @@ -226,7 +227,8 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
let dataview = this.as_object().map(JsObject::borrow);
let dataview = this.as_object();
let dataview = dataview.as_ref().map(JsObject::borrow);
let dataview = dataview
.as_ref()
.and_then(|obj| obj.as_data_view())
Expand Down Expand Up @@ -265,7 +267,8 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
let dataview = this.as_object().map(JsObject::borrow);
let dataview = this.as_object();
let dataview = dataview.as_ref().map(JsObject::borrow);
let dataview = dataview
.as_ref()
.and_then(|obj| obj.as_data_view())
Expand Down Expand Up @@ -305,7 +308,8 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Perform ? RequireInternalSlot(view, [[DataView]]).
// 2. Assert: view has a [[ViewedArrayBuffer]] internal slot.
let view = view.as_object().map(JsObject::borrow);
let view = view.as_object();
let view = view.as_ref().map(JsObject::borrow);
let view = view
.as_ref()
.and_then(|obj| obj.as_data_view())
Expand Down Expand Up @@ -664,7 +668,8 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Perform ? RequireInternalSlot(view, [[DataView]]).
// 2. Assert: view has a [[ViewedArrayBuffer]] internal slot.
let view = view.as_object().map(JsObject::borrow);
let view = view.as_object();
let view = view.as_ref().map(JsObject::borrow);
let view = view
.as_ref()
.and_then(|obj| obj.as_data_view())
Expand Down
35 changes: 18 additions & 17 deletions boa_engine/src/builtins/date/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ use crate::{
},
property::Attribute,
symbol::WellKnownSymbols,
value::{JsValue, PreferredType},
value::{JsValue, JsVariant, PreferredType},
Context, JsResult, JsString,
};
use boa_gc::{unsafe_empty_trace, Finalize, Trace};
Expand Down Expand Up @@ -400,24 +400,25 @@ impl Date {
context: &mut Context,
) -> JsResult<JsObject> {
let value = &args[0];
let tv = match this_time_value(value, context) {
Ok(dt) => dt.0,
_ => match value.to_primitive(context, PreferredType::Default)? {
JsValue::String(ref str) => match chrono::DateTime::parse_from_rfc3339(str) {
let tv = if let Ok(dt) = this_time_value(value, context) {
dt.0
} else {
let tv = value.to_primitive(context, PreferredType::Default)?;
if let JsVariant::String(ref str) = tv.variant() {
match chrono::DateTime::parse_from_rfc3339(str) {
Ok(dt) => Some(dt.naive_utc()),
_ => None,
},
tv => {
let tv = tv.to_number(context)?;
if tv.is_nan() {
None
} else {
let secs = (tv / 1_000f64) as i64;
let nano_secs = ((tv % 1_000f64) * 1_000_000f64) as u32;
NaiveDateTime::from_timestamp_opt(secs, nano_secs)
}
}
},
} else {
let tv = tv.to_number(context)?;
if tv.is_nan() {
None
} else {
let secs = (tv / 1_000f64) as i64;
let nano_secs = ((tv % 1_000f64) * 1_000_000f64) as u32;
NaiveDateTime::from_timestamp_opt(secs, nano_secs)
}
}
};

let tv = tv.filter(|time| Self::time_clip(time.timestamp_millis() as f64).is_some());
Expand Down Expand Up @@ -522,7 +523,7 @@ impl Date {

let hint = args.get_or_undefined(0);

let try_first = match hint.as_string().map(JsString::as_str) {
let try_first = match hint.as_string().as_ref().map(JsString::as_str) {
// 3. If hint is "string" or "default", then
// a. Let tryFirst be string.
Some("string" | "default") => PreferredType::String,
Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/date/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ fn forward_dt_utc(context: &mut Context, src: &str) -> Option<NaiveDateTime> {
panic!("expected success")
};

if let JsValue::Object(ref date_time) = date_time {
if let Some(date_time) = date_time.as_object() {
if let Some(date_time) = date_time.borrow().as_date() {
date_time.0
} else {
Expand Down
1 change: 0 additions & 1 deletion boa_engine/src/builtins/function/arguments.rs
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,6 @@ impl Arguments {
// In the case of duplicate parameter names, the last one is bound as the environment binding.
//
// The following logic implements the steps 17-19 adjusted for our environment structure.

let mut bindings = FxHashMap::default();
let mut property_index = 0;
'outer: for formal in formals.parameters.iter() {
Expand Down
7 changes: 3 additions & 4 deletions boa_engine/src/builtins/function/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -392,9 +392,7 @@ impl BuiltInFunctionObject {
let target_name = target.get("name", context)?;

// 9. If Type(targetName) is not String, set targetName to the empty String.
let target_name = target_name
.as_string()
.map_or(JsString::new(""), Clone::clone);
let target_name = target_name.as_string().unwrap_or_default();

// 10. Perform SetFunctionName(F, targetName, "bound").
set_function_name(&f, &target_name.into(), Some("bound"), context);
Expand Down Expand Up @@ -430,7 +428,8 @@ impl BuiltInFunctionObject {

#[allow(clippy::wrong_self_convention)]
fn to_string(this: &JsValue, _: &[JsValue], context: &mut Context) -> JsResult<JsValue> {
let object = this.as_object().map(JsObject::borrow);
let object = this.as_object();
let object = object.as_ref().map(JsObject::borrow);
let function = object
.as_deref()
.and_then(Object::as_function)
Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/function/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -246,7 +246,7 @@ fn closure_capture_clone() {
object
.__get_own_property__(&"key".into(), context)?
.and_then(|prop| prop.value().cloned())
.and_then(|val| val.as_string().cloned())
.and_then(|val| val.as_string())
.ok_or_else(|| context.construct_type_error("invalid `key` property"))?,
);
Ok(hw.into())
Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/generator/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ impl Generator {
// 1. Return ? GeneratorResume(this value, value, empty).
match this.as_object() {
Some(obj) if obj.is_generator() => {
Self::generator_resume(obj, args.get_or_undefined(0), context)
Self::generator_resume(&obj, args.get_or_undefined(0), context)
}
_ => context.throw_type_error("Generator.prototype.next called on non generator"),
}
Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/generator_function/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ impl BuiltIn for GeneratorFunction {
.borrow_mut()
.insert(WellKnownSymbols::to_string_tag(), property);

JsValue::Null
JsValue::null()
}
}

Expand Down
2 changes: 1 addition & 1 deletion boa_engine/src/builtins/intl/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ impl Intl {
// 1. Let ll be ? CanonicalizeLocaleList(locales).
let ll = Self::canonicalize_locale_list(args, context)?;
// 2. Return CreateArrayFromList(ll).
Ok(JsValue::Object(Array::create_array_from_list(
Ok(JsValue::new(Array::create_array_from_list(
ll.into_iter().map(Into::into),
context,
)))
Expand Down
6 changes: 3 additions & 3 deletions boa_engine/src/builtins/iterable/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@ impl JsValue {
// 1. Let syncMethod be ? GetMethod(obj, @@iterator).
let sync_method = self
.get_method(WellKnownSymbols::iterator(), context)?
.map_or(Self::Undefined, Self::from);
.map_or(Self::undefined(), Self::from);
// 2. Let syncIteratorRecord be ? GetIterator(obj, sync, syncMethod).
let _sync_iterator_record =
self.get_iterator(context, Some(IteratorHint::Sync), Some(sync_method));
Expand All @@ -147,7 +147,7 @@ impl JsValue {
} else {
// b. Otherwise, set method to ? GetMethod(obj, @@iterator).
self.get_method(WellKnownSymbols::iterator(), context)?
.map_or(Self::Undefined, Self::from)
.map_or(Self::undefined(), Self::from)
}
};

Expand Down Expand Up @@ -285,7 +285,7 @@ impl IteratorRecord {
// 3. If Type(result) is not Object, throw a TypeError exception.
// 4. Return result.
if let Some(o) = result.as_object() {
Ok(IteratorResult { object: o.clone() })
Ok(IteratorResult { object: o })
} else {
context.throw_type_error("next value should be an object")
}
Expand Down
Loading

0 comments on commit 09d99dd

Please sign in to comment.