Commit e8cab885 authored by ishell's avatar ishell Committed by Commit bot

Move both dynamic and static object body visiting logic to BodyDescriptorBase class.

Review URL: https://codereview.chromium.org/1416243009

Cr-Commit-Position: refs/heads/master@{#31829}
parent 9c8f4f91
......@@ -188,79 +188,34 @@ class VisitorDispatchTable {
};
template <typename StaticVisitor>
class BodyVisitorBase : public AllStatic {
public:
INLINE(static void IteratePointers(Heap* heap, HeapObject* object,
int start_offset, int end_offset)) {
DCHECK(!FLAG_unbox_double_fields || object->map()->HasFastPointerLayout());
IterateRawPointers(heap, object, start_offset, end_offset);
}
INLINE(static void IterateBody(Heap* heap, HeapObject* object,
int start_offset, int end_offset)) {
if (!FLAG_unbox_double_fields || object->map()->HasFastPointerLayout()) {
IterateRawPointers(heap, object, start_offset, end_offset);
} else {
IterateBodyUsingLayoutDescriptor(heap, object, start_offset, end_offset);
}
}
private:
INLINE(static void IterateRawPointers(Heap* heap, HeapObject* object,
int start_offset, int end_offset)) {
StaticVisitor::VisitPointers(heap, object,
HeapObject::RawField(object, start_offset),
HeapObject::RawField(object, end_offset));
}
static void IterateBodyUsingLayoutDescriptor(Heap* heap, HeapObject* object,
int start_offset,
int end_offset) {
DCHECK(FLAG_unbox_double_fields);
DCHECK(IsAligned(start_offset, kPointerSize) &&
IsAligned(end_offset, kPointerSize));
LayoutDescriptorHelper helper(object->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)) {
IterateRawPointers(heap, object, offset, end_of_region_offset);
}
offset = end_of_region_offset;
}
}
};
template <typename StaticVisitor, typename BodyDescriptor, typename ReturnType>
class FlexibleBodyVisitor : public BodyVisitorBase<StaticVisitor> {
class FlexibleBodyVisitor : public AllStatic {
public:
INLINE(static ReturnType Visit(Map* map, HeapObject* object)) {
int object_size = BodyDescriptor::SizeOf(map, object);
BodyVisitorBase<StaticVisitor>::IterateBody(
map->GetHeap(), object, BodyDescriptor::kStartOffset, object_size);
BodyDescriptor::template IterateBody<StaticVisitor>(object, object_size);
return static_cast<ReturnType>(object_size);
}
// This specialization is only suitable for objects containing pointer fields.
template <int object_size>
static inline ReturnType VisitSpecialized(Map* map, HeapObject* object) {
DCHECK(BodyDescriptor::SizeOf(map, object) == object_size);
BodyVisitorBase<StaticVisitor>::IteratePointers(
map->GetHeap(), object, BodyDescriptor::kStartOffset, object_size);
DCHECK(!FLAG_unbox_double_fields || map->HasFastPointerLayout());
StaticVisitor::VisitPointers(
object->GetHeap(), object,
HeapObject::RawField(object, BodyDescriptor::kStartOffset),
HeapObject::RawField(object, object_size));
return static_cast<ReturnType>(object_size);
}
};
template <typename StaticVisitor, typename BodyDescriptor, typename ReturnType>
class FixedBodyVisitor : public BodyVisitorBase<StaticVisitor> {
class FixedBodyVisitor : public AllStatic {
public:
INLINE(static ReturnType Visit(Map* map, HeapObject* object)) {
BodyVisitorBase<StaticVisitor>::IterateBody(map->GetHeap(), object,
BodyDescriptor::kStartOffset,
BodyDescriptor::kEndOffset);
BodyDescriptor::template IterateBody<StaticVisitor>(object);
return static_cast<ReturnType>(BodyDescriptor::kSize);
}
};
......
......@@ -7841,7 +7841,8 @@ Relocatable::~Relocatable() {
// static
int JSObject::BodyDescriptor::SizeOf(Map* map, HeapObject* object) {
template <int start_offset>
int FlexibleBodyDescriptor<start_offset>::SizeOf(Map* map, HeapObject* object) {
return map->instance_size();
}
......@@ -7852,12 +7853,6 @@ int FixedArray::BodyDescriptor::SizeOf(Map* map, HeapObject* object) {
}
// static
int StructBodyDescriptor::SizeOf(Map* map, HeapObject* object) {
return map->instance_size();
}
void Foreign::ForeignIterateBody(ObjectVisitor* v) {
v->VisitExternalReference(
reinterpret_cast<Address*>(FIELD_ADDR(this, kForeignAddressOffset)));
......@@ -7914,48 +7909,54 @@ void ExternalTwoByteString::ExternalTwoByteStringIterateBody() {
}
static inline void IterateBodyUsingLayoutDescriptor(HeapObject* object,
int start_offset,
int end_offset,
ObjectVisitor* v) {
DCHECK(FLAG_unbox_double_fields);
DCHECK(IsAligned(start_offset, kPointerSize) &&
IsAligned(end_offset, kPointerSize));
LayoutDescriptorHelper helper(object->map());
DCHECK(!helper.all_fields_tagged());
for (int offset = start_offset; offset < end_offset; offset += kPointerSize) {
// Visit all tagged fields.
if (helper.IsTagged(offset)) {
v->VisitPointer(HeapObject::RawField(object, offset));
}
}
}
template<int start_offset, int end_offset, int size>
void FixedBodyDescriptor<start_offset, end_offset, size>::IterateBody(
HeapObject* obj,
ObjectVisitor* v) {
void BodyDescriptorBase::IterateBodyImpl(HeapObject* obj, int start_offset,
int end_offset, ObjectVisitor* v) {
if (!FLAG_unbox_double_fields || obj->map()->HasFastPointerLayout()) {
v->VisitPointers(HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, end_offset));
} else {
IterateBodyUsingLayoutDescriptor(obj, start_offset, end_offset, v);
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)) {
v->VisitPointers(HeapObject::RawField(obj, offset),
HeapObject::RawField(obj, end_of_region_offset));
}
offset = end_of_region_offset;
}
}
}
template<int start_offset>
void FlexibleBodyDescriptor<start_offset>::IterateBody(HeapObject* obj,
int object_size,
ObjectVisitor* v) {
template <typename StaticVisitor>
void BodyDescriptorBase::IterateBodyImpl(HeapObject* obj, int start_offset,
int end_offset) {
Heap* heap = obj->GetHeap();
if (!FLAG_unbox_double_fields || obj->map()->HasFastPointerLayout()) {
v->VisitPointers(HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, object_size));
StaticVisitor::VisitPointers(heap, obj,
HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, end_offset));
} else {
IterateBodyUsingLayoutDescriptor(obj, start_offset, object_size, v);
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)) {
StaticVisitor::VisitPointers(
heap, obj, HeapObject::RawField(obj, offset),
HeapObject::RawField(obj, end_of_region_offset));
}
offset = end_of_region_offset;
}
}
}
......
......@@ -1637,46 +1637,69 @@ class HeapObject: public Object {
};
// This is the base class for object's body descriptors.
class BodyDescriptorBase {
protected:
static inline void IterateBodyImpl(HeapObject* obj, int start_offset,
int end_offset, ObjectVisitor* v);
template <typename StaticVisitor>
static inline void IterateBodyImpl(HeapObject* obj, int start_offset,
int end_offset);
};
// This class describes a body of an object of a fixed size
// in which all pointer fields are located in the [start_offset, end_offset)
// interval.
template<int start_offset, int end_offset, int size>
class FixedBodyDescriptor {
template <int start_offset, int end_offset, int size>
class FixedBodyDescriptor : public BodyDescriptorBase {
public:
static const int kStartOffset = start_offset;
static const int kEndOffset = end_offset;
static const int kSize = size;
static inline void IterateBody(HeapObject* obj, ObjectVisitor* v);
static inline void IterateBody(HeapObject* obj, ObjectVisitor* v) {
IterateBodyImpl(obj, start_offset, end_offset, v);
}
template<typename StaticVisitor>
template <typename StaticVisitor>
static inline void IterateBody(HeapObject* obj) {
StaticVisitor::VisitPointers(HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, end_offset));
IterateBodyImpl<StaticVisitor>(obj, start_offset, end_offset);
}
};
// This class describes a body of an object of a variable size
// This base class describes a body of an object of a variable size
// in which all pointer fields are located in the [start_offset, object_size)
// interval.
template<int start_offset>
class FlexibleBodyDescriptor {
template <int start_offset>
class FlexibleBodyDescriptorBase : public BodyDescriptorBase {
public:
static const int kStartOffset = start_offset;
static inline void IterateBody(HeapObject* obj,
int object_size,
ObjectVisitor* v);
static inline void IterateBody(HeapObject* obj, int object_size,
ObjectVisitor* v) {
IterateBodyImpl(obj, start_offset, object_size, v);
}
template<typename StaticVisitor>
template <typename StaticVisitor>
static inline void IterateBody(HeapObject* obj, int object_size) {
StaticVisitor::VisitPointers(HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, object_size));
IterateBodyImpl<StaticVisitor>(obj, start_offset, object_size);
}
};
// This class describes a body of an object of a variable size
// in which all pointer fields are located in the [start_offset, object_size)
// interval. The size of the object is taken from the map.
template <int start_offset>
class FlexibleBodyDescriptor : public FlexibleBodyDescriptorBase<start_offset> {
public:
static inline int SizeOf(Map* map, HeapObject* object);
};
// The HeapNumber class describes heap allocated numbers that cannot be
// represented in a Smi (small integer)
class HeapNumber: public HeapObject {
......@@ -2477,10 +2500,7 @@ class JSObject: public JSReceiver {
STATIC_ASSERT(kHeaderSize == Internals::kJSObjectHeaderSize);
class BodyDescriptor : public FlexibleBodyDescriptor<kPropertiesOffset> {
public:
static inline int SizeOf(Map* map, HeapObject* object);
};
typedef FlexibleBodyDescriptor<kPropertiesOffset> BodyDescriptor;
Context* GetCreationContext();
......@@ -2659,7 +2679,7 @@ class FixedArray: public FixedArrayBase {
// object, the prefix of this array is sorted.
void SortPairs(FixedArray* numbers, uint32_t len);
class BodyDescriptor : public FlexibleBodyDescriptor<kHeaderSize> {
class BodyDescriptor : public FlexibleBodyDescriptorBase<kHeaderSize> {
public:
static inline int SizeOf(Map* map, HeapObject* object);
};
......@@ -10713,11 +10733,7 @@ class ObjectVisitor BASE_EMBEDDED {
};
class StructBodyDescriptor : public
FlexibleBodyDescriptor<HeapObject::kHeaderSize> {
public:
static inline int SizeOf(Map* map, HeapObject* object);
};
typedef FlexibleBodyDescriptor<HeapObject::kHeaderSize> StructBodyDescriptor;
// BooleanBit is a helper class for setting and getting a bit in an integer.
......
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