Commit 67f99ee1 authored by hpayer's avatar hpayer Committed by Commit bot

[heap] Black is encoded with 11, grey with 10.

This CL changes the color for encoding black and grey. Moreover, it introduces a higher level live object iterator.

BUG=chromium:561449
LOG=n

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

Cr-Commit-Position: refs/heads/master@{#33208}
parent fbbb9cab
......@@ -3248,8 +3248,8 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch0,
Register scratch1,
Label* on_black) {
HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -3304,8 +3304,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -4189,8 +4189,8 @@ void MacroAssembler::HasColor(Register object,
// These bit sequences are backwards. The first character in the string
// represents the least significant bit.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
// Check for the color.
if (first_bit == 0) {
......@@ -4218,8 +4218,8 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch0,
Register scratch1,
Label* on_black) {
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 1); // kBlackBitPattern.
}
......@@ -4265,8 +4265,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// These bit sequences are backwards. The first character in the string
// represents the least significant bit.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
GetMarkBits(value, bitmap_scratch, shift_scratch);
Ldr(load_scratch, MemOperand(bitmap_scratch, MemoryChunk::kHeaderSize));
......
......@@ -140,6 +140,55 @@ void CodeFlusher::ClearNextCandidate(SharedFunctionInfo* candidate) {
candidate->code()->set_gc_metadata(NULL, SKIP_WRITE_BARRIER);
}
template <LiveObjectIterationMode T>
HeapObject* LiveObjectIterator<T>::Next() {
while (!it_.Done()) {
HeapObject* object = nullptr;
while (current_cell_ != 0) {
uint32_t trailing_zeros = base::bits::CountTrailingZeros32(current_cell_);
Address addr = cell_base_ + trailing_zeros * kPointerSize;
// Clear the first bit of the found object..
current_cell_ &= ~(1u << trailing_zeros);
uint32_t second_bit_index = 0;
if (trailing_zeros < Bitmap::kBitIndexMask) {
second_bit_index = 1u << (trailing_zeros + 1);
} else {
second_bit_index = 0x1;
// The overlapping case; there has to exist a cell after the current
// cell.
DCHECK(!it_.Done());
it_.Advance();
cell_base_ = it_.CurrentCellBase();
current_cell_ = *it_.CurrentCell();
}
if (T == kBlackObjects && (current_cell_ & second_bit_index)) {
object = HeapObject::FromAddress(addr);
} else if (T == kGreyObjects && !(current_cell_ & second_bit_index)) {
object = HeapObject::FromAddress(addr);
} else if (T == kAllLiveObjects) {
object = HeapObject::FromAddress(addr);
}
// Clear the second bit of the found object.
current_cell_ &= ~second_bit_index;
// We found a live object.
if (object != nullptr) break;
}
if (current_cell_ == 0) {
if (!it_.Done()) {
it_.Advance();
cell_base_ = it_.CurrentCellBase();
current_cell_ = *it_.CurrentCell();
}
}
if (object != nullptr) return object;
}
return nullptr;
}
} // namespace internal
} // namespace v8
......
This diff is collapsed.
......@@ -45,10 +45,10 @@ class Marking : public AllStatic {
return !mark_bit.Get() && mark_bit.Next().Get();
}
// Black markbits: 10 - this is required by the sweeper.
// Black markbits: 11
static const char* kBlackBitPattern;
INLINE(static bool IsBlack(MarkBit mark_bit)) {
return mark_bit.Get() && !mark_bit.Next().Get();
return mark_bit.Get() && mark_bit.Next().Get();
}
// White markbits: 00 - this is required by the mark bit clearer.
......@@ -58,10 +58,10 @@ class Marking : public AllStatic {
return !mark_bit.Get();
}
// Grey markbits: 11
// Grey markbits: 10
static const char* kGreyBitPattern;
INLINE(static bool IsGrey(MarkBit mark_bit)) {
return mark_bit.Get() && mark_bit.Next().Get();
return mark_bit.Get() && !mark_bit.Next().Get();
}
// IsBlackOrGrey assumes that the first bit is set for black or grey
......@@ -70,7 +70,7 @@ class Marking : public AllStatic {
INLINE(static void MarkBlack(MarkBit mark_bit)) {
mark_bit.Set();
mark_bit.Next().Clear();
mark_bit.Next().Set();
}
INLINE(static void MarkWhite(MarkBit mark_bit)) {
......@@ -81,6 +81,7 @@ class Marking : public AllStatic {
INLINE(static void BlackToWhite(MarkBit markbit)) {
DCHECK(IsBlack(markbit));
markbit.Clear();
markbit.Next().Clear();
}
INLINE(static void GreyToWhite(MarkBit markbit)) {
......@@ -91,23 +92,23 @@ class Marking : public AllStatic {
INLINE(static void BlackToGrey(MarkBit markbit)) {
DCHECK(IsBlack(markbit));
markbit.Next().Set();
markbit.Next().Clear();
}
INLINE(static void WhiteToGrey(MarkBit markbit)) {
DCHECK(IsWhite(markbit));
markbit.Set();
markbit.Next().Set();
}
INLINE(static void WhiteToBlack(MarkBit markbit)) {
DCHECK(IsWhite(markbit));
markbit.Set();
markbit.Next().Set();
}
INLINE(static void GreyToBlack(MarkBit markbit)) {
DCHECK(IsGrey(markbit));
markbit.Next().Clear();
markbit.Next().Set();
}
INLINE(static void BlackToGrey(HeapObject* obj)) {
......@@ -116,7 +117,7 @@ class Marking : public AllStatic {
INLINE(static void AnyToGrey(MarkBit markbit)) {
markbit.Set();
markbit.Next().Set();
markbit.Next().Clear();
}
static void TransferMark(Heap* heap, Address old_start, Address new_start);
......@@ -160,16 +161,15 @@ class Marking : public AllStatic {
INLINE(static bool TransferColor(HeapObject* from, HeapObject* to)) {
MarkBit from_mark_bit = MarkBitFrom(from);
MarkBit to_mark_bit = MarkBitFrom(to);
bool is_black = false;
DCHECK(Marking::IsWhite(to_mark_bit));
if (from_mark_bit.Get()) {
to_mark_bit.Set();
is_black = true; // Looks black so far.
}
if (from_mark_bit.Next().Get()) {
to_mark_bit.Next().Set();
is_black = false; // Was actually gray.
if (from_mark_bit.Next().Get()) {
to_mark_bit.Next().Set();
return true;
}
}
return is_black;
return false;
}
private:
......@@ -853,6 +853,26 @@ class MarkBitCellIterator BASE_EMBEDDED {
Address cell_base_;
};
enum LiveObjectIterationMode { kBlackObjects, kGreyObjects, kAllLiveObjects };
template <LiveObjectIterationMode T>
class LiveObjectIterator BASE_EMBEDDED {
public:
explicit LiveObjectIterator(MemoryChunk* chunk)
: chunk_(chunk),
it_(chunk_),
cell_base_(it_.CurrentCellBase()),
current_cell_(*it_.CurrentCell()) {}
HeapObject* Next();
private:
MemoryChunk* chunk_;
MarkBitCellIterator it_;
Address cell_base_;
MarkBit::CellType current_cell_;
};
class EvacuationScope BASE_EMBEDDED {
public:
......
......@@ -2900,10 +2900,9 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch1,
Label* on_black,
Label::Distance on_black_near) {
HasColor(object, scratch0, scratch1,
on_black, on_black_near,
1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, on_black_near, 1,
1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -2965,8 +2964,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -5408,8 +5408,8 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch0,
Register scratch1,
Label* on_black) {
HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -5466,8 +5466,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -6121,8 +6121,8 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch0,
Register scratch1,
Label* on_black) {
HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -6178,8 +6178,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -3174,8 +3174,8 @@ void MacroAssembler::CheckPageFlag(
void MacroAssembler::JumpIfBlack(Register object, Register scratch0,
Register scratch1, Label* on_black) {
HasColor(object, scratch0, scratch1, on_black, 1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, 1, 1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -3232,8 +3232,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -5286,16 +5286,13 @@ void MacroAssembler::JumpIfBlack(Register object,
Label* on_black,
Label::Distance on_black_distance) {
DCHECK(!AreAliased(object, bitmap_scratch, mask_scratch, rcx));
GetMarkBits(object, bitmap_scratch, mask_scratch);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
// The mask_scratch register contains a 1 at the position of the first bit
// and a 0 at all other positions, including the position of the second bit.
// and a 1 at a position of the second bit. All other positions are zero.
movp(rcx, mask_scratch);
// Make rcx into a mask that covers both marking bits using the operation
// rcx = mask | (mask << 1).
leap(rcx, Operand(mask_scratch, mask_scratch, times_2, 0));
// Note that we are using a 4-byte aligned 8-byte load.
andp(rcx, Operand(bitmap_scratch, MemoryChunk::kHeaderSize));
cmpp(mask_scratch, rcx);
j(equal, on_black, on_black_distance);
......@@ -5321,7 +5318,7 @@ void MacroAssembler::GetMarkBits(Register addr_reg,
movp(rcx, addr_reg);
shrl(rcx, Immediate(kPointerSizeLog2));
andp(rcx, Immediate((1 << Bitmap::kBitsPerCellLog2) - 1));
movl(mask_reg, Immediate(1));
movl(mask_reg, Immediate(3));
shlp_cl(mask_reg);
}
......@@ -5334,8 +5331,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
......@@ -230,11 +230,9 @@ class MacroAssembler: public Assembler {
}
// Check if an object has the black incremental marking color. Also uses rcx!
void JumpIfBlack(Register object,
Register scratch0,
Register scratch1,
Label* on_black,
Label::Distance on_black_distance = Label::kFar);
void JumpIfBlack(Register object, Register bitmap_scratch,
Register mask_scratch, Label* on_black,
Label::Distance on_black_distance);
// Checks the color of an object. If the object is white we jump to the
// incremental marker.
......
......@@ -2772,10 +2772,9 @@ void MacroAssembler::JumpIfBlack(Register object,
Register scratch1,
Label* on_black,
Label::Distance on_black_near) {
HasColor(object, scratch0, scratch1,
on_black, on_black_near,
1, 0); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
HasColor(object, scratch0, scratch1, on_black, on_black_near, 1,
1); // kBlackBitPattern.
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
}
......@@ -2837,8 +2836,8 @@ void MacroAssembler::JumpIfWhite(Register value, Register bitmap_scratch,
// If the value is black or grey we don't need to do anything.
DCHECK(strcmp(Marking::kWhiteBitPattern, "00") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kBlackBitPattern, "11") == 0);
DCHECK(strcmp(Marking::kGreyBitPattern, "10") == 0);
DCHECK(strcmp(Marking::kImpossibleBitPattern, "01") == 0);
// Since both black and grey have a 1 in the first position and white does
......
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