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 "vm/code_generator.h" | 9 #include "vm/code_generator.h" |
10 #include "vm/code_patcher.h" | 10 #include "vm/code_patcher.h" |
(...skipping 1158 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1169 if (function.HasOptimizedCode()) { | 1169 if (function.HasOptimizedCode()) { |
1170 function.SwitchToUnoptimizedCode(); | 1170 function.SwitchToUnoptimizedCode(); |
1171 } | 1171 } |
1172 } | 1172 } |
1173 } | 1173 } |
1174 } | 1174 } |
1175 } | 1175 } |
1176 } | 1176 } |
1177 | 1177 |
1178 | 1178 |
1179 void Debugger::SetInternalBreakpoints(const Function& target_function) { | 1179 RawError* Debugger::SetInternalBreakpoints(const Function& target_function) { |
1180 if (target_function.is_native()) { | 1180 if (target_function.is_native()) { |
1181 // Can't instrument native functions. | 1181 // Can't instrument native functions. Fail silently. |
1182 return; | 1182 return Error::null(); |
1183 } | 1183 } |
1184 Isolate* isolate = Isolate::Current(); | 1184 Isolate* isolate = Isolate::Current(); |
1185 if (!target_function.HasCode()) { | 1185 if (!target_function.HasCode()) { |
1186 Compiler::CompileFunction(isolate, target_function); | 1186 const Error& error = Error::Handle( |
1187 // If there were any errors, ignore them silently and return without | 1187 Compiler::CompileFunction(isolate, target_function)); |
1188 // adding breakpoints to target. | 1188 if (!error.IsNull()) { |
1189 if (!target_function.HasCode()) { | 1189 return error.raw(); |
1190 return; | |
1191 } | 1190 } |
1192 } | 1191 } |
1193 // Hang on to the code object before deoptimizing, in case deoptimization | 1192 // Hang on to the code object before deoptimizing, in case deoptimization |
1194 // might cause the GC to run. | 1193 // might cause the GC to run. |
1195 Code& code = Code::Handle(isolate, target_function.unoptimized_code()); | 1194 Code& code = Code::Handle(isolate, target_function.unoptimized_code()); |
1196 ASSERT(!code.IsNull()); | 1195 ASSERT(!code.IsNull()); |
1197 DeoptimizeWorld(); | 1196 DeoptimizeWorld(); |
1198 ASSERT(!target_function.HasOptimizedCode()); | 1197 ASSERT(!target_function.HasOptimizedCode()); |
1199 PcDescriptors& desc = PcDescriptors::Handle(isolate, code.pc_descriptors()); | 1198 PcDescriptors& desc = PcDescriptors::Handle(isolate, code.pc_descriptors()); |
1200 PcDescriptors::Iterator iter(desc, kSafepointKind); | 1199 PcDescriptors::Iterator iter(desc, kSafepointKind); |
1201 while (iter.MoveNext()) { | 1200 while (iter.MoveNext()) { |
1202 if (iter.TokenPos() != Scanner::kNoSourcePos) { | 1201 if (iter.TokenPos() != Scanner::kNoSourcePos) { |
1203 CodeBreakpoint* bpt = GetCodeBreakpoint(iter.Pc()); | 1202 CodeBreakpoint* bpt = GetCodeBreakpoint(iter.Pc()); |
1204 if (bpt != NULL) { | 1203 if (bpt != NULL) { |
1205 // There is already a breakpoint for this address. Make sure | 1204 // There is already a breakpoint for this address. Make sure |
1206 // it is enabled. | 1205 // it is enabled. |
1207 bpt->Enable(); | 1206 bpt->Enable(); |
1208 continue; | 1207 continue; |
1209 } | 1208 } |
1210 bpt = new CodeBreakpoint(code, iter.TokenPos(), | 1209 bpt = new CodeBreakpoint(code, iter.TokenPos(), |
1211 iter.Pc(), iter.Kind()); | 1210 iter.Pc(), iter.Kind()); |
1212 RegisterCodeBreakpoint(bpt); | 1211 RegisterCodeBreakpoint(bpt); |
1213 bpt->Enable(); | 1212 bpt->Enable(); |
1214 } | 1213 } |
1215 } | 1214 } |
| 1215 return Error::null(); |
1216 } | 1216 } |
1217 | 1217 |
1218 | 1218 |
1219 void Debugger::SignalBpResolved(SourceBreakpoint* bpt) { | 1219 void Debugger::SignalBpResolved(SourceBreakpoint* bpt) { |
1220 if (HasEventHandler()) { | 1220 if (HasEventHandler()) { |
1221 DebuggerEvent event(isolate_, DebuggerEvent::kBreakpointResolved); | 1221 DebuggerEvent event(isolate_, DebuggerEvent::kBreakpointResolved); |
1222 event.set_breakpoint(bpt); | 1222 event.set_breakpoint(bpt); |
1223 InvokeEventHandler(&event); | 1223 InvokeEventHandler(&event); |
1224 } | 1224 } |
1225 } | 1225 } |
(...skipping 639 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1865 cbpt->Enable(); | 1865 cbpt->Enable(); |
1866 } else { | 1866 } else { |
1867 cbpt->Disable(); | 1867 cbpt->Disable(); |
1868 } | 1868 } |
1869 } | 1869 } |
1870 cbpt = cbpt->next(); | 1870 cbpt = cbpt->next(); |
1871 } | 1871 } |
1872 } | 1872 } |
1873 | 1873 |
1874 | 1874 |
1875 void Debugger::OneTimeBreakAtEntry(const Function& target_function) { | 1875 RawError* Debugger::OneTimeBreakAtEntry(const Function& target_function) { |
1876 SetInternalBreakpoints(target_function); | 1876 Error& err = Error::Handle(); |
1877 if (target_function.HasImplicitClosureFunction()) { | 1877 err = SetInternalBreakpoints(target_function); |
| 1878 if (err.IsNull() && target_function.HasImplicitClosureFunction()) { |
1878 const Function& closure_func = | 1879 const Function& closure_func = |
1879 Function::Handle(target_function.ImplicitClosureFunction()); | 1880 Function::Handle(target_function.ImplicitClosureFunction()); |
1880 SetInternalBreakpoints(closure_func); | 1881 err = SetInternalBreakpoints(closure_func); |
1881 } | 1882 } |
| 1883 return err.raw(); |
1882 } | 1884 } |
1883 | 1885 |
1884 | 1886 |
1885 SourceBreakpoint* Debugger::SetBreakpointAtEntry( | 1887 SourceBreakpoint* Debugger::SetBreakpointAtEntry( |
1886 const Function& target_function) { | 1888 const Function& target_function) { |
1887 ASSERT(!target_function.IsNull()); | 1889 ASSERT(!target_function.IsNull()); |
1888 const Script& script = Script::Handle(target_function.script()); | 1890 const Script& script = Script::Handle(target_function.script()); |
1889 return SetBreakpoint(script, | 1891 return SetBreakpoint(script, |
1890 target_function.token_pos(), | 1892 target_function.token_pos(), |
1891 target_function.end_token_pos()); | 1893 target_function.end_token_pos()); |
(...skipping 686 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2578 } | 2580 } |
2579 | 2581 |
2580 | 2582 |
2581 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) { | 2583 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) { |
2582 ASSERT(bpt->next() == NULL); | 2584 ASSERT(bpt->next() == NULL); |
2583 bpt->set_next(code_breakpoints_); | 2585 bpt->set_next(code_breakpoints_); |
2584 code_breakpoints_ = bpt; | 2586 code_breakpoints_ = bpt; |
2585 } | 2587 } |
2586 | 2588 |
2587 } // namespace dart | 2589 } // namespace dart |
OLD | NEW |