LCOV - code coverage report
Current view: top level - src/debug/x64 - debug-x64.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 46 50 92.0 %
Date: 2017-04-26 Functions: 8 8 100.0 %

          Line data    Source code
       1             : // Copyright 2012 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #if V8_TARGET_ARCH_X64
       6             : 
       7             : #include "src/debug/debug.h"
       8             : 
       9             : #include "src/assembler.h"
      10             : #include "src/codegen.h"
      11             : #include "src/debug/liveedit.h"
      12             : #include "src/objects-inl.h"
      13             : 
      14             : namespace v8 {
      15             : namespace internal {
      16             : 
      17             : #define __ ACCESS_MASM(masm)
      18             : 
      19             : 
      20     4636800 : void EmitDebugBreakSlot(MacroAssembler* masm) {
      21             :   Label check_codesize;
      22     4636800 :   __ bind(&check_codesize);
      23     4636800 :   __ Nop(Assembler::kDebugBreakSlotLength);
      24             :   DCHECK_EQ(Assembler::kDebugBreakSlotLength,
      25             :             masm->SizeOfCodeGeneratedSince(&check_codesize));
      26     4636800 : }
      27             : 
      28             : 
      29       17028 : void DebugCodegen::GenerateSlot(MacroAssembler* masm, RelocInfo::Mode mode) {
      30             :   // Generate enough nop's to make space for a call instruction.
      31       17028 :   masm->RecordDebugBreakSlot(mode);
      32       17028 :   EmitDebugBreakSlot(masm);
      33       17028 : }
      34             : 
      35             : 
      36     4619772 : void DebugCodegen::ClearDebugBreakSlot(Isolate* isolate, Address pc) {
      37     4619772 :   CodePatcher patcher(isolate, pc, Assembler::kDebugBreakSlotLength);
      38     4619772 :   EmitDebugBreakSlot(patcher.masm());
      39     4619772 : }
      40             : 
      41             : 
      42     2212169 : void DebugCodegen::PatchDebugBreakSlot(Isolate* isolate, Address pc,
      43             :                                        Handle<Code> code) {
      44             :   DCHECK(code->is_debug_stub());
      45             :   static const int kSize = Assembler::kDebugBreakSlotLength;
      46     2212169 :   CodePatcher patcher(isolate, pc, kSize);
      47             :   Label check_codesize;
      48     2212169 :   patcher.masm()->bind(&check_codesize);
      49     2212169 :   patcher.masm()->movp(kScratchRegister, reinterpret_cast<void*>(code->entry()),
      50     2212169 :                        Assembler::RelocInfoNone());
      51     2212169 :   patcher.masm()->call(kScratchRegister);
      52             :   // Check that the size of the code generated is as expected.
      53     2212169 :   DCHECK_EQ(kSize, patcher.masm()->SizeOfCodeGeneratedSince(&check_codesize));
      54     2212169 : }
      55             : 
      56       87516 : bool DebugCodegen::DebugBreakSlotIsPatched(Address pc) {
      57       87516 :   return !Assembler::IsNop(pc);
      58             : }
      59             : 
      60         129 : void DebugCodegen::GenerateDebugBreakStub(MacroAssembler* masm,
      61             :                                           DebugBreakCallHelperMode mode) {
      62          86 :   __ RecordComment("Debug break");
      63             : 
      64             :   // Enter an internal frame.
      65             :   {
      66          86 :     FrameScope scope(masm, StackFrame::INTERNAL);
      67             : 
      68             :     // Push arguments for DebugBreak call.
      69          86 :     if (mode == SAVE_RESULT_REGISTER) {
      70             :       // Break on return.
      71          43 :       __ Push(rax);
      72             :     } else {
      73             :       // Non-return breaks.
      74          43 :       __ Push(masm->isolate()->factory()->the_hole_value());
      75             :     }
      76             : 
      77             :     __ CallRuntime(Runtime::kDebugBreak, 1, kDontSaveFPRegs);
      78             : 
      79          86 :     if (FLAG_debug_code) {
      80           0 :       for (int i = 0; i < kNumJSCallerSaved; ++i) {
      81           0 :         Register reg = {JSCallerSavedCode(i)};
      82             :         // Do not clobber rax if mode is SAVE_RESULT_REGISTER. It will
      83             :         // contain return value of the function.
      84           0 :         if (!(reg.is(rax) && (mode == SAVE_RESULT_REGISTER))) {
      85           0 :           __ Set(reg, kDebugZapValue);
      86             :         }
      87             :       }
      88          86 :     }
      89             :     // Get rid of the internal frame.
      90             :   }
      91             : 
      92          86 :   __ MaybeDropFrames();
      93             : 
      94             :   // Return to caller.
      95          86 :   __ ret(0);
      96          86 : }
      97             : 
      98          43 : void DebugCodegen::GenerateHandleDebuggerStatement(MacroAssembler* masm) {
      99             :   {
     100          43 :     FrameScope scope(masm, StackFrame::INTERNAL);
     101          43 :     __ CallRuntime(Runtime::kHandleDebuggerStatement, 0);
     102             :   }
     103          43 :   __ MaybeDropFrames();
     104             : 
     105             :   // Return to caller.
     106          43 :   __ ret(0);
     107          43 : }
     108             : 
     109          43 : void DebugCodegen::GenerateFrameDropperTrampoline(MacroAssembler* masm) {
     110             :   // Frame is being dropped:
     111             :   // - Drop to the target frame specified by rbx.
     112             :   // - Look up current function on the frame.
     113             :   // - Leave the frame.
     114             :   // - Restart the frame by calling the function.
     115          43 :   __ movp(rbp, rbx);
     116          86 :   __ movp(rdi, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset));
     117          43 :   __ leave();
     118             : 
     119             :   __ movp(rbx, FieldOperand(rdi, JSFunction::kSharedFunctionInfoOffset));
     120             :   __ LoadSharedFunctionInfoSpecialField(
     121          43 :       rbx, rbx, SharedFunctionInfo::kFormalParameterCountOffset);
     122             : 
     123             :   ParameterCount dummy(rbx);
     124             :   __ InvokeFunction(rdi, no_reg, dummy, dummy, JUMP_FUNCTION,
     125          43 :                     CheckDebugStepCallWrapper());
     126          43 : }
     127             : 
     128             : const bool LiveEdit::kFrameDropperSupported = true;
     129             : 
     130             : #undef __
     131             : 
     132             : }  // namespace internal
     133             : }  // namespace v8
     134             : 
     135             : #endif  // V8_TARGET_ARCH_X64

Generated by: LCOV version 1.10