Commit 49b2510a authored by Jakob Gruber's avatar Jakob Gruber Committed by Commit Bot

[objects] Make JSArray::length and JSObject::elements stores atomic

Both fields are accessed during background compilation and thus need
to be written atomically.

This CL changes the default setters `set_foo(value, mode)` to use
relaxed stores underneath.

Bug: v8:7790
Change-Id: I49161a548cb0ef6797bd3e5592dc5bf0c9a27a15
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/2704076Reviewed-by: 's avatarUlan Degenbaev <ulan@chromium.org>
Commit-Queue: Jakob Gruber <jgruber@chromium.org>
Cr-Commit-Position: refs/heads/master@{#72899}
parent 18136654
......@@ -21,7 +21,15 @@ OBJECT_CONSTRUCTORS_IMPL(JSArrayIterator, JSObject)
CAST_ACCESSOR(JSArray)
CAST_ACCESSOR(JSArrayIterator)
ACCESSORS(JSArray, length, Object, kLengthOffset)
DEF_GETTER(JSArray, length, Object) {
return TaggedField<Object, kLengthOffset>::load(isolate, *this);
}
void JSArray::set_length(Object value, WriteBarrierMode mode) {
// Note the relaxed atomic store.
TaggedField<Object, kLengthOffset>::Relaxed_Store(*this, value);
CONDITIONAL_WRITE_BARRIER(*this, kLengthOffset, value, mode);
}
void JSArray::set_length(Smi length) {
// Don't need a write barrier for a Smi.
......
......@@ -26,6 +26,15 @@ class JSArray : public JSObject {
// [length]: The length property.
DECL_ACCESSORS(length, Object)
// Acquire/release semantics on this field are explicitly forbidden to avoid
// confusion, since the default setter uses relaxed semantics. If
// acquire/release semantics ever become necessary, the default setter should
// be reverted to non-atomic behavior, and setters with explicit tags
// introduced and used when required.
Object length(IsolateRoot isolate, AcquireLoadTag tag) const = delete;
void set_length(Object value, ReleaseStoreTag tag,
WriteBarrierMode mode = UPDATE_WRITE_BARRIER) = delete;
// Overload the length setter to skip write barrier when the length
// is set to a smi. This matches the set function on FixedArray.
inline void set_length(Smi length);
......
......@@ -50,6 +50,21 @@ CAST_ACCESSOR(JSIteratorResult)
CAST_ACCESSOR(JSMessageObject)
CAST_ACCESSOR(JSReceiver)
DEF_GETTER(JSObject, elements, FixedArrayBase) {
return TaggedField<FixedArrayBase, kElementsOffset>::load(isolate, *this);
}
FixedArrayBase JSObject::elements(IsolateRoot isolate, RelaxedLoadTag) const {
return TaggedField<FixedArrayBase, kElementsOffset>::Relaxed_Load(isolate,
*this);
}
void JSObject::set_elements(FixedArrayBase value, WriteBarrierMode mode) {
// Note the relaxed atomic store.
TaggedField<FixedArrayBase, kElementsOffset>::Relaxed_Store(*this, value);
CONDITIONAL_WRITE_BARRIER(*this, kElementsOffset, value, mode);
}
MaybeHandle<Object> JSReceiver::GetProperty(Isolate* isolate,
Handle<JSReceiver> receiver,
Handle<Name> name) {
......
......@@ -311,6 +311,19 @@ class JSObject : public TorqueGeneratedJSObject<JSObject, JSReceiver> {
static V8_WARN_UNUSED_RESULT MaybeHandle<JSObject> ObjectCreate(
Isolate* isolate, Handle<Object> prototype);
DECL_ACCESSORS(elements, FixedArrayBase)
DECL_RELAXED_GETTER(elements, FixedArrayBase)
// Acquire/release semantics on this field are explicitly forbidden to avoid
// confusion, since the default setter uses relaxed semantics. If
// acquire/release semantics ever become necessary, the default setter should
// be reverted to non-atomic behavior, and setters with explicit tags
// introduced and used when required.
FixedArrayBase elements(IsolateRoot isolate,
AcquireLoadTag tag) const = delete;
void set_elements(FixedArrayBase value, ReleaseStoreTag tag,
WriteBarrierMode mode = UPDATE_WRITE_BARRIER) = delete;
inline void initialize_elements();
static inline void SetMapAndElements(Handle<JSObject> object, Handle<Map> map,
Handle<FixedArrayBase> elements);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment