blob: a05f315aeac7ebd77036805b28f880ee7261fb90 [file]
// Copyright 2026 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef V8_OBJECTS_OBJECT_PREDICATES_INL_H_
#define V8_OBJECTS_OBJECT_PREDICATES_INL_H_
#include "src/objects/object-predicates.h"
// Include the non-inl header before the rest of the headers.
#include "src/common/globals.h"
#include "src/heap/heap-layout-inl.h"
#include "src/objects/casting.h"
#include "src/objects/heap-object-inl.h"
#include "src/objects/smi.h"
#include "src/objects/tagged-index.h"
#include "src/roots/roots.h"
namespace v8::internal {
bool IsTaggedIndex(Tagged<Object> obj) {
return IsSmi(obj) &&
TaggedIndex::IsValid(Tagged<TaggedIndex>(obj.ptr()).value());
}
bool IsZero(Tagged<Object> obj) { return obj == Smi::zero(); }
bool IsNoSharedNameSentinel(Tagged<Object> obj) {
return obj == SharedFunctionInfo::kNoSharedNameSentinel;
}
bool IsJSObjectThatCanBeTrackedAsPrototype(Tagged<Object> obj) {
return IsHeapObject(obj) &&
IsJSObjectThatCanBeTrackedAsPrototype(Cast<HeapObject>(obj));
}
bool IsJSObjectThatCanBeTrackedAsPrototype(Tagged<HeapObject> obj) {
return IsJSObject(obj) && !HeapLayout::InWritableSharedSpace(obj);
}
bool IsAnyObjectThatCanBeTrackedAsPrototype(Tagged<Object> obj) {
return IsHeapObject(obj) &&
IsAnyObjectThatCanBeTrackedAsPrototype(Cast<HeapObject>(obj));
}
bool IsAnyObjectThatCanBeTrackedAsPrototype(Tagged<HeapObject> obj) {
return (IsJSObject(obj) || IsWasmObject(obj)) &&
!HeapLayout::InWritableSharedSpace(obj);
}
bool IsNumber(Tagged<Object> obj) {
if (IsSmi(obj)) return true;
return IsHeapNumber(Cast<HeapObject>(obj));
}
bool IsNumeric(Tagged<Object> obj) {
if (IsSmi(obj)) return true;
Tagged<HeapObject> heap_object = Cast<HeapObject>(obj);
return IsHeapNumber(heap_object) || IsBigInt(heap_object);
}
bool IsShared(Tagged<Object> obj) {
// This logic should be kept in sync with fast paths in
// CodeStubAssembler::SharedValueBarrier.
// Smis are trivially shared.
if (IsSmi(obj)) return true;
Tagged<HeapObject> object = Cast<HeapObject>(obj);
// RO objects are shared when the RO space is shared.
if (HeapLayout::InReadOnlySpace(object)) {
return true;
}
// Check if this object is already shared.
InstanceType instance_type = object->map()->instance_type();
if (InstanceTypeChecker::IsAlwaysSharedSpaceJSObject(instance_type)) {
DCHECK(HeapLayout::InAnySharedSpace(object));
return true;
}
switch (instance_type) {
case SHARED_SEQ_TWO_BYTE_STRING_TYPE:
case SHARED_SEQ_ONE_BYTE_STRING_TYPE:
case SHARED_EXTERNAL_TWO_BYTE_STRING_TYPE:
case SHARED_EXTERNAL_ONE_BYTE_STRING_TYPE:
case SHARED_UNCACHED_EXTERNAL_TWO_BYTE_STRING_TYPE:
case SHARED_UNCACHED_EXTERNAL_ONE_BYTE_STRING_TYPE:
DCHECK(HeapLayout::InAnySharedSpace(object));
return true;
#if V8_ENABLE_WEBASSEMBLY
case WASM_STRUCT_TYPE:
case WASM_ARRAY_TYPE:
return HeapLayout::InAnySharedSpace(object);
#endif
case INTERNALIZED_TWO_BYTE_STRING_TYPE:
case INTERNALIZED_ONE_BYTE_STRING_TYPE:
case EXTERNAL_INTERNALIZED_TWO_BYTE_STRING_TYPE:
case EXTERNAL_INTERNALIZED_ONE_BYTE_STRING_TYPE:
case UNCACHED_EXTERNAL_INTERNALIZED_TWO_BYTE_STRING_TYPE:
case UNCACHED_EXTERNAL_INTERNALIZED_ONE_BYTE_STRING_TYPE:
if (v8_flags.shared_string_table) {
DCHECK(HeapLayout::InAnySharedSpace(object));
return true;
}
return false;
case HEAP_NUMBER_TYPE:
return HeapLayout::InWritableSharedSpace(object);
default:
return false;
}
}
} // namespace v8::internal
#endif // V8_OBJECTS_OBJECT_PREDICATES_INL_H_