| Index: src/objects-body-descriptors-inl.h
|
| diff --git a/src/objects-body-descriptors-inl.h b/src/objects-body-descriptors-inl.h
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..8fe507ea3c07533e7667ea95c1c0193200379b9b
|
| --- /dev/null
|
| +++ b/src/objects-body-descriptors-inl.h
|
| @@ -0,0 +1,584 @@
|
| +// Copyright 2015 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_BODY_DESCRIPTORS_INL_H_
|
| +#define V8_OBJECTS_BODY_DESCRIPTORS_INL_H_
|
| +
|
| +#include "src/objects-body-descriptors.h"
|
| +
|
| +namespace v8 {
|
| +namespace internal {
|
| +
|
| +template <int start_offset>
|
| +int FlexibleBodyDescriptor<start_offset>::SizeOf(Map* map, HeapObject* object) {
|
| + return object->SizeFromMap(map);
|
| +}
|
| +
|
| +
|
| +bool BodyDescriptorBase::IsValidSlotImpl(HeapObject* obj, int offset) {
|
| + if (!FLAG_unbox_double_fields || obj->map()->HasFastPointerLayout()) {
|
| + return true;
|
| + } else {
|
| + DCHECK(FLAG_unbox_double_fields);
|
| + DCHECK(IsAligned(offset, kPointerSize));
|
| +
|
| + LayoutDescriptorHelper helper(obj->map());
|
| + DCHECK(!helper.all_fields_tagged());
|
| + return helper.IsTagged(offset);
|
| + }
|
| +}
|
| +
|
| +template <typename ObjectVisitor>
|
| +void BodyDescriptorBase::IterateBodyImpl(HeapObject* obj, int start_offset,
|
| + int end_offset, ObjectVisitor* v) {
|
| + if (!FLAG_unbox_double_fields || obj->map()->HasFastPointerLayout()) {
|
| + IteratePointers(obj, start_offset, end_offset, v);
|
| + } else {
|
| + DCHECK(FLAG_unbox_double_fields);
|
| + DCHECK(IsAligned(start_offset, kPointerSize) &&
|
| + IsAligned(end_offset, kPointerSize));
|
| +
|
| + LayoutDescriptorHelper helper(obj->map());
|
| + DCHECK(!helper.all_fields_tagged());
|
| + for (int offset = start_offset; offset < end_offset;) {
|
| + int end_of_region_offset;
|
| + if (helper.IsTagged(offset, end_offset, &end_of_region_offset)) {
|
| + IteratePointers(obj, offset, end_of_region_offset, v);
|
| + }
|
| + offset = end_of_region_offset;
|
| + }
|
| + }
|
| +}
|
| +
|
| +
|
| +template <typename StaticVisitor>
|
| +void BodyDescriptorBase::IterateBodyImpl(Heap* heap, HeapObject* obj,
|
| + int start_offset, int end_offset) {
|
| + if (!FLAG_unbox_double_fields || obj->map()->HasFastPointerLayout()) {
|
| + IteratePointers<StaticVisitor>(heap, obj, start_offset, end_offset);
|
| + } else {
|
| + DCHECK(FLAG_unbox_double_fields);
|
| + DCHECK(IsAligned(start_offset, kPointerSize) &&
|
| + IsAligned(end_offset, kPointerSize));
|
| +
|
| + LayoutDescriptorHelper helper(obj->map());
|
| + DCHECK(!helper.all_fields_tagged());
|
| + for (int offset = start_offset; offset < end_offset;) {
|
| + int end_of_region_offset;
|
| + if (helper.IsTagged(offset, end_offset, &end_of_region_offset)) {
|
| + IteratePointers<StaticVisitor>(heap, obj, offset, end_of_region_offset);
|
| + }
|
| + offset = end_of_region_offset;
|
| + }
|
| + }
|
| +}
|
| +
|
| +
|
| +template <typename ObjectVisitor>
|
| +void BodyDescriptorBase::IteratePointers(HeapObject* obj, int start_offset,
|
| + int end_offset, ObjectVisitor* v) {
|
| + v->VisitPointers(HeapObject::RawField(obj, start_offset),
|
| + HeapObject::RawField(obj, end_offset));
|
| +}
|
| +
|
| +
|
| +template <typename StaticVisitor>
|
| +void BodyDescriptorBase::IteratePointers(Heap* heap, HeapObject* obj,
|
| + int start_offset, int end_offset) {
|
| + StaticVisitor::VisitPointers(heap, obj,
|
| + HeapObject::RawField(obj, start_offset),
|
| + HeapObject::RawField(obj, end_offset));
|
| +}
|
| +
|
| +
|
| +template <typename ObjectVisitor>
|
| +void BodyDescriptorBase::IteratePointer(HeapObject* obj, int offset,
|
| + ObjectVisitor* v) {
|
| + v->VisitPointer(HeapObject::RawField(obj, offset));
|
| +}
|
| +
|
| +
|
| +template <typename StaticVisitor>
|
| +void BodyDescriptorBase::IteratePointer(Heap* heap, HeapObject* obj,
|
| + int offset) {
|
| + StaticVisitor::VisitPointer(heap, obj, HeapObject::RawField(obj, offset));
|
| +}
|
| +
|
| +
|
| +// Iterates the function object according to the visiting policy.
|
| +template <JSFunction::BodyVisitingPolicy body_visiting_policy>
|
| +class JSFunction::BodyDescriptorImpl final : public BodyDescriptorBase {
|
| + public:
|
| + STATIC_ASSERT(kNonWeakFieldsEndOffset == kCodeEntryOffset);
|
| + STATIC_ASSERT(kCodeEntryOffset + kPointerSize == kNextFunctionLinkOffset);
|
| + STATIC_ASSERT(kNextFunctionLinkOffset + kPointerSize == kSize);
|
| +
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + if (offset < kSize) return true;
|
| + // TODO(ishell): v8:4531, fix when JFunctions are allowed to have
|
| + // in-object properties
|
| + // return IsValidSlotImpl(obj, offset);
|
| + return true;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IteratePointers(obj, kPropertiesOffset, kNonWeakFieldsEndOffset, v);
|
| +
|
| + if (body_visiting_policy & kVisitCodeEntry) {
|
| + v->VisitCodeEntry(obj->address() + kCodeEntryOffset);
|
| + }
|
| +
|
| + if (body_visiting_policy & kVisitNextFunction) {
|
| + IteratePointers(obj, kNextFunctionLinkOffset, kSize, v);
|
| + }
|
| +
|
| + // TODO(ishell): v8:4531, fix when JFunctions are allowed to have in-object
|
| + // properties
|
| + // IterateBodyImpl(obj, kSize, object_size, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointers<StaticVisitor>(heap, obj, kPropertiesOffset,
|
| + kNonWeakFieldsEndOffset);
|
| +
|
| + if (body_visiting_policy & kVisitCodeEntry) {
|
| + StaticVisitor::VisitCodeEntry(heap, obj,
|
| + obj->address() + kCodeEntryOffset);
|
| + }
|
| +
|
| + if (body_visiting_policy & kVisitNextFunction) {
|
| + IteratePointers<StaticVisitor>(heap, obj, kNextFunctionLinkOffset, kSize);
|
| + }
|
| +
|
| + // TODO(ishell): v8:4531, fix when JFunctions are allowed to have in-object
|
| + // properties
|
| + // IterateBodyImpl<StaticVisitor>(heap, obj, kSize, object_size);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) {
|
| + // TODO(ishell): v8:4531, fix when JFunctions are allowed to have in-object
|
| + // properties
|
| + return JSFunction::kSize;
|
| + }
|
| +};
|
| +
|
| +
|
| +class JSArrayBuffer::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + STATIC_ASSERT(kByteLengthOffset + kPointerSize == kBackingStoreOffset);
|
| + STATIC_ASSERT(kBackingStoreOffset + kPointerSize == kBitFieldSlot);
|
| + STATIC_ASSERT(kBitFieldSlot + kPointerSize == kSize);
|
| +
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + if (offset < kBackingStoreOffset) return true;
|
| + if (offset < kSize) return false;
|
| + if (offset < kSizeWithInternalFields) return true;
|
| + // TODO(ishell): v8:4531, fix when JSArrayBuffers are allowed to have
|
| + // in-object properties
|
| + // return IsValidSlotImpl(obj, offset);
|
| + return true;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IteratePointers(obj, kPropertiesOffset, kBackingStoreOffset, v);
|
| + IteratePointers(obj, kSize, kSizeWithInternalFields, v);
|
| +
|
| + // TODO(ishell): v8:4531, fix when JSArrayBuffers are allowed to have
|
| + // in-object properties
|
| + // IterateBodyImpl(obj, kSize, object_size, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointers<StaticVisitor>(heap, obj, kPropertiesOffset,
|
| + kBackingStoreOffset);
|
| + IteratePointers<StaticVisitor>(heap, obj, kSize, kSizeWithInternalFields);
|
| +
|
| + // TODO(ishell): v8:4531, fix when JSArrayBuffers are allowed to have
|
| + // in-object properties
|
| + // IterateBodyImpl<StaticVisitor>(heap, obj, kSize, object_size);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) {
|
| + // TODO(ishell): v8:4531, fix when JSArrayBuffers are allowed to have
|
| + // in-object properties
|
| + // return map->instance_size();
|
| + return kSizeWithInternalFields;
|
| + }
|
| +};
|
| +
|
| +
|
| +class BytecodeArray::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + return offset == kConstantPoolOffset;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IteratePointer(obj, kConstantPoolOffset, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointer<StaticVisitor>(heap, obj, kConstantPoolOffset);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) {
|
| + return SizeFor(
|
| + reinterpret_cast<FixedArray*>(object)->synchronized_length());
|
| + }
|
| +};
|
| +
|
| +
|
| +class FixedTypedArrayBase::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + return offset == kBasePointerOffset;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IteratePointer(obj, kBasePointerOffset, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointer<StaticVisitor>(heap, obj, kBasePointerOffset);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) {
|
| + return reinterpret_cast<FixedTypedArrayBase*>(object)->size();
|
| + }
|
| +};
|
| +
|
| +
|
| +class JSWeakCollection::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + // TODO(ishell): v8:4531, fix when JSWeakCollections are allowed to have
|
| + // in-object properties
|
| + // return IsValidSlotImpl(obj, offset);
|
| + return true;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IteratePointers(obj, kPropertiesOffset, kSize, v);
|
| +
|
| + // TODO(ishell): v8:4531, fix when JSWeakCollections are allowed to have
|
| + // in-object properties
|
| + // IterateBodyImpl(obj, kSize, object_size, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointers<StaticVisitor>(heap, obj, kPropertiesOffset, kSize);
|
| +
|
| + // TODO(ishell): v8:4531, fix when JSWeakCollections are allowed to have
|
| + // in-object properties
|
| + // IterateBodyImpl<StaticVisitor>(heap, obj, kSize, object_size);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) { return kSize; }
|
| +};
|
| +
|
| +
|
| +class Foreign::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) { return false; }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + v->VisitExternalReference(reinterpret_cast<Address*>(
|
| + HeapObject::RawField(obj, kForeignAddressOffset)));
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + StaticVisitor::VisitExternalReference(reinterpret_cast<Address*>(
|
| + HeapObject::RawField(obj, kForeignAddressOffset)));
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) { return kSize; }
|
| +};
|
| +
|
| +
|
| +class ExternalOneByteString::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) { return false; }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + typedef v8::String::ExternalOneByteStringResource Resource;
|
| + v->VisitExternalOneByteString(reinterpret_cast<Resource**>(
|
| + HeapObject::RawField(obj, kResourceOffset)));
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + typedef v8::String::ExternalOneByteStringResource Resource;
|
| + StaticVisitor::VisitExternalOneByteString(reinterpret_cast<Resource**>(
|
| + HeapObject::RawField(obj, kResourceOffset)));
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) { return kSize; }
|
| +};
|
| +
|
| +
|
| +class ExternalTwoByteString::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + static bool IsValidSlot(HeapObject* obj, int offset) { return false; }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + typedef v8::String::ExternalStringResource Resource;
|
| + v->VisitExternalTwoByteString(reinterpret_cast<Resource**>(
|
| + HeapObject::RawField(obj, kResourceOffset)));
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + typedef v8::String::ExternalStringResource Resource;
|
| + StaticVisitor::VisitExternalTwoByteString(reinterpret_cast<Resource**>(
|
| + HeapObject::RawField(obj, kResourceOffset)));
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) { return kSize; }
|
| +};
|
| +
|
| +
|
| +class Code::BodyDescriptor final : public BodyDescriptorBase {
|
| + public:
|
| + STATIC_ASSERT(kRelocationInfoOffset + kPointerSize == kHandlerTableOffset);
|
| + STATIC_ASSERT(kHandlerTableOffset + kPointerSize ==
|
| + kDeoptimizationDataOffset);
|
| + STATIC_ASSERT(kDeoptimizationDataOffset + kPointerSize ==
|
| + kTypeFeedbackInfoOffset);
|
| + STATIC_ASSERT(kTypeFeedbackInfoOffset + kPointerSize == kNextCodeLinkOffset);
|
| +
|
| + static bool IsValidSlot(HeapObject* obj, int offset) {
|
| + // Slots in code can't be invalid because we never trim code objects.
|
| + return true;
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, ObjectVisitor* v) {
|
| + int mode_mask = RelocInfo::kCodeTargetMask |
|
| + RelocInfo::ModeMask(RelocInfo::EMBEDDED_OBJECT) |
|
| + RelocInfo::ModeMask(RelocInfo::CELL) |
|
| + RelocInfo::ModeMask(RelocInfo::EXTERNAL_REFERENCE) |
|
| + RelocInfo::ModeMask(RelocInfo::INTERNAL_REFERENCE) |
|
| + RelocInfo::ModeMask(RelocInfo::INTERNAL_REFERENCE_ENCODED) |
|
| + RelocInfo::ModeMask(RelocInfo::RUNTIME_ENTRY) |
|
| + RelocInfo::kDebugBreakSlotMask;
|
| +
|
| + IteratePointers(obj, kRelocationInfoOffset, kNextCodeLinkOffset, v);
|
| + v->VisitNextCodeLink(HeapObject::RawField(obj, kNextCodeLinkOffset));
|
| +
|
| + RelocIterator it(reinterpret_cast<Code*>(obj), mode_mask);
|
| + Isolate* isolate = obj->GetIsolate();
|
| + for (; !it.done(); it.next()) {
|
| + it.rinfo()->Visit(isolate, v);
|
| + }
|
| + }
|
| +
|
| + template <typename ObjectVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size,
|
| + ObjectVisitor* v) {
|
| + IterateBody(obj, v);
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj) {
|
| + int mode_mask = RelocInfo::kCodeTargetMask |
|
| + RelocInfo::ModeMask(RelocInfo::EMBEDDED_OBJECT) |
|
| + RelocInfo::ModeMask(RelocInfo::CELL) |
|
| + RelocInfo::ModeMask(RelocInfo::EXTERNAL_REFERENCE) |
|
| + RelocInfo::ModeMask(RelocInfo::INTERNAL_REFERENCE) |
|
| + RelocInfo::ModeMask(RelocInfo::INTERNAL_REFERENCE_ENCODED) |
|
| + RelocInfo::ModeMask(RelocInfo::RUNTIME_ENTRY) |
|
| + RelocInfo::kDebugBreakSlotMask;
|
| +
|
| + Heap* heap = obj->GetHeap();
|
| + IteratePointers<StaticVisitor>(heap, obj, kRelocationInfoOffset,
|
| + kNextCodeLinkOffset);
|
| + StaticVisitor::VisitNextCodeLink(
|
| + heap, HeapObject::RawField(obj, kNextCodeLinkOffset));
|
| +
|
| + RelocIterator it(reinterpret_cast<Code*>(obj), mode_mask);
|
| + for (; !it.done(); it.next()) {
|
| + it.rinfo()->template Visit<StaticVisitor>(heap);
|
| + }
|
| + }
|
| +
|
| + template <typename StaticVisitor>
|
| + static inline void IterateBody(HeapObject* obj, int object_size) {
|
| + IterateBody<StaticVisitor>(obj);
|
| + }
|
| +
|
| + static inline int SizeOf(Map* map, HeapObject* object) {
|
| + return reinterpret_cast<Code*>(object)->CodeSize();
|
| + }
|
| +};
|
| +
|
| +
|
| +template <typename Op, typename ReturnType, typename T1, typename T2,
|
| + typename T3>
|
| +ReturnType BodyDescriptorApply(InstanceType type, T1 p1, T2 p2, T3 p3) {
|
| + if (type < FIRST_NONSTRING_TYPE) {
|
| + switch (type & kStringRepresentationMask) {
|
| + case kSeqStringTag:
|
| + return ReturnType();
|
| + case kConsStringTag:
|
| + return Op::template apply<ConsString::BodyDescriptor>(p1, p2, p3);
|
| + case kSlicedStringTag:
|
| + return Op::template apply<SlicedString::BodyDescriptor>(p1, p2, p3);
|
| + case kExternalStringTag:
|
| + if ((type & kStringEncodingMask) == kOneByteStringTag) {
|
| + return Op::template apply<ExternalOneByteString::BodyDescriptor>(
|
| + p1, p2, p3);
|
| + } else {
|
| + return Op::template apply<ExternalTwoByteString::BodyDescriptor>(
|
| + p1, p2, p3);
|
| + }
|
| + }
|
| + UNREACHABLE();
|
| + return ReturnType();
|
| + }
|
| +
|
| + switch (type) {
|
| + case FIXED_ARRAY_TYPE:
|
| + return Op::template apply<FixedArray::BodyDescriptor>(p1, p2, p3);
|
| + case FIXED_DOUBLE_ARRAY_TYPE:
|
| + return ReturnType();
|
| + case JS_OBJECT_TYPE:
|
| + case JS_CONTEXT_EXTENSION_OBJECT_TYPE:
|
| + case JS_GENERATOR_OBJECT_TYPE:
|
| + case JS_MODULE_TYPE:
|
| + case JS_VALUE_TYPE:
|
| + case JS_DATE_TYPE:
|
| + case JS_ARRAY_TYPE:
|
| + case JS_TYPED_ARRAY_TYPE:
|
| + case JS_DATA_VIEW_TYPE:
|
| + case JS_SET_TYPE:
|
| + case JS_MAP_TYPE:
|
| + case JS_SET_ITERATOR_TYPE:
|
| + case JS_MAP_ITERATOR_TYPE:
|
| + case JS_ITERATOR_RESULT_TYPE:
|
| + case JS_REGEXP_TYPE:
|
| + case JS_GLOBAL_PROXY_TYPE:
|
| + case JS_GLOBAL_OBJECT_TYPE:
|
| + case JS_MESSAGE_OBJECT_TYPE:
|
| + return Op::template apply<JSObject::BodyDescriptor>(p1, p2, p3);
|
| + case JS_WEAK_MAP_TYPE:
|
| + case JS_WEAK_SET_TYPE:
|
| + return Op::template apply<JSWeakCollection::BodyDescriptor>(p1, p2, p3);
|
| + case JS_ARRAY_BUFFER_TYPE:
|
| + return Op::template apply<JSArrayBuffer::BodyDescriptor>(p1, p2, p3);
|
| + case JS_FUNCTION_TYPE:
|
| + return Op::template apply<JSFunction::BodyDescriptor>(p1, p2, p3);
|
| + case ODDBALL_TYPE:
|
| + return Op::template apply<Oddball::BodyDescriptor>(p1, p2, p3);
|
| + case JS_PROXY_TYPE:
|
| + return Op::template apply<JSProxy::BodyDescriptor>(p1, p2, p3);
|
| + case JS_FUNCTION_PROXY_TYPE:
|
| + return Op::template apply<JSFunctionProxy::BodyDescriptor>(p1, p2, p3);
|
| + case FOREIGN_TYPE:
|
| + return Op::template apply<Foreign::BodyDescriptor>(p1, p2, p3);
|
| + case MAP_TYPE:
|
| + return Op::template apply<Map::BodyDescriptor>(p1, p2, p3);
|
| + case CODE_TYPE:
|
| + return Op::template apply<Code::BodyDescriptor>(p1, p2, p3);
|
| + case CELL_TYPE:
|
| + return Op::template apply<Cell::BodyDescriptor>(p1, p2, p3);
|
| + case PROPERTY_CELL_TYPE:
|
| + return Op::template apply<PropertyCell::BodyDescriptor>(p1, p2, p3);
|
| + case WEAK_CELL_TYPE:
|
| + return Op::template apply<WeakCell::BodyDescriptor>(p1, p2, p3);
|
| + case SYMBOL_TYPE:
|
| + return Op::template apply<Symbol::BodyDescriptor>(p1, p2, p3);
|
| + case BYTECODE_ARRAY_TYPE:
|
| + return Op::template apply<BytecodeArray::BodyDescriptor>(p1, p2, p3);
|
| +
|
| + case HEAP_NUMBER_TYPE:
|
| + case MUTABLE_HEAP_NUMBER_TYPE:
|
| + case SIMD128_VALUE_TYPE:
|
| + case FILLER_TYPE:
|
| + case BYTE_ARRAY_TYPE:
|
| + case FREE_SPACE_TYPE:
|
| + return ReturnType();
|
| +
|
| +#define TYPED_ARRAY_CASE(Type, type, TYPE, ctype, size) \
|
| + case FIXED_##TYPE##_ARRAY_TYPE: \
|
| + return Op::template apply<FixedTypedArrayBase::BodyDescriptor>(p1, p2, p3);
|
| + TYPED_ARRAYS(TYPED_ARRAY_CASE)
|
| +#undef TYPED_ARRAY_CASE
|
| +
|
| + case SHARED_FUNCTION_INFO_TYPE: {
|
| + return Op::template apply<SharedFunctionInfo::BodyDescriptor>(p1, p2, p3);
|
| + }
|
| +
|
| +#define MAKE_STRUCT_CASE(NAME, Name, name) case NAME##_TYPE:
|
| + STRUCT_LIST(MAKE_STRUCT_CASE)
|
| +#undef MAKE_STRUCT_CASE
|
| + if (type == ALLOCATION_SITE_TYPE) {
|
| + return Op::template apply<AllocationSite::BodyDescriptor>(p1, p2, p3);
|
| + } else {
|
| + return Op::template apply<StructBodyDescriptor>(p1, p2, p3);
|
| + }
|
| + default:
|
| + PrintF("Unknown type: %d\n", type);
|
| + UNREACHABLE();
|
| + return ReturnType();
|
| + }
|
| +}
|
| +
|
| +
|
| +template <typename ObjectVisitor>
|
| +void HeapObject::IterateFast(ObjectVisitor* v) {
|
| + BodyDescriptorBase::IteratePointer(this, kMapOffset, v);
|
| + IterateBody(v);
|
| +}
|
| +
|
| +
|
| +template <typename ObjectVisitor>
|
| +void HeapObject::IterateBodyFast(ObjectVisitor* v) {
|
| + Map* m = map();
|
| + IterateBody(m->instance_type(), SizeFromMap(m), v);
|
| +}
|
| +
|
| +
|
| +struct CallIterateBody {
|
| + template <typename BodyDescriptor, typename ObjectVisitor>
|
| + static void apply(HeapObject* obj, int object_size, ObjectVisitor* v) {
|
| + BodyDescriptor::IterateBody(obj, object_size, v);
|
| + }
|
| +};
|
| +
|
| +template <typename ObjectVisitor>
|
| +void HeapObject::IterateBodyFast(InstanceType type, int object_size,
|
| + ObjectVisitor* v) {
|
| + BodyDescriptorApply<CallIterateBody, void>(type, this, object_size, v);
|
| +}
|
| +} // namespace internal
|
| +} // namespace v8
|
| +
|
| +#endif // V8_OBJECTS_BODY_DESCRIPTORS_INL_H_
|
|
|