Commit 737a4e4c authored by Marja Hölttä's avatar Marja Hölttä Committed by Commit Bot

[in-place weak refs] Cleanup: Remove BodyDescriptorWeak

Unification: now BodyDescriptor deals with all weakness types.

This doesn't replace the weak list pointers with in-place weak references, since
it would cause extra work: we anyway recreate the lists after GC, so we
shouldn't track them at all during GC.

BUG=v8:7308

Change-Id: Ifb2f573d3e7ee311136b59e185cc659487c9cab3
Reviewed-on: https://chromium-review.googlesource.com/1229894Reviewed-by: 's avatarMichael Lippautz <mlippautz@chromium.org>
Commit-Queue: Marja Hölttä <marja@chromium.org>
Cr-Commit-Position: refs/heads/master@{#56030}
parent 3f661258
...@@ -609,12 +609,7 @@ class Context : public FixedArray, public NeverReadOnlySpaceObject { ...@@ -609,12 +609,7 @@ class Context : public FixedArray, public NeverReadOnlySpaceObject {
static const int kSize = kHeaderSize + NATIVE_CONTEXT_SLOTS * kPointerSize; static const int kSize = kHeaderSize + NATIVE_CONTEXT_SLOTS * kPointerSize;
static const int kNotFound = -1; static const int kNotFound = -1;
// GC support. class BodyDescriptor;
typedef FixedBodyDescriptor<kHeaderSize, kSize, kSize> BodyDescriptor;
typedef FixedBodyDescriptor<
kHeaderSize, kHeaderSize + FIRST_WEAK_SLOT * kPointerSize, kSize>
BodyDescriptorWeak;
private: private:
#ifdef DEBUG #ifdef DEBUG
......
...@@ -151,6 +151,11 @@ class ConcurrentMarkingVisitor final ...@@ -151,6 +151,11 @@ class ConcurrentMarkingVisitor final
} }
} }
// Weak list pointers should be ignored during marking. The lists are
// reconstructed after GC.
void VisitCustomWeakPointers(HeapObject* host, Object** start,
Object** end) override {}
void VisitPointersInSnapshot(HeapObject* host, const SlotSnapshot& snapshot) { void VisitPointersInSnapshot(HeapObject* host, const SlotSnapshot& snapshot) {
for (int i = 0; i < snapshot.number_of_slots(); i++) { for (int i = 0; i < snapshot.number_of_slots(); i++) {
Object** slot = snapshot.slot(i); Object** slot = snapshot.slot(i);
...@@ -263,7 +268,7 @@ class ConcurrentMarkingVisitor final ...@@ -263,7 +268,7 @@ class ConcurrentMarkingVisitor final
} }
// =========================================================================== // ===========================================================================
// Objects with weak fields and/or side-effectiful visitation. // Side-effectful visitation.
// =========================================================================== // ===========================================================================
int VisitBytecodeArray(Map* map, BytecodeArray* object) { int VisitBytecodeArray(Map* map, BytecodeArray* object) {
...@@ -275,22 +280,6 @@ class ConcurrentMarkingVisitor final ...@@ -275,22 +280,6 @@ class ConcurrentMarkingVisitor final
return size; return size;
} }
int VisitAllocationSite(Map* map, AllocationSite* object) {
if (!ShouldVisit(object)) return 0;
int size = AllocationSite::BodyDescriptorWeak::SizeOf(map, object);
VisitMapPointer(object, object->map_slot());
AllocationSite::BodyDescriptorWeak::IterateBody(map, object, size, this);
return size;
}
int VisitCodeDataContainer(Map* map, CodeDataContainer* object) {
if (!ShouldVisit(object)) return 0;
int size = CodeDataContainer::BodyDescriptorWeak::SizeOf(map, object);
VisitMapPointer(object, object->map_slot());
CodeDataContainer::BodyDescriptorWeak::IterateBody(map, object, size, this);
return size;
}
int VisitMap(Map* meta_map, Map* map) { int VisitMap(Map* meta_map, Map* map) {
if (marking_state_.IsGrey(map)) { if (marking_state_.IsGrey(map)) {
// Maps have ad-hoc weakness for descriptor arrays. They also clear the // Maps have ad-hoc weakness for descriptor arrays. They also clear the
...@@ -308,14 +297,6 @@ class ConcurrentMarkingVisitor final ...@@ -308,14 +297,6 @@ class ConcurrentMarkingVisitor final
return 0; return 0;
} }
int VisitNativeContext(Map* map, Context* object) {
if (!ShouldVisit(object)) return 0;
int size = Context::BodyDescriptorWeak::SizeOf(map, object);
VisitMapPointer(object, object->map_slot());
Context::BodyDescriptorWeak::IterateBody(map, object, size, this);
return size;
}
int VisitTransitionArray(Map* map, TransitionArray* array) { int VisitTransitionArray(Map* map, TransitionArray* array) {
if (!ShouldVisit(array)) return 0; if (!ShouldVisit(array)) return 0;
VisitMapPointer(array, array->map_slot()); VisitMapPointer(array, array->map_slot());
......
...@@ -23,16 +23,6 @@ MarkingVisitor<fixed_array_mode, retaining_path_mode, ...@@ -23,16 +23,6 @@ MarkingVisitor<fixed_array_mode, retaining_path_mode,
collector_(collector), collector_(collector),
marking_state_(marking_state) {} marking_state_(marking_state) {}
template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode,
MarkingState>::VisitAllocationSite(Map* map,
AllocationSite* object) {
int size = AllocationSite::BodyDescriptorWeak::SizeOf(map, object);
AllocationSite::BodyDescriptorWeak::IterateBody(map, object, size, this);
return size;
}
template <FixedArrayVisitationMode fixed_array_mode, template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState> TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode, int MarkingVisitor<fixed_array_mode, retaining_path_mode,
...@@ -44,15 +34,6 @@ int MarkingVisitor<fixed_array_mode, retaining_path_mode, ...@@ -44,15 +34,6 @@ int MarkingVisitor<fixed_array_mode, retaining_path_mode,
return size; return size;
} }
template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode, MarkingState>::
VisitCodeDataContainer(Map* map, CodeDataContainer* object) {
int size = CodeDataContainer::BodyDescriptorWeak::SizeOf(map, object);
CodeDataContainer::BodyDescriptorWeak::IterateBody(map, object, size, this);
return size;
}
template <FixedArrayVisitationMode fixed_array_mode, template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState> TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode, int MarkingVisitor<fixed_array_mode, retaining_path_mode,
...@@ -128,16 +109,6 @@ int MarkingVisitor<fixed_array_mode, retaining_path_mode, ...@@ -128,16 +109,6 @@ int MarkingVisitor<fixed_array_mode, retaining_path_mode,
return size; return size;
} }
template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode,
MarkingState>::VisitNativeContext(Map* map,
Context* context) {
int size = Context::BodyDescriptorWeak::SizeOf(map, context);
Context::BodyDescriptorWeak::IterateBody(map, context, size, this);
return size;
}
template <FixedArrayVisitationMode fixed_array_mode, template <FixedArrayVisitationMode fixed_array_mode,
TraceRetainingPathMode retaining_path_mode, typename MarkingState> TraceRetainingPathMode retaining_path_mode, typename MarkingState>
int MarkingVisitor<fixed_array_mode, retaining_path_mode, int MarkingVisitor<fixed_array_mode, retaining_path_mode,
......
...@@ -905,14 +905,11 @@ class MarkingVisitor final ...@@ -905,14 +905,11 @@ class MarkingVisitor final
V8_INLINE bool ShouldVisitMapPointer() { return false; } V8_INLINE bool ShouldVisitMapPointer() { return false; }
V8_INLINE int VisitAllocationSite(Map* map, AllocationSite* object);
V8_INLINE int VisitBytecodeArray(Map* map, BytecodeArray* object); V8_INLINE int VisitBytecodeArray(Map* map, BytecodeArray* object);
V8_INLINE int VisitCodeDataContainer(Map* map, CodeDataContainer* object);
V8_INLINE int VisitEphemeronHashTable(Map* map, EphemeronHashTable* object); V8_INLINE int VisitEphemeronHashTable(Map* map, EphemeronHashTable* object);
V8_INLINE int VisitFixedArray(Map* map, FixedArray* object); V8_INLINE int VisitFixedArray(Map* map, FixedArray* object);
V8_INLINE int VisitJSApiObject(Map* map, JSObject* object); V8_INLINE int VisitJSApiObject(Map* map, JSObject* object);
V8_INLINE int VisitMap(Map* map, Map* object); V8_INLINE int VisitMap(Map* map, Map* object);
V8_INLINE int VisitNativeContext(Map* map, Context* object);
V8_INLINE int VisitTransitionArray(Map* map, TransitionArray* object); V8_INLINE int VisitTransitionArray(Map* map, TransitionArray* object);
// ObjectVisitor implementation. // ObjectVisitor implementation.
...@@ -925,6 +922,11 @@ class MarkingVisitor final ...@@ -925,6 +922,11 @@ class MarkingVisitor final
V8_INLINE void VisitEmbeddedPointer(Code* host, RelocInfo* rinfo) final; V8_INLINE void VisitEmbeddedPointer(Code* host, RelocInfo* rinfo) final;
V8_INLINE void VisitCodeTarget(Code* host, RelocInfo* rinfo) final; V8_INLINE void VisitCodeTarget(Code* host, RelocInfo* rinfo) final;
// Weak list pointers should be ignored during marking. The lists are
// reconstructed after GC.
void VisitCustomWeakPointers(HeapObject* host, Object** start,
Object** end) final {}
private: private:
// Granularity in which FixedArrays are scanned if |fixed_array_mode| // Granularity in which FixedArrays are scanned if |fixed_array_mode|
// is true. // is true.
......
...@@ -86,6 +86,19 @@ void BodyDescriptorBase::IterateMaybeWeakPointer(HeapObject* obj, int offset, ...@@ -86,6 +86,19 @@ void BodyDescriptorBase::IterateMaybeWeakPointer(HeapObject* obj, int offset,
v->VisitPointer(obj, HeapObject::RawMaybeWeakField(obj, offset)); v->VisitPointer(obj, HeapObject::RawMaybeWeakField(obj, offset));
} }
template <typename ObjectVisitor>
DISABLE_CFI_PERF void BodyDescriptorBase::IterateCustomWeakPointers(
HeapObject* obj, int start_offset, int end_offset, ObjectVisitor* v) {
v->VisitCustomWeakPointers(obj, HeapObject::RawField(obj, start_offset),
HeapObject::RawField(obj, end_offset));
}
template <typename ObjectVisitor>
void BodyDescriptorBase::IterateCustomWeakPointer(HeapObject* obj, int offset,
ObjectVisitor* v) {
v->VisitCustomWeakPointer(obj, HeapObject::RawField(obj, offset));
}
class JSObject::BodyDescriptor final : public BodyDescriptorBase { class JSObject::BodyDescriptor final : public BodyDescriptorBase {
public: public:
static const int kStartOffset = JSReceiver::kPropertiesOrHashOffset; static const int kStartOffset = JSReceiver::kPropertiesOrHashOffset;
...@@ -149,8 +162,7 @@ class JSFunction::BodyDescriptor final : public BodyDescriptorBase { ...@@ -149,8 +162,7 @@ class JSFunction::BodyDescriptor final : public BodyDescriptorBase {
} }
}; };
template <bool includeWeakNext> class AllocationSite::BodyDescriptor final : public BodyDescriptorBase {
class AllocationSite::BodyDescriptorImpl final : public BodyDescriptorBase {
public: public:
STATIC_ASSERT(AllocationSite::kCommonPointerFieldEndOffset == STATIC_ASSERT(AllocationSite::kCommonPointerFieldEndOffset ==
AllocationSite::kPretenureDataOffset); AllocationSite::kPretenureDataOffset);
...@@ -165,8 +177,7 @@ class AllocationSite::BodyDescriptorImpl final : public BodyDescriptorBase { ...@@ -165,8 +177,7 @@ class AllocationSite::BodyDescriptorImpl final : public BodyDescriptorBase {
return true; return true;
} }
// check for weak_next offset // check for weak_next offset
if (includeWeakNext && if (map->instance_size() == AllocationSite::kSizeWithWeakNext &&
map->instance_size() == AllocationSite::kSizeWithWeakNext &&
offset == AllocationSite::kWeakNextOffset) { offset == AllocationSite::kWeakNextOffset) {
return true; return true;
} }
...@@ -179,12 +190,12 @@ class AllocationSite::BodyDescriptorImpl final : public BodyDescriptorBase { ...@@ -179,12 +190,12 @@ class AllocationSite::BodyDescriptorImpl final : public BodyDescriptorBase {
// Iterate over all the common pointer fields // Iterate over all the common pointer fields
IteratePointers(obj, AllocationSite::kStartOffset, IteratePointers(obj, AllocationSite::kStartOffset,
AllocationSite::kCommonPointerFieldEndOffset, v); AllocationSite::kCommonPointerFieldEndOffset, v);
// Skip PretenureDataOffset and PretenureCreateCount which are Int32 fields // Skip PretenureDataOffset and PretenureCreateCount which are Int32 fields.
// Visit weak_next only for full body descriptor and if it has weak_next // Visit weak_next only if it has weak_next field.
// field if (object_size == AllocationSite::kSizeWithWeakNext) {
if (includeWeakNext && object_size == AllocationSite::kSizeWithWeakNext) IterateCustomWeakPointers(obj, AllocationSite::kWeakNextOffset,
IteratePointers(obj, AllocationSite::kWeakNextOffset, AllocationSite::kSizeWithWeakNext, v);
AllocationSite::kSizeWithWeakNext, v); }
} }
static inline int SizeOf(Map* map, HeapObject* object) { static inline int SizeOf(Map* map, HeapObject* object) {
...@@ -647,6 +658,49 @@ class DataHandler::BodyDescriptor final : public BodyDescriptorBase { ...@@ -647,6 +658,49 @@ class DataHandler::BodyDescriptor final : public BodyDescriptorBase {
} }
}; };
class Context::BodyDescriptor final : public BodyDescriptorBase {
public:
static bool IsValidSlot(Map* map, HeapObject* obj, int offset) {
return offset >= Context::kHeaderSize && offset < Context::kSize;
}
template <typename ObjectVisitor>
static inline void IterateBody(Map* map, HeapObject* obj, int object_size,
ObjectVisitor* v) {
IteratePointers(obj, Context::kHeaderSize,
Context::kHeaderSize + FIRST_WEAK_SLOT * kPointerSize, v);
IterateCustomWeakPointers(
obj, Context::kHeaderSize + FIRST_WEAK_SLOT * kPointerSize,
Context::kSize, v);
}
static inline int SizeOf(Map* map, HeapObject* object) {
return Context::kSize;
}
};
class CodeDataContainer::BodyDescriptor final : public BodyDescriptorBase {
public:
static bool IsValidSlot(Map* map, HeapObject* obj, int offset) {
return offset >= CodeDataContainer::kHeaderSize &&
offset < CodeDataContainer::kSize;
}
template <typename ObjectVisitor>
static inline void IterateBody(Map* map, HeapObject* obj, int object_size,
ObjectVisitor* v) {
IteratePointers(obj, CodeDataContainer::kHeaderSize,
CodeDataContainer::kPointerFieldsStrongEndOffset, v);
IterateCustomWeakPointers(
obj, CodeDataContainer::kPointerFieldsStrongEndOffset,
CodeDataContainer::kPointerFieldsWeakEndOffset, v);
}
static inline int SizeOf(Map* map, HeapObject* object) {
return CodeDataContainer::kSize;
}
};
template <typename Op, typename ReturnType, typename T1, typename T2, template <typename Op, typename ReturnType, typename T1, typename T2,
typename T3, typename T4> typename T3, typename T4>
ReturnType BodyDescriptorApply(InstanceType type, T1 p1, T2 p2, T3 p3, T4 p4) { ReturnType BodyDescriptorApply(InstanceType type, T1 p1, T2 p2, T3 p3, T4 p4) {
......
...@@ -36,6 +36,15 @@ class BodyDescriptorBase { ...@@ -36,6 +36,15 @@ class BodyDescriptorBase {
static inline void IteratePointer(HeapObject* obj, int offset, static inline void IteratePointer(HeapObject* obj, int offset,
ObjectVisitor* v); ObjectVisitor* v);
template <typename ObjectVisitor>
static inline void IterateCustomWeakPointers(HeapObject* obj,
int start_offset, int end_offset,
ObjectVisitor* v);
template <typename ObjectVisitor>
static inline void IterateCustomWeakPointer(HeapObject* obj, int offset,
ObjectVisitor* v);
template <typename ObjectVisitor> template <typename ObjectVisitor>
static inline void IterateMaybeWeakPointers(HeapObject* obj, int start_offset, static inline void IterateMaybeWeakPointers(HeapObject* obj, int start_offset,
int end_offset, ObjectVisitor* v); int end_offset, ObjectVisitor* v);
......
...@@ -150,16 +150,7 @@ class AllocationSite : public Struct, public NeverReadOnlySpaceObject { ...@@ -150,16 +150,7 @@ class AllocationSite : public Struct, public NeverReadOnlySpaceObject {
static const int kStartOffset = HeapObject::kHeaderSize; static const int kStartOffset = HeapObject::kHeaderSize;
template <bool includeWeakNext> class BodyDescriptor;
class BodyDescriptorImpl;
// BodyDescriptor is used to traverse all the pointer fields including
// weak_next
typedef BodyDescriptorImpl<true> BodyDescriptor;
// BodyDescriptorWeak is used to traverse all the pointer fields
// except for weak_next
typedef BodyDescriptorImpl<false> BodyDescriptorWeak;
private: private:
inline bool PretenuringDecisionMade() const; inline bool PretenuringDecisionMade() const;
......
...@@ -477,15 +477,7 @@ class CodeDataContainer : public HeapObject, public NeverReadOnlySpaceObject { ...@@ -477,15 +477,7 @@ class CodeDataContainer : public HeapObject, public NeverReadOnlySpaceObject {
static const int kPointerFieldsStrongEndOffset = kNextCodeLinkOffset; static const int kPointerFieldsStrongEndOffset = kNextCodeLinkOffset;
static const int kPointerFieldsWeakEndOffset = kKindSpecificFlagsOffset; static const int kPointerFieldsWeakEndOffset = kKindSpecificFlagsOffset;
// Ignores weakness. class BodyDescriptor;
typedef FixedBodyDescriptor<HeapObject::kHeaderSize,
kPointerFieldsWeakEndOffset, kSize>
BodyDescriptor;
// Respects weakness.
typedef FixedBodyDescriptor<HeapObject::kHeaderSize,
kPointerFieldsStrongEndOffset, kSize>
BodyDescriptorWeak;
private: private:
DISALLOW_IMPLICIT_CONSTRUCTORS(CodeDataContainer); DISALLOW_IMPLICIT_CONSTRUCTORS(CodeDataContainer);
......
...@@ -93,6 +93,15 @@ class ObjectVisitor { ...@@ -93,6 +93,15 @@ class ObjectVisitor {
virtual void VisitPointers(HeapObject* host, MaybeObject** start, virtual void VisitPointers(HeapObject* host, MaybeObject** start,
MaybeObject** end) = 0; MaybeObject** end) = 0;
// Custom weak pointers must be ignored by the GC but not other
// visitors. They're used for e.g., lists that are recreated after GC. The
// default implementation treats them as strong pointers. Visitors who want to
// ignore them must override this function with empty.
virtual void VisitCustomWeakPointers(HeapObject* host, Object** start,
Object** end) {
VisitPointers(host, start, end);
}
// Handy shorthand for visiting a single pointer. // Handy shorthand for visiting a single pointer.
virtual void VisitPointer(HeapObject* host, Object** p) { virtual void VisitPointer(HeapObject* host, Object** p) {
VisitPointers(host, p, p + 1); VisitPointers(host, p, p + 1);
...@@ -100,6 +109,9 @@ class ObjectVisitor { ...@@ -100,6 +109,9 @@ class ObjectVisitor {
virtual void VisitPointer(HeapObject* host, MaybeObject** p) { virtual void VisitPointer(HeapObject* host, MaybeObject** p) {
VisitPointers(host, p, p + 1); VisitPointers(host, p, p + 1);
} }
virtual void VisitCustomWeakPointer(HeapObject* host, Object** p) {
VisitCustomWeakPointers(host, p, p + 1);
}
// To allow lazy clearing of inline caches the visitor has // To allow lazy clearing of inline caches the visitor has
// a rich interface for iterating over Code objects ... // a rich interface for iterating over Code objects ...
......
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