Commit 067507a2 authored by Leszek Swirski's avatar Leszek Swirski Committed by V8 LUCI CQ

[objects] Make map validity cell access relaxed

... because it's now read concurrently by Maglev.

Bug: v8:7700
Change-Id: Iab20ee398269bab403f9d463665c967dcf48e9aa
Fixed: chromium:1360255, v8:13266
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3875903Reviewed-by: 's avatarIgor Sheludko <ishell@chromium.org>
Auto-Submit: Leszek Swirski <leszeks@chromium.org>
Reviewed-by: 's avatarOmer Katz <omerkatz@chromium.org>
Reviewed-by: 's avatarCamillo Bruni <cbruni@chromium.org>
Commit-Queue: Camillo Bruni <cbruni@chromium.org>
Cr-Commit-Position: refs/heads/main@{#82998}
parent 8d7186c6
......@@ -555,7 +555,7 @@ void Map::MapVerify(Isolate* isolate) {
IsJSAtomicsCondition()) {
CHECK(InSharedHeap());
CHECK(GetBackPointer().IsUndefined(isolate));
Object maybe_cell = prototype_validity_cell();
Object maybe_cell = prototype_validity_cell(kRelaxedLoad);
if (maybe_cell.IsCell()) CHECK(maybe_cell.InSharedHeap());
CHECK(!is_extensible());
CHECK(!is_prototype_map());
......
......@@ -2705,7 +2705,8 @@ void Map::MapPrint(std::ostream& os) {
} else {
os << "\n - back pointer: " << Brief(GetBackPointer());
}
os << "\n - prototype_validity cell: " << Brief(prototype_validity_cell());
os << "\n - prototype_validity cell: "
<< Brief(prototype_validity_cell(kRelaxedLoad));
os << "\n - instance descriptors " << (owns_descriptors() ? "(own) " : "")
<< "#" << NumberOfOwnDescriptors() << ": "
<< Brief(instance_descriptors());
......
......@@ -2052,12 +2052,13 @@ Map Factory::InitializeMap(Map map, InstanceType type, int instance_size,
map.SetInObjectPropertiesStartInWords(instance_size / kTaggedSize -
inobject_properties);
DCHECK_EQ(map.GetInObjectProperties(), inobject_properties);
map.set_prototype_validity_cell(roots->invalid_prototype_validity_cell());
map.set_prototype_validity_cell(roots->invalid_prototype_validity_cell(),
kRelaxedStore);
} else {
DCHECK_EQ(inobject_properties, 0);
map.set_inobject_properties_start_or_constructor_function_index(0);
map.set_prototype_validity_cell(Smi::FromInt(Map::kPrototypeChainValid),
SKIP_WRITE_BARRIER);
kRelaxedStore, SKIP_WRITE_BARRIER);
}
map.set_dependent_code(DependentCode::empty_dependent_code(ro_roots),
SKIP_WRITE_BARRIER);
......
......@@ -176,7 +176,8 @@ AllocationResult Heap::AllocatePartialMap(InstanceType instance_type,
map.set_visitor_id(Map::GetVisitorId(map));
map.set_inobject_properties_start_or_constructor_function_index(0);
DCHECK(!map.IsJSObjectMap());
map.set_prototype_validity_cell(Smi::FromInt(Map::kPrototypeChainValid));
map.set_prototype_validity_cell(Smi::FromInt(Map::kPrototypeChainValid),
kRelaxedStore);
map.SetInObjectUnusedPropertyFields(0);
map.set_bit_field(0);
map.set_bit_field2(0);
......
......@@ -295,7 +295,8 @@ MaybeObjectHandle StoreHandler::StoreTransition(Isolate* isolate,
} else {
// Ensure the transition map contains a valid prototype validity cell.
if (!validity_cell.is_null()) {
transition_map->set_prototype_validity_cell(*validity_cell);
transition_map->set_prototype_validity_cell(*validity_cell,
kRelaxedStore);
}
return MaybeObjectHandle::Weak(transition_map);
}
......
......@@ -1073,8 +1073,8 @@ bool MaglevGraphBuilder::TryBuildMonomorphicLoadFromLoadHandler(
}
compiler::MapRef proto_map = receiver_map.prototype().map();
while (proto_map.object()->prototype_validity_cell(local_isolate_) ==
validity_cell) {
while (proto_map.object()->prototype_validity_cell(
local_isolate_, kRelaxedLoad) == validity_cell) {
broker()->dependencies()->DependOnStableMap(proto_map);
proto_map = proto_map.prototype().map();
}
......
......@@ -4946,7 +4946,7 @@ void InvalidateOnePrototypeValidityCellInternal(Map map) {
PrintF("Invalidating prototype map %p 's cell\n",
reinterpret_cast<void*>(map.ptr()));
}
Object maybe_cell = map.prototype_validity_cell();
Object maybe_cell = map.prototype_validity_cell(kRelaxedLoad);
if (maybe_cell.IsCell()) {
// Just set the value; the cell will be replaced lazily.
Cell cell = Cell::cast(maybe_cell);
......
......@@ -660,7 +660,7 @@ void LookupIterator::ApplyTransitionToDataProperty(
// configuration can produce valid transition handler maps.
Handle<Object> validity_cell =
Map::GetOrCreatePrototypeChainValidityCell(transition, isolate());
transition->set_prototype_validity_cell(*validity_cell);
transition->set_prototype_validity_cell(*validity_cell, kRelaxedStore);
}
if (!receiver->IsJSProxy(isolate_)) {
......
......@@ -779,7 +779,8 @@ Map Map::ElementsTransitionMap(Isolate* isolate, ConcurrencyMode cmode) {
}
ACCESSORS(Map, dependent_code, DependentCode, kDependentCodeOffset)
ACCESSORS(Map, prototype_validity_cell, Object, kPrototypeValidityCellOffset)
RELAXED_ACCESSORS(Map, prototype_validity_cell, Object,
kPrototypeValidityCellOffset)
ACCESSORS_CHECKED2(Map, constructor_or_back_pointer, Object,
kConstructorOrBackPointerOrNativeContextOffset,
!IsContextMap(), value.IsNull() || !IsContextMap())
......@@ -800,7 +801,7 @@ ACCESSORS_CHECKED(Map, wasm_type_info, WasmTypeInfo,
#endif // V8_ENABLE_WEBASSEMBLY
bool Map::IsPrototypeValidityCellValid() const {
Object validity_cell = prototype_validity_cell();
Object validity_cell = prototype_validity_cell(kRelaxedLoad);
if (validity_cell.IsSmi()) {
// Smi validity cells should always be considered valid.
DCHECK_EQ(Smi::cast(validity_cell).value(), Map::kPrototypeChainValid);
......
......@@ -2260,7 +2260,7 @@ Handle<Object> Map::GetOrCreatePrototypeChainValidityCell(Handle<Map> map,
JSObject::LazyRegisterPrototypeUser(handle(prototype->map(), isolate),
isolate);
Object maybe_cell = prototype->map().prototype_validity_cell();
Object maybe_cell = prototype->map().prototype_validity_cell(kRelaxedLoad);
// Return existing cell if it's still valid.
if (maybe_cell.IsCell()) {
Handle<Cell> cell(Cell::cast(maybe_cell), isolate);
......@@ -2271,14 +2271,14 @@ Handle<Object> Map::GetOrCreatePrototypeChainValidityCell(Handle<Map> map,
// Otherwise create a new cell.
Handle<Cell> cell = isolate->factory()->NewCell(
handle(Smi::FromInt(Map::kPrototypeChainValid), isolate));
prototype->map().set_prototype_validity_cell(*cell);
prototype->map().set_prototype_validity_cell(*cell, kRelaxedStore);
return cell;
}
// static
bool Map::IsPrototypeChainInvalidated(Map map) {
DCHECK(map.is_prototype_map());
Object maybe_cell = map.prototype_validity_cell();
Object maybe_cell = map.prototype_validity_cell(kRelaxedLoad);
if (maybe_cell.IsCell()) {
Cell cell = Cell::cast(maybe_cell);
return cell.value() != Smi::FromInt(Map::kPrototypeChainValid);
......
......@@ -624,7 +624,7 @@ class Map : public TorqueGeneratedMap<Map, HeapObject> {
// For non-prototype maps which are used as transitioning store handlers this
// field contains the validity cell which guards modifications of this map's
// prototype.
DECL_ACCESSORS(prototype_validity_cell, Object)
DECL_RELAXED_ACCESSORS(prototype_validity_cell, Object)
// Returns true if prototype validity cell value represents "valid" prototype
// chain state.
......
......@@ -1469,8 +1469,8 @@ void V8HeapExplorer::ExtractMapReferences(HeapEntry* entry, Map map) {
TagObject(map.dependent_code(), "(dependent code)");
SetInternalReference(entry, "dependent_code", map.dependent_code(),
Map::kDependentCodeOffset);
TagObject(map.prototype_validity_cell(), "(prototype validity cell)",
HeapEntry::kObjectShape);
TagObject(map.prototype_validity_cell(kRelaxedLoad),
"(prototype validity cell)", HeapEntry::kObjectShape);
}
void V8HeapExplorer::ExtractSharedFunctionInfoReferences(
......
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