| Index: src/x64/macro-assembler-x64.cc
|
| diff --git a/src/x64/macro-assembler-x64.cc b/src/x64/macro-assembler-x64.cc
|
| index b2281163f37e7ec307a24fb1600f51a16d1cdc49..e740d0f521f6ed6fec4073fceb793d191c637d7e 100644
|
| --- a/src/x64/macro-assembler-x64.cc
|
| +++ b/src/x64/macro-assembler-x64.cc
|
| @@ -507,6 +507,77 @@ void MacroAssembler::RecordWrite(
|
| }
|
| }
|
|
|
| +void MacroAssembler::RecordWriteCodeEntryField(Register js_function,
|
| + Register code_entry,
|
| + Register dst) {
|
| + const int offset = JSFunction::kCodeEntryOffset;
|
| +
|
| + // Since a code entry (value) is always in old space, we don't need to update
|
| + // remembered set. If incremental marking is off, there is nothing for us to
|
| + // do.
|
| + if (!FLAG_incremental_marking) return;
|
| +
|
| + leap(dst, FieldOperand(js_function, offset));
|
| +
|
| + DCHECK(!js_function.is(code_entry));
|
| + DCHECK(!js_function.is(dst));
|
| + DCHECK(!code_entry.is(dst));
|
| + AssertNotSmi(js_function);
|
| +
|
| + if (emit_debug_code()) {
|
| + Label ok;
|
| + cmpp(code_entry, Operand(dst, 0));
|
| + j(equal, &ok, Label::kNear);
|
| + int3();
|
| + bind(&ok);
|
| + }
|
| +
|
| + // First, check if a write barrier is even needed. The tests below
|
| + // catch stores of Smis and stores into young gen.
|
| + Label done;
|
| +
|
| + CheckPageFlag(code_entry,
|
| + code_entry, // Used as scratch.
|
| + MemoryChunk::kPointersToHereAreInterestingMask, zero, &done,
|
| + Label::kNear);
|
| + CheckPageFlag(js_function,
|
| + code_entry, // Used as scratch.
|
| + MemoryChunk::kPointersFromHereAreInterestingMask, zero, &done,
|
| + Label::kNear);
|
| +
|
| + // Save input registers.
|
| + Push(js_function);
|
| + Push(code_entry);
|
| +
|
| + // Save caller-saved registers.
|
| + PushCallerSaved(kDontSaveFPRegs, js_function, code_entry);
|
| +
|
| + int argument_count = 3;
|
| + PrepareCallCFunction(argument_count);
|
| +
|
| + Push(js_function);
|
| + Push(dst);
|
| + Pop(arg_reg_2);
|
| + Pop(arg_reg_1);
|
| + Move(arg_reg_3, ExternalReference::isolate_address(isolate()));
|
| +
|
| + {
|
| + AllowExternalCallThatCantCauseGC scope(this);
|
| + CallCFunction(
|
| + ExternalReference::incremental_marking_record_write_code_entry_function(
|
| + isolate()),
|
| + argument_count);
|
| + }
|
| +
|
| + // Restore caller-saved registers.
|
| + PopCallerSaved(kDontSaveFPRegs, js_function, code_entry);
|
| +
|
| + // Restore input registers.
|
| + Pop(code_entry);
|
| + Pop(js_function);
|
| +
|
| + bind(&done);
|
| +}
|
|
|
| void MacroAssembler::Assert(Condition cc, BailoutReason reason) {
|
| if (emit_debug_code()) Check(cc, reason);
|
|
|