Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/debugger.h" | 5 #include "vm/debugger.h" |
| 6 | 6 |
| 7 #include "include/dart_api.h" | 7 #include "include/dart_api.h" |
| 8 | 8 |
| 9 #include "platform/address_sanitizer.h" | 9 #include "platform/address_sanitizer.h" |
| 10 | 10 |
| (...skipping 921 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 932 intptr_t var_desc_len = var_descriptors_.Length(); | 932 intptr_t var_desc_len = var_descriptors_.Length(); |
| 933 for (intptr_t i = 0; i < var_desc_len; i++) { | 933 for (intptr_t i = 0; i < var_desc_len; i++) { |
| 934 RawLocalVarDescriptors::VarInfo var_info; | 934 RawLocalVarDescriptors::VarInfo var_info; |
| 935 var_descriptors_.GetInfo(i, &var_info); | 935 var_descriptors_.GetInfo(i, &var_info); |
| 936 const int8_t kind = var_info.kind(); | 936 const int8_t kind = var_info.kind(); |
| 937 if (kind == RawLocalVarDescriptors::kSavedCurrentContext) { | 937 if (kind == RawLocalVarDescriptors::kSavedCurrentContext) { |
| 938 if (FLAG_trace_debugger_stacktrace) { | 938 if (FLAG_trace_debugger_stacktrace) { |
| 939 OS::PrintErr("\tFound saved current ctx at index %d\n", | 939 OS::PrintErr("\tFound saved current ctx at index %d\n", |
| 940 var_info.index()); | 940 var_info.index()); |
| 941 } | 941 } |
| 942 ctx_ ^= GetStackVar(var_info.index()); | 942 const Object& obj = Object::Handle(GetStackVar(var_info.index())); |
|
siva
2017/04/13 01:22:58
This handle could be hoisted outside the for loop.
Cutch
2017/04/13 14:34:44
Done.
| |
| 943 if (obj.IsClosure()) { | |
| 944 ASSERT(function().name() == Symbols::Call().raw()); | |
| 945 ASSERT(function().IsInvokeFieldDispatcher()); | |
| 946 // Closure.call frames. | |
| 947 ctx_ ^= Closure::Cast(obj).context(); | |
| 948 } else if (obj.IsContext()) { | |
| 949 ctx_ ^= Context::Cast(obj).raw(); | |
| 950 } else { | |
| 951 ASSERT(obj.IsNull()); | |
| 952 } | |
| 943 return ctx_; | 953 return ctx_; |
| 944 } | 954 } |
| 945 } | 955 } |
| 946 return Context::ZoneHandle(Context::null()); | 956 return Context::ZoneHandle(Context::null()); |
|
siva
2017/04/13 01:30:06
Why is it not ok to use the same ctx_ as above
i.e
Cutch
2017/04/13 14:34:44
Done.
| |
| 947 } | 957 } |
| 948 | 958 |
| 949 | 959 |
| 950 RawObject* ActivationFrame::GetAsyncOperation() { | 960 RawObject* ActivationFrame::GetAsyncOperation() { |
| 951 GetVarDescriptors(); | 961 GetVarDescriptors(); |
| 952 intptr_t var_desc_len = var_descriptors_.Length(); | 962 intptr_t var_desc_len = var_descriptors_.Length(); |
| 953 for (intptr_t i = 0; i < var_desc_len; i++) { | 963 for (intptr_t i = 0; i < var_desc_len; i++) { |
| 954 RawLocalVarDescriptors::VarInfo var_info; | 964 RawLocalVarDescriptors::VarInfo var_info; |
| 955 var_descriptors_.GetInfo(i, &var_info); | 965 var_descriptors_.GetInfo(i, &var_info); |
| 956 if (var_descriptors_.GetName(i) == Symbols::AsyncOperation().raw()) { | 966 if (var_descriptors_.GetName(i) == Symbols::AsyncOperation().raw()) { |
| (...skipping 1011 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1968 } | 1978 } |
| 1969 // Follow the link. | 1979 // Follow the link. |
| 1970 async_stack_trace = async_stack_trace.async_link(); | 1980 async_stack_trace = async_stack_trace.async_link(); |
| 1971 } | 1981 } |
| 1972 | 1982 |
| 1973 return stack_trace; | 1983 return stack_trace; |
| 1974 } | 1984 } |
| 1975 | 1985 |
| 1976 | 1986 |
| 1977 DebuggerStackTrace* Debugger::CollectAwaiterReturnStackTrace() { | 1987 DebuggerStackTrace* Debugger::CollectAwaiterReturnStackTrace() { |
| 1978 if (!FLAG_causal_async_stacks) { | 1988 if (!FLAG_async_debugger) { |
| 1979 return NULL; | 1989 return NULL; |
| 1980 } | 1990 } |
| 1981 // Causal async stacks are not supported in the AOT runtime. | 1991 // Causal async stacks are not supported in the AOT runtime. |
| 1982 ASSERT(!FLAG_precompiled_runtime); | 1992 ASSERT(!FLAG_precompiled_runtime); |
| 1983 | 1993 |
| 1984 Thread* thread = Thread::Current(); | 1994 Thread* thread = Thread::Current(); |
| 1985 Zone* zone = thread->zone(); | 1995 Zone* zone = thread->zone(); |
| 1986 Isolate* isolate = thread->isolate(); | 1996 Isolate* isolate = thread->isolate(); |
| 1987 DebuggerStackTrace* stack_trace = new DebuggerStackTrace(8); | 1997 DebuggerStackTrace* stack_trace = new DebuggerStackTrace(8); |
| 1988 | 1998 |
| 1989 StackFrameIterator iterator(StackFrameIterator::kDontValidateFrames); | 1999 StackFrameIterator iterator(StackFrameIterator::kDontValidateFrames); |
| 1990 | 2000 |
| 1991 Code& code = Code::Handle(zone); | 2001 Code& code = Code::Handle(zone); |
| 1992 Smi& offset = Smi::Handle(zone); | 2002 Smi& offset = Smi::Handle(zone); |
| 1993 Function& function = Function::Handle(zone); | 2003 Function& function = Function::Handle(zone); |
| 1994 Code& inlined_code = Code::Handle(zone); | 2004 Code& inlined_code = Code::Handle(zone); |
| 1995 Closure& async_activation = Closure::Handle(zone); | 2005 Closure& async_activation = Closure::Handle(zone); |
| 1996 Object& next_async_activation = Object::Handle(zone); | 2006 Object& next_async_activation = Object::Handle(zone); |
| 1997 Array& deopt_frame = Array::Handle(zone); | 2007 Array& deopt_frame = Array::Handle(zone); |
| 1998 class StackTrace& async_stack_trace = StackTrace::Handle(zone); | 2008 class StackTrace& async_stack_trace = StackTrace::Handle(zone); |
| 1999 | 2009 bool stack_has_async_function = false; |
| 2000 for (StackFrame* frame = iterator.NextFrame(); frame != NULL; | 2010 for (StackFrame* frame = iterator.NextFrame(); frame != NULL; |
| 2001 frame = iterator.NextFrame()) { | 2011 frame = iterator.NextFrame()) { |
| 2002 ASSERT(frame->IsValid()); | 2012 ASSERT(frame->IsValid()); |
| 2003 if (FLAG_trace_debugger_stacktrace) { | 2013 if (FLAG_trace_debugger_stacktrace) { |
| 2004 OS::PrintErr("CollectStackTrace: visiting frame:\n\t%s\n", | 2014 OS::PrintErr("CollectStackTrace: visiting frame:\n\t%s\n", |
| 2005 frame->ToCString()); | 2015 frame->ToCString()); |
| 2006 } | 2016 } |
| 2007 if (frame->IsDartFrame()) { | 2017 if (frame->IsDartFrame()) { |
| 2008 code = frame->LookupDartCode(); | 2018 code = frame->LookupDartCode(); |
| 2009 if (code.is_optimized()) { | 2019 if (code.is_optimized()) { |
| 2010 deopt_frame = DeoptimizeToArray(thread, frame, code); | 2020 deopt_frame = DeoptimizeToArray(thread, frame, code); |
| 2011 bool found_async_awaiter = false; | 2021 bool found_async_awaiter = false; |
| 2012 for (InlinedFunctionsIterator it(code, frame->pc()); !it.Done(); | 2022 for (InlinedFunctionsIterator it(code, frame->pc()); !it.Done(); |
| 2013 it.Advance()) { | 2023 it.Advance()) { |
| 2014 inlined_code = it.code(); | 2024 inlined_code = it.code(); |
| 2015 function = it.function(); | 2025 function = it.function(); |
| 2016 if (FLAG_trace_debugger_stacktrace) { | 2026 if (FLAG_trace_debugger_stacktrace) { |
| 2017 ASSERT(!function.IsNull()); | 2027 ASSERT(!function.IsNull()); |
| 2018 OS::PrintErr("CollectStackTrace: visiting inlined function: %s\n", | 2028 OS::PrintErr("CollectStackTrace: visiting inlined function: %s\n", |
| 2019 function.ToFullyQualifiedCString()); | 2029 function.ToFullyQualifiedCString()); |
| 2020 } | 2030 } |
| 2021 intptr_t deopt_frame_offset = it.GetDeoptFpOffset(); | 2031 intptr_t deopt_frame_offset = it.GetDeoptFpOffset(); |
| 2022 if (function.IsAsyncClosure() || function.IsAsyncGenClosure()) { | 2032 if (function.IsAsyncClosure() || function.IsAsyncGenClosure()) { |
| 2023 ActivationFrame* activation = CollectDartFrame( | 2033 ActivationFrame* activation = CollectDartFrame( |
| 2024 isolate, it.pc(), frame, inlined_code, deopt_frame, | 2034 isolate, it.pc(), frame, inlined_code, deopt_frame, |
| 2025 deopt_frame_offset, ActivationFrame::kAsyncActivation); | 2035 deopt_frame_offset, ActivationFrame::kAsyncActivation); |
| 2026 ASSERT(activation != NULL); | 2036 ASSERT(activation != NULL); |
| 2027 stack_trace->AddActivation(activation); | 2037 stack_trace->AddActivation(activation); |
| 2038 stack_has_async_function = true; | |
| 2028 // Grab the awaiter. | 2039 // Grab the awaiter. |
| 2029 async_activation ^= activation->GetAsyncAwaiter(); | 2040 async_activation ^= activation->GetAsyncAwaiter(); |
| 2030 found_async_awaiter = true; | 2041 found_async_awaiter = true; |
| 2031 break; | 2042 break; |
| 2032 } else { | 2043 } else { |
| 2033 stack_trace->AddActivation( | 2044 stack_trace->AddActivation( |
| 2034 CollectDartFrame(isolate, it.pc(), frame, inlined_code, | 2045 CollectDartFrame(isolate, it.pc(), frame, inlined_code, |
| 2035 deopt_frame, deopt_frame_offset)); | 2046 deopt_frame, deopt_frame_offset)); |
| 2036 } | 2047 } |
| 2037 } | 2048 } |
| 2038 // Break out of outer loop. | 2049 // Break out of outer loop. |
| 2039 if (found_async_awaiter) { | 2050 if (found_async_awaiter) { |
| 2040 break; | 2051 break; |
| 2041 } | 2052 } |
| 2042 } else { | 2053 } else { |
| 2043 function = code.function(); | 2054 function = code.function(); |
| 2044 if (function.IsAsyncClosure() || function.IsAsyncGenClosure()) { | 2055 if (function.IsAsyncClosure() || function.IsAsyncGenClosure()) { |
| 2045 ActivationFrame* activation = CollectDartFrame( | 2056 ActivationFrame* activation = CollectDartFrame( |
| 2046 isolate, frame->pc(), frame, code, Object::null_array(), 0, | 2057 isolate, frame->pc(), frame, code, Object::null_array(), 0, |
| 2047 ActivationFrame::kAsyncActivation); | 2058 ActivationFrame::kAsyncActivation); |
| 2048 ASSERT(activation != NULL); | 2059 ASSERT(activation != NULL); |
| 2049 stack_trace->AddActivation(activation); | 2060 stack_trace->AddActivation(activation); |
| 2061 stack_has_async_function = true; | |
| 2050 // Grab the awaiter. | 2062 // Grab the awaiter. |
| 2051 async_activation ^= activation->GetAsyncAwaiter(); | 2063 async_activation ^= activation->GetAsyncAwaiter(); |
| 2064 async_stack_trace ^= activation->GetCausalStack(); | |
| 2052 break; | 2065 break; |
| 2053 } else { | 2066 } else { |
| 2054 stack_trace->AddActivation(CollectDartFrame( | 2067 stack_trace->AddActivation(CollectDartFrame( |
| 2055 isolate, frame->pc(), frame, code, Object::null_array(), 0)); | 2068 isolate, frame->pc(), frame, code, Object::null_array(), 0)); |
| 2056 } | 2069 } |
| 2057 } | 2070 } |
| 2058 } | 2071 } |
| 2059 } | 2072 } |
| 2060 | 2073 |
| 2061 // Return NULL to indicate that there is no useful information in this stack | 2074 // If the stack doesn't have any async functions on it, return NULL. |
| 2062 // trace because we never found an awaiter. | 2075 if (!stack_has_async_function) { |
| 2063 if (async_activation.IsNull()) { | |
| 2064 return NULL; | 2076 return NULL; |
| 2065 } | 2077 } |
| 2066 | 2078 |
| 2067 // Append the awaiter return call stack. | 2079 // Append the awaiter return call stack. |
| 2068 while (!async_activation.IsNull()) { | 2080 while (!async_activation.IsNull()) { |
| 2069 ActivationFrame* activation = new (zone) ActivationFrame(async_activation); | 2081 ActivationFrame* activation = new (zone) ActivationFrame(async_activation); |
| 2070 activation->ExtractTokenPositionFromAsyncClosure(); | 2082 activation->ExtractTokenPositionFromAsyncClosure(); |
| 2071 stack_trace->AddActivation(activation); | 2083 stack_trace->AddActivation(activation); |
| 2072 next_async_activation = activation->GetAsyncAwaiter(); | 2084 next_async_activation = activation->GetAsyncAwaiter(); |
| 2073 if (next_async_activation.IsNull()) { | 2085 if (next_async_activation.IsNull()) { |
| (...skipping 2280 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 4354 | 4366 |
| 4355 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) { | 4367 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) { |
| 4356 ASSERT(bpt->next() == NULL); | 4368 ASSERT(bpt->next() == NULL); |
| 4357 bpt->set_next(code_breakpoints_); | 4369 bpt->set_next(code_breakpoints_); |
| 4358 code_breakpoints_ = bpt; | 4370 code_breakpoints_ = bpt; |
| 4359 } | 4371 } |
| 4360 | 4372 |
| 4361 #endif // !PRODUCT | 4373 #endif // !PRODUCT |
| 4362 | 4374 |
| 4363 } // namespace dart | 4375 } // namespace dart |
| OLD | NEW |