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

[18.x] vm: backport vm-related fixes #51004

Closed
wants to merge 22 commits into from
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
a6524dd
deps: V8: cherry-pick c400af48b5ef
joyeecheung Dec 1, 2023
990caf3
deps: V8: cherry-pick 7f5daed62d47
joyeecheung Dec 1, 2023
8ade4aa
deps: V8: cherry-pick 9a98f96b6d68
joyeecheung Dec 1, 2023
80f54b7
deps: V8: cherry-pick 94e8282325a1
joyeecheung Dec 1, 2023
213e73b
deps: V8: cherry-pick 3dd9576ce336
joyeecheung Dec 1, 2023
0f33b00
deps: V8: cherry-pick 1fada6b36f8d
joyeecheung Dec 1, 2023
59cf71f
deps: V8: cherry-pick 705e374124ae
joyeecheung Dec 1, 2023
86d8b58
deps: V8: cherry-pick 71ff68830279
joyeecheung Dec 1, 2023
c8ed93a
lib: fix compileFunction throws range error for negative numbers
MrJithil Oct 6, 2023
f1251ef
src: cast v8::Object::GetInternalField() return value to v8::Value
joyeecheung Aug 2, 2023
af9edb4
deps: add v8::Object::SetInternalFieldForNodeCore()
joyeecheung Sep 26, 2023
9e8629c
src: set ModuleWrap internal fields only once
joyeecheung Sep 8, 2023
bb3462a
module: use symbol in WeakMap to manage host defined options
joyeecheung Jun 21, 2023
05778c4
module: fix leak of vm.SyntheticModule
joyeecheung Jun 21, 2023
0849599
module: fix the leak in SourceTextModule and ContextifySript
joyeecheung Jun 23, 2023
2feffae
test: add checkIfCollectable to test/common/gc.js
joyeecheung Sep 16, 2023
466c304
test: use checkIfCollectable in vm leak tests
joyeecheung Sep 16, 2023
fc003be
test: deflake test-vm-contextified-script-leak
joyeecheung Sep 23, 2023
d183187
vm: use default HDO when importModuleDynamically is not set
joyeecheung Oct 5, 2023
c8be386
vm: unify host-defined option generation in vm.compileFunction
joyeecheung Oct 5, 2023
222877e
vm: use internal versions of compileFunction and Script
joyeecheung Oct 11, 2023
a2b3f6e
vm: reject in importModuleDynamically without --experimental-vm-modules
joyeecheung Oct 5, 2023
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
Prev Previous commit
Next Next commit
deps: V8: cherry-pick 94e8282325a1
Original commit message:

    [symbol-as-weakmap-key] Fix DCHECKs and add CanBeHeldWeakly

    There are a few DCHECKs that weren't updated to allow for Symbols as
    weak collection keys. This CL updates those DCHECKs and also does the
    following refactors for clarity:

    - Add Object::CanBeHeldWeakly
    - Rename GotoIfCannotBeWeakKey -> GotoIfCannotBeHeldWeakly to align with
      spec AO name

    Bug: chromium:1370400, chromium:1370402, v8:12947
    Change-Id: I380840c8377497feae97e3fca37555dae0dcc255
    Fixed: chromium:1370400, chromium:1370402
    Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3928150
    Auto-Submit: Shu-yu Guo <syg@chromium.org>
    Reviewed-by: Marja Hölttä <marja@chromium.org>
    Commit-Queue: Marja Hölttä <marja@chromium.org>
    Cr-Commit-Position: refs/heads/main@{#83507}

Refs: v8/v8@94e8282
  • Loading branch information
joyeecheung committed Dec 1, 2023
commit 80f54b7b306db3560a96d57c62d4ab6faa6a975a
38 changes: 19 additions & 19 deletions deps/v8/src/builtins/builtins-collections-gen.cc
Original file line number Diff line number Diff line change
Expand Up @@ -399,23 +399,23 @@ TNode<IntPtrT> BaseCollectionsAssembler::EstimatedInitialSize(
[=] { return IntPtrConstant(0); });
}

void BaseCollectionsAssembler::GotoIfCannotBeWeakKey(
const TNode<Object> obj, Label* if_cannot_be_weak_key) {
void BaseCollectionsAssembler::GotoIfCannotBeHeldWeakly(
const TNode<Object> obj, Label* if_cannot_be_held_weakly) {
Label check_symbol_key(this);
Label end(this);
GotoIf(TaggedIsSmi(obj), if_cannot_be_weak_key);
GotoIf(TaggedIsSmi(obj), if_cannot_be_held_weakly);
TNode<Uint16T> instance_type = LoadMapInstanceType(LoadMap(CAST(obj)));
GotoIfNot(IsJSReceiverInstanceType(instance_type), &check_symbol_key);
// TODO(v8:12547) Shared structs should only be able to point to shared values
// in weak collections. For now, disallow them as weak collection keys.
GotoIf(IsJSSharedStructInstanceType(instance_type), if_cannot_be_weak_key);
GotoIf(IsJSSharedStructInstanceType(instance_type), if_cannot_be_held_weakly);
Goto(&end);
Bind(&check_symbol_key);
GotoIfNot(HasHarmonySymbolAsWeakmapKeyFlag(), if_cannot_be_weak_key);
GotoIfNot(IsSymbolInstanceType(instance_type), if_cannot_be_weak_key);
GotoIfNot(HasHarmonySymbolAsWeakmapKeyFlag(), if_cannot_be_held_weakly);
GotoIfNot(IsSymbolInstanceType(instance_type), if_cannot_be_held_weakly);
TNode<Uint32T> flags = LoadSymbolFlags(CAST(obj));
GotoIf(Word32And(flags, Symbol::IsInPublicSymbolTableBit::kMask),
if_cannot_be_weak_key);
if_cannot_be_held_weakly);
Goto(&end);
Bind(&end);
}
Expand Down Expand Up @@ -2573,17 +2573,17 @@ TF_BUILTIN(WeakMapLookupHashIndex, WeakCollectionsBuiltinsAssembler) {
auto table = Parameter<EphemeronHashTable>(Descriptor::kTable);
auto key = Parameter<Object>(Descriptor::kKey);

Label if_cannot_be_weak_key(this);
Label if_cannot_be_held_weakly(this);

GotoIfCannotBeWeakKey(key, &if_cannot_be_weak_key);
GotoIfCannotBeHeldWeakly(key, &if_cannot_be_held_weakly);

TNode<IntPtrT> hash = GetHash(CAST(key), &if_cannot_be_weak_key);
TNode<IntPtrT> hash = GetHash(CAST(key), &if_cannot_be_held_weakly);
TNode<IntPtrT> capacity = LoadTableCapacity(table);
TNode<IntPtrT> key_index = FindKeyIndexForKey(
table, key, hash, EntryMask(capacity), &if_cannot_be_weak_key);
table, key, hash, EntryMask(capacity), &if_cannot_be_held_weakly);
Return(SmiTag(ValueIndexFromKeyIndex(key_index)));

BIND(&if_cannot_be_weak_key);
BIND(&if_cannot_be_held_weakly);
Return(SmiConstant(-1));
}

Expand Down Expand Up @@ -2638,22 +2638,22 @@ TF_BUILTIN(WeakCollectionDelete, WeakCollectionsBuiltinsAssembler) {
auto collection = Parameter<JSWeakCollection>(Descriptor::kCollection);
auto key = Parameter<Object>(Descriptor::kKey);

Label call_runtime(this), if_cannot_be_weak_key(this);
Label call_runtime(this), if_cannot_be_held_weakly(this);

GotoIfCannotBeWeakKey(key, &if_cannot_be_weak_key);
GotoIfCannotBeHeldWeakly(key, &if_cannot_be_held_weakly);

TNode<IntPtrT> hash = GetHash(CAST(key), &if_cannot_be_weak_key);
TNode<IntPtrT> hash = GetHash(CAST(key), &if_cannot_be_held_weakly);
TNode<EphemeronHashTable> table = LoadTable(collection);
TNode<IntPtrT> capacity = LoadTableCapacity(table);
TNode<IntPtrT> key_index = FindKeyIndexForKey(
table, key, hash, EntryMask(capacity), &if_cannot_be_weak_key);
table, key, hash, EntryMask(capacity), &if_cannot_be_held_weakly);
TNode<IntPtrT> number_of_elements = LoadNumberOfElements(table, -1);
GotoIf(ShouldShrink(capacity, number_of_elements), &call_runtime);

RemoveEntry(table, key_index, number_of_elements);
Return(TrueConstant());

BIND(&if_cannot_be_weak_key);
BIND(&if_cannot_be_held_weakly);
Return(FalseConstant());

BIND(&call_runtime);
Expand Down Expand Up @@ -2735,7 +2735,7 @@ TF_BUILTIN(WeakMapPrototypeSet, WeakCollectionsBuiltinsAssembler) {
"WeakMap.prototype.set");

Label throw_invalid_key(this);
GotoIfCannotBeWeakKey(key, &throw_invalid_key);
GotoIfCannotBeHeldWeakly(key, &throw_invalid_key);

Return(
CallBuiltin(Builtin::kWeakCollectionSet, context, receiver, key, value));
Expand All @@ -2753,7 +2753,7 @@ TF_BUILTIN(WeakSetPrototypeAdd, WeakCollectionsBuiltinsAssembler) {
"WeakSet.prototype.add");

Label throw_invalid_value(this);
GotoIfCannotBeWeakKey(value, &throw_invalid_value);
GotoIfCannotBeHeldWeakly(value, &throw_invalid_value);

Return(CallBuiltin(Builtin::kWeakCollectionSet, context, receiver, value,
TrueConstant()));
Expand Down
4 changes: 2 additions & 2 deletions deps/v8/src/builtins/builtins-collections-gen.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,8 @@ class BaseCollectionsAssembler : public CodeStubAssembler {

virtual ~BaseCollectionsAssembler() = default;

void GotoIfCannotBeWeakKey(const TNode<Object> obj,
Label* if_cannot_be_weak_key);
void GotoIfCannotBeHeldWeakly(const TNode<Object> obj,
Label* if_cannot_be_held_weakly);

protected:
enum Variant { kMap, kSet, kWeakMap, kWeakSet };
Expand Down
21 changes: 4 additions & 17 deletions deps/v8/src/builtins/builtins-weak-refs.cc
Original file line number Diff line number Diff line change
Expand Up @@ -27,23 +27,10 @@ BUILTIN(FinalizationRegistryUnregister) {

// 4. If CanBeHeldWeakly(unregisterToken) is false, throw a TypeError
// exception.
if (FLAG_harmony_symbol_as_weakmap_key) {
if (!unregister_token->IsJSReceiver() &&
(!unregister_token->IsSymbol() ||
Handle<Symbol>::cast(unregister_token)->is_in_public_symbol_table())) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate,
NewTypeError(MessageTemplate::kInvalidWeakRefsUnregisterToken,
unregister_token));
}
} else {
// 4. If Type(unregisterToken) is not Object, throw a TypeError exception.
if (!unregister_token->IsJSReceiver()) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate,
NewTypeError(MessageTemplate::kInvalidWeakRefsUnregisterToken,
unregister_token));
}
if (!unregister_token->CanBeHeldWeakly()) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate, NewTypeError(MessageTemplate::kInvalidWeakRefsUnregisterToken,
unregister_token));
}

bool success = JSFinalizationRegistry::Unregister(
Expand Down
6 changes: 3 additions & 3 deletions deps/v8/src/builtins/finalization-registry.tq
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ extern transitioning macro
RemoveFinalizationRegistryCellFromUnregisterTokenMap(
JSFinalizationRegistry, WeakCell): void;

extern macro WeakCollectionsBuiltinsAssembler::GotoIfCannotBeWeakKey(JSAny):
extern macro WeakCollectionsBuiltinsAssembler::GotoIfCannotBeHeldWeakly(JSAny):
void labels NotWeakKey;

macro SplitOffTail(weakCell: WeakCell): WeakCell|Undefined {
Expand Down Expand Up @@ -140,7 +140,7 @@ FinalizationRegistryRegister(
MessageTemplate::kIncompatibleMethodReceiver,
'FinalizationRegistry.prototype.register', receiver);
// 3. If CanBeHeldWeakly(target) is false, throw a TypeError exception.
GotoIfCannotBeWeakKey(arguments[0])
GotoIfCannotBeHeldWeakly(arguments[0])
otherwise ThrowTypeError(MessageTemplate::kInvalidWeakRefsRegisterTarget);

const target = UnsafeCast<(JSReceiver | Symbol)>(arguments[0]);
Expand All @@ -159,7 +159,7 @@ FinalizationRegistryRegister(
if (IsUndefined(unregisterTokenRaw)) {
unregisterToken = Undefined;
} else {
GotoIfCannotBeWeakKey(unregisterTokenRaw)
GotoIfCannotBeHeldWeakly(unregisterTokenRaw)
otherwise ThrowTypeError(
MessageTemplate::kInvalidWeakRefsUnregisterToken, unregisterTokenRaw);
unregisterToken = UnsafeCast<(JSReceiver | Symbol)>(unregisterTokenRaw);
Expand Down
2 changes: 1 addition & 1 deletion deps/v8/src/builtins/weak-ref.tq
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ WeakRefConstructor(
}

// 2. If CanBeHeldWeakly(weakTarget) is false, throw a TypeError exception.
GotoIfCannotBeWeakKey(weakTarget) otherwise ThrowTypeError(
GotoIfCannotBeHeldWeakly(weakTarget) otherwise ThrowTypeError(
MessageTemplate::kInvalidWeakRefsWeakRefConstructorTarget);

// 3. Let weakRef be ? OrdinaryCreateFromConstructor(NewTarget,
Expand Down
8 changes: 2 additions & 6 deletions deps/v8/src/diagnostics/objects-debug.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1240,9 +1240,7 @@ void JSSharedStruct::JSSharedStructVerify(Isolate* isolate) {
void WeakCell::WeakCellVerify(Isolate* isolate) {
CHECK(IsWeakCell());

CHECK(target().IsJSReceiver() || target().IsUndefined(isolate) ||
(target().IsSymbol() &&
!Symbol::cast(target()).is_in_public_symbol_table()));
CHECK(target().IsUndefined(isolate) || target().CanBeHeldWeakly());

CHECK(prev().IsWeakCell() || prev().IsUndefined(isolate));
if (prev().IsWeakCell()) {
Expand Down Expand Up @@ -1270,9 +1268,7 @@ void WeakCell::WeakCellVerify(Isolate* isolate) {
void JSWeakRef::JSWeakRefVerify(Isolate* isolate) {
CHECK(IsJSWeakRef());
JSObjectVerify(isolate);
CHECK(target().IsUndefined(isolate) || target().IsJSReceiver() ||
(target().IsSymbol() &&
!Symbol::cast(target()).is_in_public_symbol_table()));
CHECK(target().IsUndefined(isolate) || target().CanBeHeldWeakly());
}

void JSFinalizationRegistry::JSFinalizationRegistryVerify(Isolate* isolate) {
Expand Down
6 changes: 2 additions & 4 deletions deps/v8/src/objects/js-weak-refs-inl.h
Original file line number Diff line number Diff line change
Expand Up @@ -170,9 +170,7 @@ void WeakCell::Nullify(Isolate* isolate,
// only called for WeakCells which haven't been unregistered yet, so they will
// be in the active_cells list. (The caller must guard against calling this
// for unregistered WeakCells by checking that the target is not undefined.)
DCHECK(target().IsJSReceiver() ||
(target().IsSymbol() &&
!Symbol::cast(target()).is_in_public_symbol_table()));
DCHECK(target().CanBeHeldWeakly());
set_target(ReadOnlyRoots(isolate).undefined_value());

JSFinalizationRegistry fr =
Expand Down Expand Up @@ -218,7 +216,7 @@ void WeakCell::RemoveFromFinalizationRegistryCells(Isolate* isolate) {

// It's important to set_target to undefined here. This guards that we won't
// call Nullify (which assumes that the WeakCell is in active_cells).
DCHECK(target().IsUndefined() || target().IsJSReceiver());
DCHECK(target().IsUndefined() || target().CanBeHeldWeakly());
set_target(ReadOnlyRoots(isolate).undefined_value());

JSFinalizationRegistry fr =
Expand Down
17 changes: 17 additions & 0 deletions deps/v8/src/objects/objects-inl.h
Original file line number Diff line number Diff line change
Expand Up @@ -1206,6 +1206,23 @@ MaybeHandle<Object> Object::Share(Isolate* isolate, Handle<Object> value,
throw_if_cannot_be_shared);
}

// https://tc39.es/proposal-symbols-as-weakmap-keys/#sec-canbeheldweakly-abstract-operation
bool Object::CanBeHeldWeakly() const {
if (IsJSReceiver()) {
// TODO(v8:12547) Shared structs and arrays should only be able to point
// to shared values in weak collections. For now, disallow them as weak
// collection keys.
if (FLAG_harmony_struct) {
return !IsJSSharedStruct();
}
return true;
}
if (FLAG_harmony_symbol_as_weakmap_key) {
return IsSymbol() && !Symbol::cast(*this).is_in_public_symbol_table();
}
return false;
}

Handle<Object> ObjectHashTableShape::AsHandle(Handle<Object> key) {
return key;
}
Expand Down
5 changes: 5 additions & 0 deletions deps/v8/src/objects/objects.h
Original file line number Diff line number Diff line change
Expand Up @@ -770,6 +770,11 @@ class Object : public TaggedImpl<HeapObjectReferenceType::STRONG, Address> {
Handle<HeapObject> value,
ShouldThrow throw_if_cannot_be_shared);

// Whether this Object can be held weakly, i.e. whether it can be used as a
// key in WeakMap, as a key in WeakSet, as the target of a WeakRef, or as a
// target or unregister token of a FinalizationRegistry.
inline bool CanBeHeldWeakly() const;

protected:
inline Address field_address(size_t offset) const {
return ptr() + offset - kHeapObjectTag;
Expand Down
4 changes: 2 additions & 2 deletions deps/v8/src/runtime/runtime-collections.cc
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ RUNTIME_FUNCTION(Runtime_WeakCollectionDelete) {
int hash = args.smi_value_at(2);

#ifdef DEBUG
DCHECK(key->IsJSReceiver());
DCHECK(key->CanBeHeldWeakly());
DCHECK(EphemeronHashTable::IsKey(ReadOnlyRoots(isolate), *key));
Handle<EphemeronHashTable> table(
EphemeronHashTable::cast(weak_collection->table()), isolate);
Expand All @@ -105,7 +105,7 @@ RUNTIME_FUNCTION(Runtime_WeakCollectionSet) {
int hash = args.smi_value_at(3);

#ifdef DEBUG
DCHECK(key->IsJSReceiver());
DCHECK(key->CanBeHeldWeakly());
DCHECK(EphemeronHashTable::IsKey(ReadOnlyRoots(isolate), *key));
Handle<EphemeronHashTable> table(
EphemeronHashTable::cast(weak_collection->table()), isolate);
Expand Down
8 changes: 1 addition & 7 deletions deps/v8/src/runtime/runtime-weak-refs.cc
Original file line number Diff line number Diff line change
Expand Up @@ -44,13 +44,7 @@ RUNTIME_FUNCTION(Runtime_JSWeakRefAddToKeptObjects) {
HandleScope scope(isolate);
DCHECK_EQ(1, args.length());
Handle<HeapObject> object = args.at<HeapObject>(0);
if (FLAG_harmony_symbol_as_weakmap_key) {
DCHECK(object->IsJSReceiver() ||
(object->IsSymbol() &&
!(Handle<Symbol>::cast(object))->is_in_public_symbol_table()));
} else {
DCHECK(object->IsJSReceiver());
}
DCHECK(object->CanBeHeldWeakly());

isolate->heap()->KeepDuringJob(object);

Expand Down
7 changes: 7 additions & 0 deletions deps/v8/test/mjsunit/harmony/symbol-as-weakmap-key.js
Original file line number Diff line number Diff line change
Expand Up @@ -99,3 +99,10 @@
assertFalse(set.delete(key));
assertFalse(set.has(key));
})();

(function TestFinalizationRegistryUnregister() {
const fr = new FinalizationRegistry(function() {});
const key = {};
fr.register(Symbol('foo'), "holdings", key);
fr.unregister(key);
})();