Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
49 changes: 11 additions & 38 deletions core/engine/src/builtins/array_buffer/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -496,19 +496,12 @@ impl ArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is true, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("get ArrayBuffer.prototype.byteLength called with invalid `this`")
})?;
let buf = require_internal_slot!(this, Self, "ArrayBuffer");

// 4. If IsDetachedBuffer(O) is true, return +0𝔽.
// 5. Let length be O.[[ArrayBufferByteLength]].
// 6. Return 𝔽(length).
Ok(buf.len().into())
Ok(buf.borrow().data().len().into())
}

/// [`get ArrayBuffer.prototype.maxByteLength`][spec].
Expand All @@ -522,18 +515,12 @@ impl ArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is true, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ().with_message(
"get ArrayBuffer.prototype.maxByteLength called with invalid `this`",
)
})?;
let buf = require_internal_slot!(this, Self, "ArrayBuffer");

// 4. If IsDetachedBuffer(O) is true, return +0𝔽.
let Some(data) = buf.bytes() else {
let buf_data = buf.borrow();
let buf_data = buf_data.data();
let Some(data) = buf_data.bytes() else {
return Ok(JsValue::from(0));
};

Expand All @@ -542,7 +529,7 @@ impl ArrayBuffer {
// 6. Else,
// a. Let length be O.[[ArrayBufferMaxByteLength]].
// 7. Return 𝔽(length).
Ok(buf.max_byte_len.unwrap_or(data.len() as u64).into())
Ok(buf_data.max_byte_len.unwrap_or(data.len() as u64).into())
}

/// [`get ArrayBuffer.prototype.resizable`][spec].
Expand All @@ -556,17 +543,10 @@ impl ArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is true, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("get ArrayBuffer.prototype.resizable called with invalid `this`")
})?;
let buf = require_internal_slot!(this, Self, "ArrayBuffer");

// 4. If IsFixedLengthArrayBuffer(O) is false, return true; otherwise return false.
Ok(JsValue::from(!buf.is_fixed_len()))
Ok(JsValue::from(!buf.borrow().data().is_fixed_len()))
}

/// [`get ArrayBuffer.prototype.detached`][spec].
Expand All @@ -581,17 +561,10 @@ impl ArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is true, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("get ArrayBuffer.prototype.detached called with invalid `this`")
})?;
let buf = require_internal_slot!(this, Self, "ArrayBuffer");

// 4. Return IsDetachedBuffer(O).
Ok(buf.is_detached().into())
Ok(buf.borrow().data().is_detached().into())
}

/// [`ArrayBuffer.prototype.resize ( newLength )`][spec].
Expand Down
33 changes: 6 additions & 27 deletions core/engine/src/builtins/array_buffer/shared.rs
Original file line number Diff line number Diff line change
Expand Up @@ -225,17 +225,10 @@ impl SharedArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is true, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("SharedArrayBuffer.byteLength called with invalid value")
})?;
let buf = require_internal_slot!(this, Self, "SharedArrayBuffer");

// 4. Let length be ArrayBufferByteLength(O, seq-cst).
let len = buf.bytes(Ordering::SeqCst).len() as u64;
let len = buf.borrow().data().bytes(Ordering::SeqCst).len() as u64;

// 5. Return 𝔽(length).
Ok(len.into())
Expand All @@ -252,17 +245,10 @@ impl SharedArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is false, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("get SharedArrayBuffer.growable called with invalid `this`")
})?;
let buf = require_internal_slot!(this, Self, "SharedArrayBuffer");

// 4. If IsFixedLengthArrayBuffer(O) is false, return true; otherwise return false.
Ok(JsValue::from(!buf.is_fixed_len()))
Ok(JsValue::from(!buf.borrow().data().is_fixed_len()))
}

/// [`get SharedArrayBuffer.prototype.maxByteLength`][spec].
Expand All @@ -276,21 +262,14 @@ impl SharedArrayBuffer {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[ArrayBufferData]]).
// 3. If IsSharedArrayBuffer(O) is false, throw a TypeError exception.
let object = this.as_object();
let buf = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| {
JsNativeError::typ()
.with_message("get SharedArrayBuffer.maxByteLength called with invalid value")
})?;
let buf = require_internal_slot!(this, Self, "SharedArrayBuffer");

// 4. If IsFixedLengthArrayBuffer(O) is true, then
// a. Let length be O.[[ArrayBufferByteLength]].
// 5. Else,
// a. Let length be O.[[ArrayBufferMaxByteLength]].
// 6. Return 𝔽(length).
Ok(buf.data.buffer.len().into())
Ok(buf.borrow().data().data.buffer.len().into())
}

/// [`SharedArrayBuffer.prototype.grow ( newLength )`][spec].
Expand Down
74 changes: 34 additions & 40 deletions core/engine/src/builtins/dataview/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -331,14 +331,11 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
let object = this.as_object();
let view = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| JsNativeError::typ().with_message("`this` is not a DataView"))?;
let view = require_internal_slot!(this, Self, "DataView");
// 3. Assert: O has a [[ViewedArrayBuffer]] internal slot.
// 4. Let buffer be O.[[ViewedArrayBuffer]].
let buffer = view.viewed_array_buffer.clone();
let view_data = view.borrow();
let buffer = view_data.data().viewed_array_buffer.clone();
// 5. Return buffer.
Ok(buffer.into())
}
Expand All @@ -361,26 +358,24 @@ impl DataView {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
// 3. Assert: O has a [[ViewedArrayBuffer]] internal slot.
let object = this.as_object();
let view = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| JsNativeError::typ().with_message("`this` is not a DataView"))?;
let view = require_internal_slot!(this, Self, "DataView");

// 4. Let viewRecord be MakeDataViewWithBufferWitnessRecord(O, seq-cst).
// 5. If IsViewOutOfBounds(viewRecord) is true, throw a TypeError exception.
let buffer = view.viewed_array_buffer.as_buffer();
let view_data = view.borrow();
let buffer = view_data.data().viewed_array_buffer.as_buffer();
let Some(slice) = buffer
.bytes(Ordering::SeqCst)
.filter(|s| !view.is_out_of_bounds(s.len()))
.filter(|s| !view.borrow().data().is_out_of_bounds(s.len()))
else {
return Err(JsNativeError::typ()
.with_message("view out of bounds for its inner buffer")
.into());
};

// 6. Let size be GetViewByteLength(viewRecord).
let size = view.byte_length(slice.len());
let view_data = view.borrow();
let size = view_data.data().byte_length(slice.len());

// 7. Return 𝔽(size).
Ok(size.into())
Expand All @@ -404,19 +399,16 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Let O be the this value.
// 2. Perform ? RequireInternalSlot(O, [[DataView]]).
let object = this.as_object();
let view = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| JsNativeError::typ().with_message("`this` is not a DataView"))?;
let view = require_internal_slot!(this, Self, "DataView");

// 3. Assert: O has a [[ViewedArrayBuffer]] internal slot.
let buffer = view.viewed_array_buffer.as_buffer();
let view_data = view.borrow();
let buffer = view_data.data().viewed_array_buffer.as_buffer();
// 4. Let viewRecord be MakeDataViewWithBufferWitnessRecord(O, seq-cst).
// 5. If IsViewOutOfBounds(viewRecord) is true, throw a TypeError exception.
if buffer
.bytes(Ordering::SeqCst)
.filter(|b| !view.is_out_of_bounds(b.len()))
.filter(|b| !view.borrow().data().is_out_of_bounds(b.len()))
.is_none()
{
return Err(JsNativeError::typ()
Expand All @@ -425,7 +417,8 @@ impl DataView {
}

// 6. Let offset be O.[[ByteOffset]].
let offset = view.byte_offset;
let view_data = view.borrow();
let offset = view_data.data().byte_offset;
// 7. Return 𝔽(offset).
Ok(offset.into())
}
Expand All @@ -448,11 +441,7 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Perform ? RequireInternalSlot(view, [[DataView]]).
// 2. Assert: view has a [[ViewedArrayBuffer]] internal slot.
let object = view.as_object();
let view = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| JsNativeError::typ().with_message("`this` is not a DataView"))?;
let view = require_internal_slot!(view, Self, "DataView");

// 3. Let getIndex be ? ToIndex(requestIndex).
let get_index = request_index.to_index(context)?;
Expand All @@ -463,21 +452,24 @@ impl DataView {
// 6. Let viewRecord be MakeDataViewWithBufferWitnessRecord(view, unordered).
// 7. NOTE: Bounds checking is not a synchronizing operation when view's backing buffer is a growable SharedArrayBuffer.
// 8. If IsViewOutOfBounds(viewRecord) is true, throw a TypeError exception.
let buffer = view.viewed_array_buffer.as_buffer();
let view_data = view.borrow();
let buffer = view_data.data().viewed_array_buffer.as_buffer();
let Some(data) = buffer
.bytes(Ordering::Relaxed)
.filter(|buf| !view.is_out_of_bounds(buf.len()))
.filter(|buf| !view.borrow().data().is_out_of_bounds(buf.len()))
else {
return Err(JsNativeError::typ()
.with_message("view out of bounds for its inner buffer")
.into());
};

// 5. Let viewOffset be view.[[ByteOffset]].
let view_offset = view.byte_offset;
let view_data = view.borrow();
let view_offset = view_data.data().byte_offset;

// 9. Let viewSize be GetViewByteLength(viewRecord).
let view_size = view.byte_length(data.len());
let view_data = view.borrow();
let view_size = view_data.data().byte_length(data.len());

// 10. Let elementSize be the Element Size value specified in Table 71 for Element Type type.
let element_size = size_of::<T>() as u64;
Expand Down Expand Up @@ -790,11 +782,7 @@ impl DataView {
) -> JsResult<JsValue> {
// 1. Perform ? RequireInternalSlot(view, [[DataView]]).
// 2. Assert: view has a [[ViewedArrayBuffer]] internal slot.
let object = view.as_object();
let view = object
.as_ref()
.and_then(JsObject::downcast_ref::<Self>)
.ok_or_else(|| JsNativeError::typ().with_message("`this` is not a DataView"))?;
let view = require_internal_slot!(view, Self, "DataView");

// 3. Let getIndex be ? ToIndex(requestIndex).
let get_index = request_index.to_index(context)?;
Expand All @@ -809,22 +797,28 @@ impl DataView {
// 8. Let viewRecord be MakeDataViewWithBufferWitnessRecord(view, unordered).
// 9. NOTE: Bounds checking is not a synchronizing operation when view's backing buffer is a growable SharedArrayBuffer.
// 10. If IsViewOutOfBounds(viewRecord) is true, throw a TypeError exception.
let mut buffer = view.viewed_array_buffer.as_buffer_mut();
let viewed_buffer = {
let view_data = view.borrow();
view_data.data().viewed_array_buffer.clone()
};
let mut buffer = viewed_buffer.as_buffer_mut();

let Some(mut data) = buffer
.bytes(Ordering::Relaxed)
.filter(|buf| !view.is_out_of_bounds(buf.len()))
.filter(|buf| !view.borrow().data().is_out_of_bounds(buf.len()))
else {
return Err(JsNativeError::typ()
.with_message("view out of bounds for its inner buffer")
.into());
};

// 11. Let viewSize be GetViewByteLength(viewRecord).
let view_size = view.byte_length(data.len());
let view_data = view.borrow();
let view_size = view_data.data().byte_length(data.len());

// 7. Let viewOffset be view.[[ByteOffset]].
let view_offset = view.byte_offset;
let view_data = view.borrow();
let view_offset = view_data.data().byte_offset;

// 12. Let elementSize be the Element Size value specified in Table 71 for Element Type type.
let elem_size = size_of::<T>();
Expand Down
Loading
Loading