зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1273908 - Refactor GC to make it easier to add new kinds of GC thing r=terrence
This commit is contained in:
Родитель
e5d11edbeb
Коммит
3d8e7a7e44
|
@ -98,15 +98,10 @@ JS_FOR_EACH_TRACEKIND(JS_EXPAND_DEF);
|
||||||
enum class RootKind : int8_t
|
enum class RootKind : int8_t
|
||||||
{
|
{
|
||||||
// These map 1:1 with trace kinds.
|
// These map 1:1 with trace kinds.
|
||||||
BaseShape = 0,
|
#define EXPAND_ROOT_KIND(name, _0, _1) \
|
||||||
JitCode,
|
name,
|
||||||
LazyScript,
|
JS_FOR_EACH_TRACEKIND(EXPAND_ROOT_KIND)
|
||||||
Object,
|
#undef EXPAND_ROOT_KIND
|
||||||
ObjectGroup,
|
|
||||||
Script,
|
|
||||||
Shape,
|
|
||||||
String,
|
|
||||||
Symbol,
|
|
||||||
|
|
||||||
// These tagged pointers are special-cased for performance.
|
// These tagged pointers are special-cased for performance.
|
||||||
Id,
|
Id,
|
||||||
|
|
|
@ -217,23 +217,10 @@ js::Allocate(ExclusiveContext* cx)
|
||||||
return GCRuntime::tryNewTenuredThing<T, allowGC>(cx, kind, thingSize);
|
return GCRuntime::tryNewTenuredThing<T, allowGC>(cx, kind, thingSize);
|
||||||
}
|
}
|
||||||
|
|
||||||
#define FOR_ALL_NON_OBJECT_GC_LAYOUTS(macro) \
|
#define DECL_ALLOCATOR_INSTANCES(allocKind, traceKind, type, sizedType) \
|
||||||
macro(JS::Symbol) \
|
|
||||||
macro(JSExternalString) \
|
|
||||||
macro(JSFatInlineString) \
|
|
||||||
macro(JSScript) \
|
|
||||||
macro(JSString) \
|
|
||||||
macro(js::AccessorShape) \
|
|
||||||
macro(js::BaseShape) \
|
|
||||||
macro(js::LazyScript) \
|
|
||||||
macro(js::ObjectGroup) \
|
|
||||||
macro(js::Shape) \
|
|
||||||
macro(js::jit::JitCode)
|
|
||||||
|
|
||||||
#define DECL_ALLOCATOR_INSTANCES(type) \
|
|
||||||
template type* js::Allocate<type, NoGC>(ExclusiveContext* cx);\
|
template type* js::Allocate<type, NoGC>(ExclusiveContext* cx);\
|
||||||
template type* js::Allocate<type, CanGC>(ExclusiveContext* cx);
|
template type* js::Allocate<type, CanGC>(ExclusiveContext* cx);
|
||||||
FOR_ALL_NON_OBJECT_GC_LAYOUTS(DECL_ALLOCATOR_INSTANCES)
|
FOR_EACH_NONOBJECT_ALLOCKIND(DECL_ALLOCATOR_INSTANCES)
|
||||||
#undef DECL_ALLOCATOR_INSTANCES
|
#undef DECL_ALLOCATOR_INSTANCES
|
||||||
|
|
||||||
template <typename T, AllowGC allowGC>
|
template <typename T, AllowGC allowGC>
|
||||||
|
|
116
js/src/gc/Heap.h
116
js/src/gc/Heap.h
|
@ -114,39 +114,60 @@ enum class AllocKind {
|
||||||
LAST = LIMIT - 1
|
LAST = LIMIT - 1
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Macro to enumerate the different allocation kinds supplying information about
|
||||||
|
// the trace kind, C++ type and allocation size.
|
||||||
|
#define FOR_EACH_OBJECT_ALLOCKIND(D) \
|
||||||
|
/* AllocKind TraceKind TypeName SizedType */ \
|
||||||
|
D(FUNCTION, Object, JSObject, JSFunction) \
|
||||||
|
D(FUNCTION_EXTENDED, Object, JSObject, FunctionExtended) \
|
||||||
|
D(OBJECT0, Object, JSObject, JSObject_Slots0) \
|
||||||
|
D(OBJECT0_BACKGROUND, Object, JSObject, JSObject_Slots0) \
|
||||||
|
D(OBJECT2, Object, JSObject, JSObject_Slots2) \
|
||||||
|
D(OBJECT2_BACKGROUND, Object, JSObject, JSObject_Slots2) \
|
||||||
|
D(OBJECT4, Object, JSObject, JSObject_Slots4) \
|
||||||
|
D(OBJECT4_BACKGROUND, Object, JSObject, JSObject_Slots4) \
|
||||||
|
D(OBJECT8, Object, JSObject, JSObject_Slots8) \
|
||||||
|
D(OBJECT8_BACKGROUND, Object, JSObject, JSObject_Slots8) \
|
||||||
|
D(OBJECT12, Object, JSObject, JSObject_Slots12) \
|
||||||
|
D(OBJECT12_BACKGROUND, Object, JSObject, JSObject_Slots12) \
|
||||||
|
D(OBJECT16, Object, JSObject, JSObject_Slots16) \
|
||||||
|
D(OBJECT16_BACKGROUND, Object, JSObject, JSObject_Slots16)
|
||||||
|
|
||||||
|
#define FOR_EACH_NONOBJECT_ALLOCKIND(D) \
|
||||||
|
/* AllocKind TraceKind TypeName SizedType */ \
|
||||||
|
D(SCRIPT, Script, JSScript, JSScript) \
|
||||||
|
D(LAZY_SCRIPT, LazyScript, js::LazyScript, js::LazyScript) \
|
||||||
|
D(SHAPE, Shape, js::Shape, js::Shape) \
|
||||||
|
D(ACCESSOR_SHAPE, Shape, js::AccessorShape, js::AccessorShape) \
|
||||||
|
D(BASE_SHAPE, BaseShape, js::BaseShape, js::BaseShape) \
|
||||||
|
D(OBJECT_GROUP, ObjectGroup, js::ObjectGroup, js::ObjectGroup) \
|
||||||
|
D(FAT_INLINE_STRING, String, JSFatInlineString, JSFatInlineString) \
|
||||||
|
D(STRING, String, JSString, JSString) \
|
||||||
|
D(EXTERNAL_STRING, String, JSExternalString, JSExternalString) \
|
||||||
|
D(SYMBOL, Symbol, JS::Symbol, JS::Symbol) \
|
||||||
|
D(JITCODE, JitCode, js::jit::JitCode, js::jit::JitCode)
|
||||||
|
|
||||||
#define FOR_EACH_ALLOCKIND(D) \
|
#define FOR_EACH_ALLOCKIND(D) \
|
||||||
/* PrettyName TypeName */ \
|
FOR_EACH_OBJECT_ALLOCKIND(D) \
|
||||||
D(FUNCTION, JSFunction) \
|
FOR_EACH_NONOBJECT_ALLOCKIND(D)
|
||||||
D(FUNCTION_EXTENDED, JSFunction) \
|
|
||||||
D(OBJECT0, JSObject) \
|
|
||||||
D(OBJECT0_BACKGROUND, JSObject) \
|
|
||||||
D(OBJECT2, JSObject) \
|
|
||||||
D(OBJECT2_BACKGROUND, JSObject) \
|
|
||||||
D(OBJECT4, JSObject) \
|
|
||||||
D(OBJECT4_BACKGROUND, JSObject) \
|
|
||||||
D(OBJECT8, JSObject) \
|
|
||||||
D(OBJECT8_BACKGROUND, JSObject) \
|
|
||||||
D(OBJECT12, JSObject) \
|
|
||||||
D(OBJECT12_BACKGROUND, JSObject) \
|
|
||||||
D(OBJECT16, JSObject) \
|
|
||||||
D(OBJECT16_BACKGROUND, JSObject) \
|
|
||||||
D(SCRIPT, JSScript) \
|
|
||||||
D(LAZY_SCRIPT, js::LazyScript) \
|
|
||||||
D(SHAPE, js::Shape) \
|
|
||||||
D(ACCESSOR_SHAPE, js::AccessorShape) \
|
|
||||||
D(BASE_SHAPE, js::BaseShape) \
|
|
||||||
D(OBJECT_GROUP, js::ObjectGroup) \
|
|
||||||
D(FAT_INLINE_STRING, JSFatInlineString) \
|
|
||||||
D(STRING, JSString) \
|
|
||||||
D(EXTERNAL_STRING, JSExternalString) \
|
|
||||||
D(SYMBOL, JS::Symbol) \
|
|
||||||
D(JITCODE, js::JitCode)
|
|
||||||
|
|
||||||
static_assert(int(AllocKind::FIRST) == 0, "Various places depend on AllocKind starting at 0, "
|
static_assert(int(AllocKind::FIRST) == 0, "Various places depend on AllocKind starting at 0, "
|
||||||
"please audit them carefully!");
|
"please audit them carefully!");
|
||||||
static_assert(int(AllocKind::OBJECT_FIRST) == 0, "Various places depend on AllocKind::OBJECT_FIRST "
|
static_assert(int(AllocKind::OBJECT_FIRST) == 0, "Various places depend on AllocKind::OBJECT_FIRST "
|
||||||
"being 0, please audit them carefully!");
|
"being 0, please audit them carefully!");
|
||||||
|
|
||||||
|
inline bool
|
||||||
|
IsAllocKind(AllocKind kind)
|
||||||
|
{
|
||||||
|
return kind >= AllocKind::FIRST && kind <= AllocKind::LIMIT;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool
|
||||||
|
IsValidAllocKind(AllocKind kind)
|
||||||
|
{
|
||||||
|
return kind >= AllocKind::FIRST && kind <= AllocKind::LAST;
|
||||||
|
}
|
||||||
|
|
||||||
inline bool
|
inline bool
|
||||||
IsObjectAllocKind(AllocKind kind)
|
IsObjectAllocKind(AllocKind kind)
|
||||||
{
|
{
|
||||||
|
@ -159,17 +180,6 @@ IsShapeAllocKind(AllocKind kind)
|
||||||
return kind == AllocKind::SHAPE || kind == AllocKind::ACCESSOR_SHAPE;
|
return kind == AllocKind::SHAPE || kind == AllocKind::ACCESSOR_SHAPE;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline bool
|
|
||||||
IsValidAllocKind(AllocKind kind)
|
|
||||||
{
|
|
||||||
return kind >= AllocKind::FIRST && kind <= AllocKind::LAST;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool IsAllocKind(AllocKind kind)
|
|
||||||
{
|
|
||||||
return kind >= AllocKind::FIRST && kind <= AllocKind::LIMIT;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns a sequence for use in a range-based for loop,
|
// Returns a sequence for use in a range-based for loop,
|
||||||
// to iterate over all alloc kinds.
|
// to iterate over all alloc kinds.
|
||||||
inline decltype(mozilla::MakeEnumeratedRange<int>(AllocKind::FIRST, AllocKind::LIMIT))
|
inline decltype(mozilla::MakeEnumeratedRange<int>(AllocKind::FIRST, AllocKind::LIMIT))
|
||||||
|
@ -210,31 +220,10 @@ static inline JS::TraceKind
|
||||||
MapAllocToTraceKind(AllocKind kind)
|
MapAllocToTraceKind(AllocKind kind)
|
||||||
{
|
{
|
||||||
static const JS::TraceKind map[] = {
|
static const JS::TraceKind map[] = {
|
||||||
JS::TraceKind::Object, /* AllocKind::FUNCTION */
|
#define EXPAND_ELEMENT(allocKind, traceKind, type, sizedType) \
|
||||||
JS::TraceKind::Object, /* AllocKind::FUNCTION_EXTENDED */
|
JS::TraceKind::traceKind,
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT0 */
|
FOR_EACH_ALLOCKIND(EXPAND_ELEMENT)
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT0_BACKGROUND */
|
#undef EXPAND_ELEMENT
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT2 */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT2_BACKGROUND */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT4 */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT4_BACKGROUND */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT8 */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT8_BACKGROUND */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT12 */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT12_BACKGROUND */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT16 */
|
|
||||||
JS::TraceKind::Object, /* AllocKind::OBJECT16_BACKGROUND */
|
|
||||||
JS::TraceKind::Script, /* AllocKind::SCRIPT */
|
|
||||||
JS::TraceKind::LazyScript, /* AllocKind::LAZY_SCRIPT */
|
|
||||||
JS::TraceKind::Shape, /* AllocKind::SHAPE */
|
|
||||||
JS::TraceKind::Shape, /* AllocKind::ACCESSOR_SHAPE */
|
|
||||||
JS::TraceKind::BaseShape, /* AllocKind::BASE_SHAPE */
|
|
||||||
JS::TraceKind::ObjectGroup, /* AllocKind::OBJECT_GROUP */
|
|
||||||
JS::TraceKind::String, /* AllocKind::FAT_INLINE_STRING */
|
|
||||||
JS::TraceKind::String, /* AllocKind::STRING */
|
|
||||||
JS::TraceKind::String, /* AllocKind::EXTERNAL_STRING */
|
|
||||||
JS::TraceKind::Symbol, /* AllocKind::SYMBOL */
|
|
||||||
JS::TraceKind::JitCode, /* AllocKind::JITCODE */
|
|
||||||
};
|
};
|
||||||
|
|
||||||
static_assert(MOZ_ARRAY_LENGTH(map) == size_t(AllocKind::LIMIT),
|
static_assert(MOZ_ARRAY_LENGTH(map) == size_t(AllocKind::LIMIT),
|
||||||
|
@ -326,6 +315,9 @@ class TenuredCell : public Cell
|
||||||
static MOZ_ALWAYS_INLINE void writeBarrierPost(void* cellp, TenuredCell* prior,
|
static MOZ_ALWAYS_INLINE void writeBarrierPost(void* cellp, TenuredCell* prior,
|
||||||
TenuredCell* next);
|
TenuredCell* next);
|
||||||
|
|
||||||
|
// Default implementation for kinds that don't require fixup.
|
||||||
|
void fixupAfterMovingGC() {}
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
inline bool isAligned() const;
|
inline bool isAligned() const;
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -350,6 +350,9 @@ AssertRootMarkingPhase(JSTracer* trc)
|
||||||
// statically select the correct Cell layout for marking. Below, we instantiate
|
// statically select the correct Cell layout for marking. Below, we instantiate
|
||||||
// each override with a declaration of the most derived layout type.
|
// each override with a declaration of the most derived layout type.
|
||||||
//
|
//
|
||||||
|
// The use of TraceKind::Null for the case where the type is not matched
|
||||||
|
// generates a compile error as no template instantiated for that kind.
|
||||||
|
//
|
||||||
// Usage:
|
// Usage:
|
||||||
// BaseGCType<T>::type
|
// BaseGCType<T>::type
|
||||||
//
|
//
|
||||||
|
@ -357,16 +360,13 @@ AssertRootMarkingPhase(JSTracer* trc)
|
||||||
// BaseGCType<JSFunction>::type => JSObject
|
// BaseGCType<JSFunction>::type => JSObject
|
||||||
// BaseGCType<UnownedBaseShape>::type => BaseShape
|
// BaseGCType<UnownedBaseShape>::type => BaseShape
|
||||||
// etc.
|
// etc.
|
||||||
template <typename T,
|
template <typename T, JS::TraceKind =
|
||||||
JS::TraceKind = IsBaseOf<JSObject, T>::value ? JS::TraceKind::Object
|
#define EXPAND_MATCH_TYPE(name, type, _) \
|
||||||
: IsBaseOf<JSString, T>::value ? JS::TraceKind::String
|
IsBaseOf<type, T>::value ? JS::TraceKind::name :
|
||||||
: IsBaseOf<JS::Symbol, T>::value ? JS::TraceKind::Symbol
|
JS_FOR_EACH_TRACEKIND(EXPAND_MATCH_TYPE)
|
||||||
: IsBaseOf<JSScript, T>::value ? JS::TraceKind::Script
|
#undef EXPAND_MATCH_TYPE
|
||||||
: IsBaseOf<Shape, T>::value ? JS::TraceKind::Shape
|
JS::TraceKind::Null>
|
||||||
: IsBaseOf<BaseShape, T>::value ? JS::TraceKind::BaseShape
|
|
||||||
: IsBaseOf<jit::JitCode, T>::value ? JS::TraceKind::JitCode
|
|
||||||
: IsBaseOf<LazyScript, T>::value ? JS::TraceKind::LazyScript
|
|
||||||
: JS::TraceKind::ObjectGroup>
|
|
||||||
struct BaseGCType;
|
struct BaseGCType;
|
||||||
#define IMPL_BASE_GC_TYPE(name, type_, _) \
|
#define IMPL_BASE_GC_TYPE(name, type_, _) \
|
||||||
template <typename T> struct BaseGCType<T, JS::TraceKind:: name> { typedef type_ type; };
|
template <typename T> struct BaseGCType<T, JS::TraceKind:: name> { typedef type_ type; };
|
||||||
|
|
|
@ -114,7 +114,6 @@ class JitCode : public gc::TenuredCell
|
||||||
|
|
||||||
void traceChildren(JSTracer* trc);
|
void traceChildren(JSTracer* trc);
|
||||||
void finalize(FreeOp* fop);
|
void finalize(FreeOp* fop);
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
void setInvalidated() {
|
void setInvalidated() {
|
||||||
invalidated_ = true;
|
invalidated_ = true;
|
||||||
}
|
}
|
||||||
|
|
217
js/src/jsgc.cpp
217
js/src/jsgc.cpp
|
@ -261,52 +261,22 @@ const AllocKind gc::slotsToThingKind[] = {
|
||||||
static_assert(JS_ARRAY_LENGTH(slotsToThingKind) == SLOTS_TO_THING_KIND_LIMIT,
|
static_assert(JS_ARRAY_LENGTH(slotsToThingKind) == SLOTS_TO_THING_KIND_LIMIT,
|
||||||
"We have defined a slot count for each kind.");
|
"We have defined a slot count for each kind.");
|
||||||
|
|
||||||
// Assert that SortedArenaList::MinThingSize and sizeof(FreeSpan) are <= the
|
#define CHECK_THING_SIZE(allocKind, traceKind, type, sizedType) \
|
||||||
// real minimum thing size. Also assert each size is a multiple of CellSize.
|
static_assert(sizeof(sizedType) >= SortedArenaList::MinThingSize, \
|
||||||
#define CHECK_THING_SIZE_INNER(x_) \
|
#sizedType " is smaller than SortedArenaList::MinThingSize!"); \
|
||||||
static_assert(x_ >= SortedArenaList::MinThingSize, \
|
static_assert(sizeof(sizedType) >= sizeof(FreeSpan), \
|
||||||
#x_ " is less than SortedArenaList::MinThingSize!"); \
|
#sizedType " is smaller than FreeSpan"); \
|
||||||
static_assert(x_ >= sizeof(FreeSpan), \
|
static_assert(sizeof(sizedType) % CellSize == 0, \
|
||||||
#x_ " is less than sizeof(FreeSpan)"); \
|
"Size of " #sizedType " is not a multiple of CellSize");
|
||||||
static_assert(x_ % CellSize == 0, \
|
FOR_EACH_ALLOCKIND(CHECK_THING_SIZE);
|
||||||
#x_ " not a multiple of CellSize");
|
#undef CHECK_THING_SIZE
|
||||||
|
|
||||||
#define CHECK_THING_SIZE(...) { __VA_ARGS__ }; /* Define the array. */ \
|
const uint32_t Arena::ThingSizes[] = {
|
||||||
MOZ_FOR_EACH(CHECK_THING_SIZE_INNER, (), (__VA_ARGS__ 0x20))
|
#define EXPAND_THING_SIZE(allocKind, traceKind, type, sizedType) \
|
||||||
|
sizeof(sizedType),
|
||||||
#define CHECK_ZEAL(name, value) \
|
FOR_EACH_ALLOCKIND(EXPAND_THING_SIZE)
|
||||||
static_assert(ZealMode::Limit >= ZealMode::name, \
|
#undef EXPAND_THING_SIZE
|
||||||
"ZealMode::Limit shouldn't be smaller than " #name);
|
};
|
||||||
JS_FOR_EACH_ZEAL_MODE(CHECK_ZEAL)
|
|
||||||
#undef CHECK_ZEAL
|
|
||||||
|
|
||||||
const uint32_t Arena::ThingSizes[] = CHECK_THING_SIZE(
|
|
||||||
sizeof(JSFunction), /* AllocKind::FUNCTION */
|
|
||||||
sizeof(FunctionExtended), /* AllocKind::FUNCTION_EXTENDED */
|
|
||||||
sizeof(JSObject_Slots0), /* AllocKind::OBJECT0 */
|
|
||||||
sizeof(JSObject_Slots0), /* AllocKind::OBJECT0_BACKGROUND */
|
|
||||||
sizeof(JSObject_Slots2), /* AllocKind::OBJECT2 */
|
|
||||||
sizeof(JSObject_Slots2), /* AllocKind::OBJECT2_BACKGROUND */
|
|
||||||
sizeof(JSObject_Slots4), /* AllocKind::OBJECT4 */
|
|
||||||
sizeof(JSObject_Slots4), /* AllocKind::OBJECT4_BACKGROUND */
|
|
||||||
sizeof(JSObject_Slots8), /* AllocKind::OBJECT8 */
|
|
||||||
sizeof(JSObject_Slots8), /* AllocKind::OBJECT8_BACKGROUND */
|
|
||||||
sizeof(JSObject_Slots12), /* AllocKind::OBJECT12 */
|
|
||||||
sizeof(JSObject_Slots12), /* AllocKind::OBJECT12_BACKGROUND */
|
|
||||||
sizeof(JSObject_Slots16), /* AllocKind::OBJECT16 */
|
|
||||||
sizeof(JSObject_Slots16), /* AllocKind::OBJECT16_BACKGROUND */
|
|
||||||
sizeof(JSScript), /* AllocKind::SCRIPT */
|
|
||||||
sizeof(LazyScript), /* AllocKind::LAZY_SCRIPT */
|
|
||||||
sizeof(Shape), /* AllocKind::SHAPE */
|
|
||||||
sizeof(AccessorShape), /* AllocKind::ACCESSOR_SHAPE */
|
|
||||||
sizeof(BaseShape), /* AllocKind::BASE_SHAPE */
|
|
||||||
sizeof(ObjectGroup), /* AllocKind::OBJECT_GROUP */
|
|
||||||
sizeof(JSFatInlineString), /* AllocKind::FAT_INLINE_STRING */
|
|
||||||
sizeof(JSString), /* AllocKind::STRING */
|
|
||||||
sizeof(JSExternalString), /* AllocKind::EXTERNAL_STRING */
|
|
||||||
sizeof(JS::Symbol), /* AllocKind::SYMBOL */
|
|
||||||
sizeof(jit::JitCode), /* AllocKind::JITCODE */
|
|
||||||
);
|
|
||||||
|
|
||||||
FreeSpan ArenaLists::placeholder;
|
FreeSpan ArenaLists::placeholder;
|
||||||
|
|
||||||
|
@ -316,31 +286,10 @@ FreeSpan ArenaLists::placeholder;
|
||||||
#define OFFSET(type) uint32_t(ArenaHeaderSize + (ArenaSize - ArenaHeaderSize) % sizeof(type))
|
#define OFFSET(type) uint32_t(ArenaHeaderSize + (ArenaSize - ArenaHeaderSize) % sizeof(type))
|
||||||
|
|
||||||
const uint32_t Arena::FirstThingOffsets[] = {
|
const uint32_t Arena::FirstThingOffsets[] = {
|
||||||
OFFSET(JSFunction), /* AllocKind::FUNCTION */
|
#define EXPAND_FIRST_THING_OFFSET(allocKind, traceKind, type, sizedType) \
|
||||||
OFFSET(FunctionExtended), /* AllocKind::FUNCTION_EXTENDED */
|
OFFSET(sizedType),
|
||||||
OFFSET(JSObject_Slots0), /* AllocKind::OBJECT0 */
|
FOR_EACH_ALLOCKIND(EXPAND_FIRST_THING_OFFSET)
|
||||||
OFFSET(JSObject_Slots0), /* AllocKind::OBJECT0_BACKGROUND */
|
#undef EXPAND_FIRST_THING_OFFSET
|
||||||
OFFSET(JSObject_Slots2), /* AllocKind::OBJECT2 */
|
|
||||||
OFFSET(JSObject_Slots2), /* AllocKind::OBJECT2_BACKGROUND */
|
|
||||||
OFFSET(JSObject_Slots4), /* AllocKind::OBJECT4 */
|
|
||||||
OFFSET(JSObject_Slots4), /* AllocKind::OBJECT4_BACKGROUND */
|
|
||||||
OFFSET(JSObject_Slots8), /* AllocKind::OBJECT8 */
|
|
||||||
OFFSET(JSObject_Slots8), /* AllocKind::OBJECT8_BACKGROUND */
|
|
||||||
OFFSET(JSObject_Slots12), /* AllocKind::OBJECT12 */
|
|
||||||
OFFSET(JSObject_Slots12), /* AllocKind::OBJECT12_BACKGROUND */
|
|
||||||
OFFSET(JSObject_Slots16), /* AllocKind::OBJECT16 */
|
|
||||||
OFFSET(JSObject_Slots16), /* AllocKind::OBJECT16_BACKGROUND */
|
|
||||||
OFFSET(JSScript), /* AllocKind::SCRIPT */
|
|
||||||
OFFSET(LazyScript), /* AllocKind::LAZY_SCRIPT */
|
|
||||||
OFFSET(Shape), /* AllocKind::SHAPE */
|
|
||||||
OFFSET(AccessorShape), /* AllocKind::ACCESSOR_SHAPE */
|
|
||||||
OFFSET(BaseShape), /* AllocKind::BASE_SHAPE */
|
|
||||||
OFFSET(ObjectGroup), /* AllocKind::OBJECT_GROUP */
|
|
||||||
OFFSET(JSFatInlineString), /* AllocKind::FAT_INLINE_STRING */
|
|
||||||
OFFSET(JSString), /* AllocKind::STRING */
|
|
||||||
OFFSET(JSExternalString), /* AllocKind::EXTERNAL_STRING */
|
|
||||||
OFFSET(JS::Symbol), /* AllocKind::SYMBOL */
|
|
||||||
OFFSET(jit::JitCode), /* AllocKind::JITCODE */
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#undef OFFSET
|
#undef OFFSET
|
||||||
|
@ -348,31 +297,10 @@ const uint32_t Arena::FirstThingOffsets[] = {
|
||||||
#define COUNT(type) uint32_t((ArenaSize - ArenaHeaderSize) / sizeof(type))
|
#define COUNT(type) uint32_t((ArenaSize - ArenaHeaderSize) / sizeof(type))
|
||||||
|
|
||||||
const uint32_t Arena::ThingsPerArena[] = {
|
const uint32_t Arena::ThingsPerArena[] = {
|
||||||
COUNT(JSFunction), /* AllocKind::FUNCTION */
|
#define EXPAND_THINGS_PER_ARENA(allocKind, traceKind, type, sizedType) \
|
||||||
COUNT(FunctionExtended), /* AllocKind::FUNCTION_EXTENDED */
|
COUNT(sizedType),
|
||||||
COUNT(JSObject_Slots0), /* AllocKind::OBJECT0 */
|
FOR_EACH_ALLOCKIND(EXPAND_THINGS_PER_ARENA)
|
||||||
COUNT(JSObject_Slots0), /* AllocKind::OBJECT0_BACKGROUND */
|
#undef EXPAND_THINGS_PER_ARENA
|
||||||
COUNT(JSObject_Slots2), /* AllocKind::OBJECT2 */
|
|
||||||
COUNT(JSObject_Slots2), /* AllocKind::OBJECT2_BACKGROUND */
|
|
||||||
COUNT(JSObject_Slots4), /* AllocKind::OBJECT4 */
|
|
||||||
COUNT(JSObject_Slots4), /* AllocKind::OBJECT4_BACKGROUND */
|
|
||||||
COUNT(JSObject_Slots8), /* AllocKind::OBJECT8 */
|
|
||||||
COUNT(JSObject_Slots8), /* AllocKind::OBJECT8_BACKGROUND */
|
|
||||||
COUNT(JSObject_Slots12), /* AllocKind::OBJECT12 */
|
|
||||||
COUNT(JSObject_Slots12), /* AllocKind::OBJECT12_BACKGROUND */
|
|
||||||
COUNT(JSObject_Slots16), /* AllocKind::OBJECT16 */
|
|
||||||
COUNT(JSObject_Slots16), /* AllocKind::OBJECT16_BACKGROUND */
|
|
||||||
COUNT(JSScript), /* AllocKind::SCRIPT */
|
|
||||||
COUNT(LazyScript), /* AllocKind::LAZY_SCRIPT */
|
|
||||||
COUNT(Shape), /* AllocKind::SHAPE */
|
|
||||||
COUNT(AccessorShape), /* AllocKind::ACCESSOR_SHAPE */
|
|
||||||
COUNT(BaseShape), /* AllocKind::BASE_SHAPE */
|
|
||||||
COUNT(ObjectGroup), /* AllocKind::OBJECT_GROUP */
|
|
||||||
COUNT(JSFatInlineString), /* AllocKind::FAT_INLINE_STRING */
|
|
||||||
COUNT(JSString), /* AllocKind::STRING */
|
|
||||||
COUNT(JSExternalString), /* AllocKind::EXTERNAL_STRING */
|
|
||||||
COUNT(JS::Symbol), /* AllocKind::SYMBOL */
|
|
||||||
COUNT(jit::JitCode), /* AllocKind::JITCODE */
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#undef COUNT
|
#undef COUNT
|
||||||
|
@ -604,43 +532,12 @@ FinalizeArenas(FreeOp* fop,
|
||||||
ArenaLists::KeepArenasEnum keepArenas)
|
ArenaLists::KeepArenasEnum keepArenas)
|
||||||
{
|
{
|
||||||
switch (thingKind) {
|
switch (thingKind) {
|
||||||
case AllocKind::FUNCTION:
|
#define EXPAND_CASE(allocKind, traceKind, type, sizedType) \
|
||||||
case AllocKind::FUNCTION_EXTENDED:
|
case AllocKind::allocKind: \
|
||||||
case AllocKind::OBJECT0:
|
return FinalizeTypedArenas<type>(fop, src, dest, thingKind, budget, keepArenas);
|
||||||
case AllocKind::OBJECT0_BACKGROUND:
|
FOR_EACH_ALLOCKIND(EXPAND_CASE)
|
||||||
case AllocKind::OBJECT2:
|
#undef EXPAND_CASE
|
||||||
case AllocKind::OBJECT2_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT4:
|
|
||||||
case AllocKind::OBJECT4_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT8:
|
|
||||||
case AllocKind::OBJECT8_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT12:
|
|
||||||
case AllocKind::OBJECT12_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT16:
|
|
||||||
case AllocKind::OBJECT16_BACKGROUND:
|
|
||||||
return FinalizeTypedArenas<JSObject>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::SCRIPT:
|
|
||||||
return FinalizeTypedArenas<JSScript>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::LAZY_SCRIPT:
|
|
||||||
return FinalizeTypedArenas<LazyScript>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::SHAPE:
|
|
||||||
return FinalizeTypedArenas<Shape>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::ACCESSOR_SHAPE:
|
|
||||||
return FinalizeTypedArenas<AccessorShape>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::BASE_SHAPE:
|
|
||||||
return FinalizeTypedArenas<BaseShape>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::OBJECT_GROUP:
|
|
||||||
return FinalizeTypedArenas<ObjectGroup>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::STRING:
|
|
||||||
return FinalizeTypedArenas<JSString>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::FAT_INLINE_STRING:
|
|
||||||
return FinalizeTypedArenas<JSFatInlineString>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::EXTERNAL_STRING:
|
|
||||||
return FinalizeTypedArenas<JSExternalString>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::SYMBOL:
|
|
||||||
return FinalizeTypedArenas<JS::Symbol>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
case AllocKind::JITCODE:
|
|
||||||
return FinalizeTypedArenas<jit::JitCode>(fop, src, dest, thingKind, budget, keepArenas);
|
|
||||||
default:
|
default:
|
||||||
MOZ_CRASH("Invalid alloc kind");
|
MOZ_CRASH("Invalid alloc kind");
|
||||||
}
|
}
|
||||||
|
@ -2543,49 +2440,15 @@ static void
|
||||||
UpdateArenaPointers(MovingTracer* trc, Arena* arena)
|
UpdateArenaPointers(MovingTracer* trc, Arena* arena)
|
||||||
{
|
{
|
||||||
AllocKind kind = arena->getAllocKind();
|
AllocKind kind = arena->getAllocKind();
|
||||||
JS::TraceKind traceKind = MapAllocToTraceKind(kind);
|
|
||||||
|
|
||||||
switch (kind) {
|
switch (kind) {
|
||||||
case AllocKind::FUNCTION:
|
#define EXPAND_CASE(allocKind, traceKind, type, sizedType) \
|
||||||
case AllocKind::FUNCTION_EXTENDED:
|
case AllocKind::allocKind: \
|
||||||
case AllocKind::OBJECT0:
|
UpdateArenaPointersTyped<type>(trc, arena, JS::TraceKind::traceKind); \
|
||||||
case AllocKind::OBJECT0_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT2:
|
|
||||||
case AllocKind::OBJECT2_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT4:
|
|
||||||
case AllocKind::OBJECT4_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT8:
|
|
||||||
case AllocKind::OBJECT8_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT12:
|
|
||||||
case AllocKind::OBJECT12_BACKGROUND:
|
|
||||||
case AllocKind::OBJECT16:
|
|
||||||
case AllocKind::OBJECT16_BACKGROUND:
|
|
||||||
UpdateArenaPointersTyped<JSObject>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::SCRIPT:
|
|
||||||
UpdateArenaPointersTyped<JSScript>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::LAZY_SCRIPT:
|
|
||||||
UpdateArenaPointersTyped<LazyScript>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::SHAPE:
|
|
||||||
UpdateArenaPointersTyped<Shape>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::ACCESSOR_SHAPE:
|
|
||||||
UpdateArenaPointersTyped<AccessorShape>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::BASE_SHAPE:
|
|
||||||
UpdateArenaPointersTyped<BaseShape>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::OBJECT_GROUP:
|
|
||||||
UpdateArenaPointersTyped<ObjectGroup>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::STRING:
|
|
||||||
UpdateArenaPointersTyped<JSString>(trc, arena, traceKind);
|
|
||||||
return;
|
|
||||||
case AllocKind::JITCODE:
|
|
||||||
UpdateArenaPointersTyped<jit::JitCode>(trc, arena, traceKind);
|
|
||||||
return;
|
return;
|
||||||
|
FOR_EACH_ALLOCKIND(EXPAND_CASE)
|
||||||
|
#undef EXPAND_CASE
|
||||||
|
|
||||||
default:
|
default:
|
||||||
MOZ_CRASH("Invalid alloc kind for UpdateArenaPointers");
|
MOZ_CRASH("Invalid alloc kind for UpdateArenaPointers");
|
||||||
}
|
}
|
||||||
|
@ -3961,11 +3824,13 @@ static const char*
|
||||||
AllocKindToAscii(AllocKind kind)
|
AllocKindToAscii(AllocKind kind)
|
||||||
{
|
{
|
||||||
switch(kind) {
|
switch(kind) {
|
||||||
#define MAKE_CASE(name, _) case AllocKind:: name: return #name;
|
#define MAKE_CASE(allocKind, traceKind, type, sizedType) \
|
||||||
FOR_EACH_ALLOCKIND(MAKE_CASE)
|
case AllocKind:: allocKind: return #allocKind;
|
||||||
|
FOR_EACH_ALLOCKIND(MAKE_CASE)
|
||||||
#undef MAKE_CASE
|
#undef MAKE_CASE
|
||||||
case AllocKind::LIMIT: MOZ_FALLTHROUGH;
|
|
||||||
default: MOZ_CRASH("Unknown AllocKind in AllocKindToAscii");
|
default:
|
||||||
|
MOZ_CRASH("Unknown AllocKind in AllocKindToAscii");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif // DEBUG
|
#endif // DEBUG
|
||||||
|
|
|
@ -53,19 +53,19 @@ enum State {
|
||||||
NUM_STATES
|
NUM_STATES
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Map from C++ type to alloc kind. JSObject does not have a 1:1 mapping, so must use Arena::thingSize. */
|
/*
|
||||||
|
* Map from C++ type to alloc kind for non-object types. JSObject does not have
|
||||||
|
* a 1:1 mapping, so must use Arena::thingSize.
|
||||||
|
*
|
||||||
|
* The AllocKind is available as MapTypeToFinalizeKind<SomeType>::kind.
|
||||||
|
*/
|
||||||
template <typename T> struct MapTypeToFinalizeKind {};
|
template <typename T> struct MapTypeToFinalizeKind {};
|
||||||
template <> struct MapTypeToFinalizeKind<JSScript> { static const AllocKind kind = AllocKind::SCRIPT; };
|
#define EXPAND_MAPTYPETOFINALIZEKIND(allocKind, traceKind, type, sizedType) \
|
||||||
template <> struct MapTypeToFinalizeKind<LazyScript> { static const AllocKind kind = AllocKind::LAZY_SCRIPT; };
|
template <> struct MapTypeToFinalizeKind<type> { \
|
||||||
template <> struct MapTypeToFinalizeKind<Shape> { static const AllocKind kind = AllocKind::SHAPE; };
|
static const AllocKind kind = AllocKind::allocKind; \
|
||||||
template <> struct MapTypeToFinalizeKind<AccessorShape> { static const AllocKind kind = AllocKind::ACCESSOR_SHAPE; };
|
};
|
||||||
template <> struct MapTypeToFinalizeKind<BaseShape> { static const AllocKind kind = AllocKind::BASE_SHAPE; };
|
FOR_EACH_NONOBJECT_ALLOCKIND(EXPAND_MAPTYPETOFINALIZEKIND)
|
||||||
template <> struct MapTypeToFinalizeKind<ObjectGroup> { static const AllocKind kind = AllocKind::OBJECT_GROUP; };
|
#undef EXPAND_MAPTYPETOFINALIZEKIND
|
||||||
template <> struct MapTypeToFinalizeKind<JSFatInlineString> { static const AllocKind kind = AllocKind::FAT_INLINE_STRING; };
|
|
||||||
template <> struct MapTypeToFinalizeKind<JSString> { static const AllocKind kind = AllocKind::STRING; };
|
|
||||||
template <> struct MapTypeToFinalizeKind<JSExternalString> { static const AllocKind kind = AllocKind::EXTERNAL_STRING; };
|
|
||||||
template <> struct MapTypeToFinalizeKind<JS::Symbol> { static const AllocKind kind = AllocKind::SYMBOL; };
|
|
||||||
template <> struct MapTypeToFinalizeKind<jit::JitCode> { static const AllocKind kind = AllocKind::JITCODE; };
|
|
||||||
|
|
||||||
template <typename T> struct ParticipatesInCC {};
|
template <typename T> struct ParticipatesInCC {};
|
||||||
#define EXPAND_PARTICIPATES_IN_CC(_, type, addToCCKind) \
|
#define EXPAND_PARTICIPATES_IN_CC(_, type, addToCCKind) \
|
||||||
|
|
|
@ -1942,7 +1942,6 @@ class JSScript : public js::gc::TenuredCell
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void finalize(js::FreeOp* fop);
|
void finalize(js::FreeOp* fop);
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
|
|
||||||
static const JS::TraceKind TraceKind = JS::TraceKind::Script;
|
static const JS::TraceKind TraceKind = JS::TraceKind::Script;
|
||||||
|
|
||||||
|
@ -2397,7 +2396,6 @@ class LazyScript : public gc::TenuredCell
|
||||||
friend class GCMarker;
|
friend class GCMarker;
|
||||||
void traceChildren(JSTracer* trc);
|
void traceChildren(JSTracer* trc);
|
||||||
void finalize(js::FreeOp* fop);
|
void finalize(js::FreeOp* fop);
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
|
|
||||||
static const JS::TraceKind TraceKind = JS::TraceKind::LazyScript;
|
static const JS::TraceKind TraceKind = JS::TraceKind::LazyScript;
|
||||||
|
|
||||||
|
|
|
@ -424,7 +424,6 @@ class ObjectGroup : public gc::TenuredCell
|
||||||
size_t sizeOfExcludingThis(mozilla::MallocSizeOf mallocSizeOf) const;
|
size_t sizeOfExcludingThis(mozilla::MallocSizeOf mallocSizeOf) const;
|
||||||
|
|
||||||
void finalize(FreeOp* fop);
|
void finalize(FreeOp* fop);
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
|
|
||||||
static const JS::TraceKind TraceKind = JS::TraceKind::ObjectGroup;
|
static const JS::TraceKind TraceKind = JS::TraceKind::ObjectGroup;
|
||||||
|
|
||||||
|
|
|
@ -454,8 +454,6 @@ class BaseShape : public gc::TenuredCell
|
||||||
void traceChildren(JSTracer* trc);
|
void traceChildren(JSTracer* trc);
|
||||||
void traceChildrenSkipShapeTable(JSTracer* trc);
|
void traceChildrenSkipShapeTable(JSTracer* trc);
|
||||||
|
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
static void staticAsserts() {
|
static void staticAsserts() {
|
||||||
JS_STATIC_ASSERT(offsetof(BaseShape, clasp_) == offsetof(js::shadow::BaseShape, clasp_));
|
JS_STATIC_ASSERT(offsetof(BaseShape, clasp_) == offsetof(js::shadow::BaseShape, clasp_));
|
||||||
|
|
|
@ -474,8 +474,6 @@ class JSString : public js::gc::TenuredCell
|
||||||
|
|
||||||
inline void finalize(js::FreeOp* fop);
|
inline void finalize(js::FreeOp* fop);
|
||||||
|
|
||||||
void fixupAfterMovingGC() {}
|
|
||||||
|
|
||||||
/* Gets the number of bytes that the chars take on the heap. */
|
/* Gets the number of bytes that the chars take on the heap. */
|
||||||
|
|
||||||
size_t sizeOfExcludingThis(mozilla::MallocSizeOf mallocSizeOf);
|
size_t sizeOfExcludingThis(mozilla::MallocSizeOf mallocSizeOf);
|
||||||
|
|
Загрузка…
Ссылка в новой задаче