Commit ba2d7da5 authored by yangguo@chromium.org's avatar yangguo@chromium.org

Introduce intrinsic to expose debug state to generated code.

R=ulan@chromium.org

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

git-svn-id: https://v8.googlecode.com/svn/branches/bleeding_edge@21908 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent e56faa99
...@@ -4009,6 +4009,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) { ...@@ -4009,6 +4009,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) {
} }
void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
ASSERT(expr->arguments()->length() == 0);
ExternalReference debug_is_active =
ExternalReference::debug_is_active_address(isolate());
__ mov(ip, Operand(debug_is_active));
__ ldrb(r0, MemOperand(ip));
__ SmiTag(r0);
context()->Plug(r0);
}
void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
if (expr->function() != NULL && if (expr->function() != NULL &&
expr->function()->intrinsic_type == Runtime::INLINE) { expr->function()->intrinsic_type == Runtime::INLINE) {
......
...@@ -3720,6 +3720,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) { ...@@ -3720,6 +3720,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) {
} }
void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
ASSERT(expr->arguments()->length() == 0);
ExternalReference debug_is_active =
ExternalReference::debug_is_active_address(isolate());
__ Mov(x10, debug_is_active);
__ Ldrb(x0, MemOperand(x10));
__ SmiTag(x0);
context()->Plug(x0);
}
void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
if (expr->function() != NULL && if (expr->function() != NULL &&
expr->function()->intrinsic_type == Runtime::INLINE) { expr->function()->intrinsic_type == Runtime::INLINE) {
......
...@@ -1128,7 +1128,7 @@ function ArrayFilter(f, receiver) { ...@@ -1128,7 +1128,7 @@ function ArrayFilter(f, receiver) {
var result = new $Array(); var result = new $Array();
var accumulator = new InternalArray(); var accumulator = new InternalArray();
var accumulator_length = 0; var accumulator_length = 0;
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
for (var i = 0; i < length; i++) { for (var i = 0; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1161,7 +1161,7 @@ function ArrayForEach(f, receiver) { ...@@ -1161,7 +1161,7 @@ function ArrayForEach(f, receiver) {
receiver = ToObject(receiver); receiver = ToObject(receiver);
} }
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
for (var i = 0; i < length; i++) { for (var i = 0; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1192,7 +1192,7 @@ function ArraySome(f, receiver) { ...@@ -1192,7 +1192,7 @@ function ArraySome(f, receiver) {
receiver = ToObject(receiver); receiver = ToObject(receiver);
} }
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
for (var i = 0; i < length; i++) { for (var i = 0; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1222,7 +1222,7 @@ function ArrayEvery(f, receiver) { ...@@ -1222,7 +1222,7 @@ function ArrayEvery(f, receiver) {
receiver = ToObject(receiver); receiver = ToObject(receiver);
} }
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
for (var i = 0; i < length; i++) { for (var i = 0; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1253,7 +1253,7 @@ function ArrayMap(f, receiver) { ...@@ -1253,7 +1253,7 @@ function ArrayMap(f, receiver) {
var result = new $Array(); var result = new $Array();
var accumulator = new InternalArray(length); var accumulator = new InternalArray(length);
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
for (var i = 0; i < length; i++) { for (var i = 0; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1400,7 +1400,7 @@ function ArrayReduce(callback, current) { ...@@ -1400,7 +1400,7 @@ function ArrayReduce(callback, current) {
} }
var receiver = %GetDefaultReceiver(callback); var receiver = %GetDefaultReceiver(callback);
var stepping = %_DebugCallbackSupportsStepping(callback); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(callback);
for (; i < length; i++) { for (; i < length; i++) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
...@@ -1437,7 +1437,7 @@ function ArrayReduceRight(callback, current) { ...@@ -1437,7 +1437,7 @@ function ArrayReduceRight(callback, current) {
} }
var receiver = %GetDefaultReceiver(callback); var receiver = %GetDefaultReceiver(callback);
var stepping = %_DebugCallbackSupportsStepping(callback); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(callback);
for (; i >= 0; i--) { for (; i >= 0; i--) {
if (i in array) { if (i in array) {
var element = array[i]; var element = array[i];
......
...@@ -1428,6 +1428,12 @@ ExternalReference ExternalReference::cpu_features() { ...@@ -1428,6 +1428,12 @@ ExternalReference ExternalReference::cpu_features() {
} }
ExternalReference ExternalReference::debug_is_active_address(
Isolate* isolate) {
return ExternalReference(isolate->debug()->is_active_address());
}
ExternalReference ExternalReference::debug_after_break_target_address( ExternalReference ExternalReference::debug_after_break_target_address(
Isolate* isolate) { Isolate* isolate) {
return ExternalReference(isolate->debug()->after_break_target_address()); return ExternalReference(isolate->debug()->after_break_target_address());
......
...@@ -911,6 +911,7 @@ class ExternalReference BASE_EMBEDDED { ...@@ -911,6 +911,7 @@ class ExternalReference BASE_EMBEDDED {
static ExternalReference cpu_features(); static ExternalReference cpu_features();
static ExternalReference debug_is_active_address(Isolate* isolate);
static ExternalReference debug_after_break_target_address(Isolate* isolate); static ExternalReference debug_after_break_target_address(Isolate* isolate);
static ExternalReference debug_restarter_frame_function_pointer_address( static ExternalReference debug_restarter_frame_function_pointer_address(
Isolate* isolate); Isolate* isolate);
......
...@@ -81,7 +81,7 @@ function SetForEach(f, receiver) { ...@@ -81,7 +81,7 @@ function SetForEach(f, receiver) {
var iterator = new SetIterator(this, ITERATOR_KIND_VALUES); var iterator = new SetIterator(this, ITERATOR_KIND_VALUES);
var entry; var entry;
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
while (!(entry = %SetIteratorNext(iterator)).done) { while (!(entry = %SetIteratorNext(iterator)).done) {
if (stepping) %DebugPrepareStepInIfStepping(f); if (stepping) %DebugPrepareStepInIfStepping(f);
%_CallFunction(receiver, entry.value, entry.value, this, f); %_CallFunction(receiver, entry.value, entry.value, this, f);
...@@ -192,7 +192,7 @@ function MapForEach(f, receiver) { ...@@ -192,7 +192,7 @@ function MapForEach(f, receiver) {
var iterator = new MapIterator(this, ITERATOR_KIND_ENTRIES); var iterator = new MapIterator(this, ITERATOR_KIND_ENTRIES);
var entry; var entry;
var stepping = %_DebugCallbackSupportsStepping(f); var stepping = DEBUG_IS_ACTIVE && %DebugCallbackSupportsStepping(f);
while (!(entry = %MapIteratorNext(iterator)).done) { while (!(entry = %MapIteratorNext(iterator)).done) {
if (stepping) %DebugPrepareStepInIfStepping(f); if (stepping) %DebugPrepareStepInIfStepping(f);
%_CallFunction(receiver, entry.value[1], entry.value[0], this, f); %_CallFunction(receiver, entry.value[1], entry.value[0], this, f);
......
...@@ -505,6 +505,10 @@ class Debug { ...@@ -505,6 +505,10 @@ class Debug {
int break_id() { return thread_local_.break_id_; } int break_id() { return thread_local_.break_id_; }
// Support for embedding into generated code. // Support for embedding into generated code.
Address is_active_address() {
return reinterpret_cast<Address>(&is_active_);
}
Address after_break_target_address() { Address after_break_target_address() {
return reinterpret_cast<Address>(&after_break_target_); return reinterpret_cast<Address>(&after_break_target_);
} }
......
...@@ -6120,6 +6120,11 @@ class HObjectAccess V8_FINAL { ...@@ -6120,6 +6120,11 @@ class HObjectAccess V8_FINAL {
Handle<String>::null(), false, false); Handle<String>::null(), false, false);
} }
static HObjectAccess ForExternalUInteger8() {
return HObjectAccess(kExternalMemory, 0, Representation::UInteger8(),
Handle<String>::null(), false, false);
}
// Create an access to an offset in a fixed array header. // Create an access to an offset in a fixed array header.
static HObjectAccess ForFixedArrayHeader(int offset); static HObjectAccess ForFixedArrayHeader(int offset);
......
...@@ -11711,11 +11711,13 @@ void HOptimizedGraphBuilder::GenerateDebugBreakInOptimizedCode( ...@@ -11711,11 +11711,13 @@ void HOptimizedGraphBuilder::GenerateDebugBreakInOptimizedCode(
} }
void HOptimizedGraphBuilder::GenerateDebugCallbackSupportsStepping( void HOptimizedGraphBuilder::GenerateDebugIsActive(CallRuntime* call) {
CallRuntime* call) { ASSERT(call->arguments()->length() == 0);
ASSERT(call->arguments()->length() == 1); HValue* ref =
// Debugging is not supported in optimized code. Add<HConstant>(ExternalReference::debug_is_active_address(isolate()));
return ast_context()->ReturnValue(graph()->GetConstantFalse()); HValue* value = Add<HLoadNamedField>(
ref, static_cast<HValue*>(NULL), HObjectAccess::ForExternalUInteger8());
return ast_context()->ReturnValue(value);
} }
......
...@@ -3996,6 +3996,16 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) { ...@@ -3996,6 +3996,16 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) {
} }
void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
ASSERT(expr->arguments()->length() == 0);
ExternalReference debug_is_active =
ExternalReference::debug_is_active_address(isolate());
__ movzx_b(eax, Operand::StaticVariable(debug_is_active));
__ SmiTag(eax);
context()->Plug(eax);
}
void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
if (expr->function() != NULL && if (expr->function() != NULL &&
expr->function()->intrinsic_type == Runtime::INLINE) { expr->function()->intrinsic_type == Runtime::INLINE) {
......
...@@ -285,3 +285,6 @@ const PROPERTY_ATTRIBUTES_PRIVATE_SYMBOL = 32; ...@@ -285,3 +285,6 @@ const PROPERTY_ATTRIBUTES_PRIVATE_SYMBOL = 32;
const ITERATOR_KIND_KEYS = 1; const ITERATOR_KIND_KEYS = 1;
const ITERATOR_KIND_VALUES = 2; const ITERATOR_KIND_VALUES = 2;
const ITERATOR_KIND_ENTRIES = 3; const ITERATOR_KIND_ENTRIES = 3;
# Check whether debug is active.
const DEBUG_IS_ACTIVE = (%_DebugIsActive() != 0);
...@@ -438,6 +438,7 @@ namespace internal { ...@@ -438,6 +438,7 @@ namespace internal {
F(DebugConstructedBy, 2, 1) \ F(DebugConstructedBy, 2, 1) \
F(DebugGetPrototype, 1, 1) \ F(DebugGetPrototype, 1, 1) \
F(DebugSetScriptSource, 2, 1) \ F(DebugSetScriptSource, 2, 1) \
F(DebugCallbackSupportsStepping, 1, 1) \
F(SystemBreak, 0, 1) \ F(SystemBreak, 0, 1) \
F(DebugDisassembleFunction, 1, 1) \ F(DebugDisassembleFunction, 1, 1) \
F(DebugDisassembleConstructor, 1, 1) \ F(DebugDisassembleConstructor, 1, 1) \
...@@ -654,7 +655,8 @@ namespace internal { ...@@ -654,7 +655,8 @@ namespace internal {
F(RegExpExec, 4, 1) \ F(RegExpExec, 4, 1) \
F(RegExpConstructResult, 3, 1) \ F(RegExpConstructResult, 3, 1) \
F(GetFromCache, 2, 1) \ F(GetFromCache, 2, 1) \
F(NumberToString, 1, 1) F(NumberToString, 1, 1) \
F(DebugIsActive, 0, 1)
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
...@@ -680,9 +682,7 @@ namespace internal { ...@@ -680,9 +682,7 @@ namespace internal {
F(DoubleHi, 1, 1) \ F(DoubleHi, 1, 1) \
F(DoubleLo, 1, 1) \ F(DoubleLo, 1, 1) \
F(MathSqrtRT, 1, 1) \ F(MathSqrtRT, 1, 1) \
F(MathLogRT, 1, 1) \ F(MathLogRT, 1, 1)
/* Debugger */ \
F(DebugCallbackSupportsStepping, 1, 1)
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
......
...@@ -4004,6 +4004,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) { ...@@ -4004,6 +4004,17 @@ void FullCodeGenerator::EmitFastAsciiArrayJoin(CallRuntime* expr) {
} }
void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
ASSERT(expr->arguments()->length() == 0);
ExternalReference debug_is_active =
ExternalReference::debug_is_active_address(isolate());
__ Move(kScratchRegister, debug_is_active);
__ movzxbp(rax, Operand(kScratchRegister, 0));
__ Integer32ToSmi(rax, rax);
context()->Plug(rax);
}
void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
if (expr->function() != NULL && if (expr->function() != NULL &&
expr->function()->intrinsic_type == Runtime::INLINE) { expr->function()->intrinsic_type == Runtime::INLINE) {
......
// Copyright 2014 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// Flags: --expose-debug-as debug --allow-natives-syntax
Debug = debug.Debug;
function f() { return %_DebugIsActive() != 0; }
assertFalse(f());
assertFalse(f());
Debug.setListener(function() {});
assertTrue(f());
Debug.setListener(null);
assertFalse(f());
%OptimizeFunctionOnNextCall(f);
assertFalse(f());
assertOptimized(f);
Debug.setListener(function() {});
assertTrue(f());
assertOptimized(f);
Debug.setListener(null);
assertFalse(f());
assertOptimized(f);
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