Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(199)

Side by Side Diff: src/debug.cc

Issue 3029033: Fix 'step in' after live edit stack manipulation (Closed)
Patch Set: follow codereview Created 10 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/debug.h ('k') | src/debug-debugger.js » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 1206 matching lines...) Expand 10 before | Expand all | Expand 10 after
1217 // Return if ensuring debug info failed. 1217 // Return if ensuring debug info failed.
1218 return; 1218 return;
1219 } 1219 }
1220 Handle<DebugInfo> debug_info = GetDebugInfo(shared); 1220 Handle<DebugInfo> debug_info = GetDebugInfo(shared);
1221 1221
1222 // Find the break location where execution has stopped. 1222 // Find the break location where execution has stopped.
1223 BreakLocationIterator it(debug_info, ALL_BREAK_LOCATIONS); 1223 BreakLocationIterator it(debug_info, ALL_BREAK_LOCATIONS);
1224 it.FindBreakLocationFromAddress(frame->pc()); 1224 it.FindBreakLocationFromAddress(frame->pc());
1225 1225
1226 // Compute whether or not the target is a call target. 1226 // Compute whether or not the target is a call target.
1227 bool is_call_target = false;
1228 bool is_load_or_store = false; 1227 bool is_load_or_store = false;
1229 bool is_inline_cache_stub = false; 1228 bool is_inline_cache_stub = false;
1229 bool is_at_restarted_function = false;
1230 Handle<Code> call_function_stub; 1230 Handle<Code> call_function_stub;
1231 if (RelocInfo::IsCodeTarget(it.rinfo()->rmode())) { 1231
1232 Address target = it.rinfo()->target_address(); 1232 if (thread_local_.restarter_frame_function_pointer_ == NULL) {
1233 Code* code = Code::GetCodeFromTargetAddress(target); 1233 if (RelocInfo::IsCodeTarget(it.rinfo()->rmode())) {
1234 if (code->is_call_stub() || code->is_keyed_call_stub()) { 1234 bool is_call_target = false;
1235 is_call_target = true; 1235 Address target = it.rinfo()->target_address();
1236 Code* code = Code::GetCodeFromTargetAddress(target);
1237 if (code->is_call_stub() || code->is_keyed_call_stub()) {
1238 is_call_target = true;
1239 }
1240 if (code->is_inline_cache_stub()) {
1241 is_inline_cache_stub = true;
1242 is_load_or_store = !is_call_target;
1243 }
1244
1245 // Check if target code is CallFunction stub.
1246 Code* maybe_call_function_stub = code;
1247 // If there is a breakpoint at this line look at the original code to
1248 // check if it is a CallFunction stub.
1249 if (it.IsDebugBreak()) {
1250 Address original_target = it.original_rinfo()->target_address();
1251 maybe_call_function_stub =
1252 Code::GetCodeFromTargetAddress(original_target);
1253 }
1254 if (maybe_call_function_stub->kind() == Code::STUB &&
1255 maybe_call_function_stub->major_key() == CodeStub::CallFunction) {
1256 // Save reference to the code as we may need it to find out arguments
1257 // count for 'step in' later.
1258 call_function_stub = Handle<Code>(maybe_call_function_stub);
1259 }
1236 } 1260 }
1237 if (code->is_inline_cache_stub()) { 1261 } else {
1238 is_inline_cache_stub = true; 1262 is_at_restarted_function = true;
1239 is_load_or_store = !is_call_target;
1240 }
1241
1242 // Check if target code is CallFunction stub.
1243 Code* maybe_call_function_stub = code;
1244 // If there is a breakpoint at this line look at the original code to
1245 // check if it is a CallFunction stub.
1246 if (it.IsDebugBreak()) {
1247 Address original_target = it.original_rinfo()->target_address();
1248 maybe_call_function_stub =
1249 Code::GetCodeFromTargetAddress(original_target);
1250 }
1251 if (maybe_call_function_stub->kind() == Code::STUB &&
1252 maybe_call_function_stub->major_key() == CodeStub::CallFunction) {
1253 // Save reference to the code as we may need it to find out arguments
1254 // count for 'step in' later.
1255 call_function_stub = Handle<Code>(maybe_call_function_stub);
1256 }
1257 } 1263 }
1258 1264
1259 // If this is the last break code target step out is the only possibility. 1265 // If this is the last break code target step out is the only possibility.
1260 if (it.IsExit() || step_action == StepOut) { 1266 if (it.IsExit() || step_action == StepOut) {
1261 if (step_action == StepOut) { 1267 if (step_action == StepOut) {
1262 // Skip step_count frames starting with the current one. 1268 // Skip step_count frames starting with the current one.
1263 while (step_count-- > 0 && !frames_it.done()) { 1269 while (step_count-- > 0 && !frames_it.done()) {
1264 frames_it.Advance(); 1270 frames_it.Advance();
1265 } 1271 }
1266 } else { 1272 } else {
1267 ASSERT(it.IsExit()); 1273 ASSERT(it.IsExit());
1268 frames_it.Advance(); 1274 frames_it.Advance();
1269 } 1275 }
1270 // Skip builtin functions on the stack. 1276 // Skip builtin functions on the stack.
1271 while (!frames_it.done() && 1277 while (!frames_it.done() &&
1272 JSFunction::cast(frames_it.frame()->function())->IsBuiltin()) { 1278 JSFunction::cast(frames_it.frame()->function())->IsBuiltin()) {
1273 frames_it.Advance(); 1279 frames_it.Advance();
1274 } 1280 }
1275 // Step out: If there is a JavaScript caller frame, we need to 1281 // Step out: If there is a JavaScript caller frame, we need to
1276 // flood it with breakpoints. 1282 // flood it with breakpoints.
1277 if (!frames_it.done()) { 1283 if (!frames_it.done()) {
1278 // Fill the function to return to with one-shot break points. 1284 // Fill the function to return to with one-shot break points.
1279 JSFunction* function = JSFunction::cast(frames_it.frame()->function()); 1285 JSFunction* function = JSFunction::cast(frames_it.frame()->function());
1280 FloodWithOneShot(Handle<SharedFunctionInfo>(function->shared())); 1286 FloodWithOneShot(Handle<SharedFunctionInfo>(function->shared()));
1281 // Set target frame pointer. 1287 // Set target frame pointer.
1282 ActivateStepOut(frames_it.frame()); 1288 ActivateStepOut(frames_it.frame());
1283 } 1289 }
1284 } else if (!(is_inline_cache_stub || RelocInfo::IsConstructCall(it.rmode()) || 1290 } else if (!(is_inline_cache_stub || RelocInfo::IsConstructCall(it.rmode()) ||
1285 !call_function_stub.is_null()) 1291 !call_function_stub.is_null() || is_at_restarted_function)
1286 || step_action == StepNext || step_action == StepMin) { 1292 || step_action == StepNext || step_action == StepMin) {
1287 // Step next or step min. 1293 // Step next or step min.
1288 1294
1289 // Fill the current function with one-shot break points. 1295 // Fill the current function with one-shot break points.
1290 FloodWithOneShot(shared); 1296 FloodWithOneShot(shared);
1291 1297
1292 // Remember source position and frame to handle step next. 1298 // Remember source position and frame to handle step next.
1293 thread_local_.last_statement_position_ = 1299 thread_local_.last_statement_position_ =
1294 debug_info->code()->SourceStatementPosition(frame->pc()); 1300 debug_info->code()->SourceStatementPosition(frame->pc());
1295 thread_local_.last_fp_ = frame->fp(); 1301 thread_local_.last_fp_ = frame->fp();
1296 } else { 1302 } else {
1297 // If it's CallFunction stub ensure target function is compiled and flood 1303 // If there's restarter frame on top of the stack, just get the pointer
1298 // it with one shot breakpoints. 1304 // to function which is going to be restarted.
1299 if (!call_function_stub.is_null()) { 1305 if (is_at_restarted_function) {
1306 Handle<JSFunction> restarted_function(
1307 JSFunction::cast(*thread_local_.restarter_frame_function_pointer_));
1308 Handle<SharedFunctionInfo> restarted_shared(
1309 restarted_function->shared());
1310 FloodWithOneShot(restarted_shared);
1311 } else if (!call_function_stub.is_null()) {
1312 // If it's CallFunction stub ensure target function is compiled and flood
1313 // it with one shot breakpoints.
1314
1300 // Find out number of arguments from the stub minor key. 1315 // Find out number of arguments from the stub minor key.
1301 // Reverse lookup required as the minor key cannot be retrieved 1316 // Reverse lookup required as the minor key cannot be retrieved
1302 // from the code object. 1317 // from the code object.
1303 Handle<Object> obj( 1318 Handle<Object> obj(
1304 Heap::code_stubs()->SlowReverseLookup(*call_function_stub)); 1319 Heap::code_stubs()->SlowReverseLookup(*call_function_stub));
1305 ASSERT(*obj != Heap::undefined_value()); 1320 ASSERT(*obj != Heap::undefined_value());
1306 ASSERT(obj->IsSmi()); 1321 ASSERT(obj->IsSmi());
1307 // Get the STUB key and extract major and minor key. 1322 // Get the STUB key and extract major and minor key.
1308 uint32_t key = Smi::cast(*obj)->value(); 1323 uint32_t key = Smi::cast(*obj)->value();
1309 // Argc in the stub is the number of arguments passed - not the 1324 // Argc in the stub is the number of arguments passed - not the
(...skipping 450 matching lines...) Expand 10 before | Expand all | Expand 10 after
1760 return (it.rinfo()->pc() == 1775 return (it.rinfo()->pc() ==
1761 addr - Assembler::kPatchReturnSequenceAddressOffset); 1776 addr - Assembler::kPatchReturnSequenceAddressOffset);
1762 } 1777 }
1763 it.next(); 1778 it.next();
1764 } 1779 }
1765 return false; 1780 return false;
1766 } 1781 }
1767 1782
1768 1783
1769 void Debug::FramesHaveBeenDropped(StackFrame::Id new_break_frame_id, 1784 void Debug::FramesHaveBeenDropped(StackFrame::Id new_break_frame_id,
1770 FrameDropMode mode) { 1785 FrameDropMode mode,
1786 Object** restarter_frame_function_pointer) {
1771 thread_local_.frame_drop_mode_ = mode; 1787 thread_local_.frame_drop_mode_ = mode;
1772 thread_local_.break_frame_id_ = new_break_frame_id; 1788 thread_local_.break_frame_id_ = new_break_frame_id;
1789 thread_local_.restarter_frame_function_pointer_ =
1790 restarter_frame_function_pointer;
1773 } 1791 }
1774 1792
1775 1793
1776 bool Debug::IsDebugGlobal(GlobalObject* global) { 1794 bool Debug::IsDebugGlobal(GlobalObject* global) {
1777 return IsLoaded() && global == Debug::debug_context()->global(); 1795 return IsLoaded() && global == Debug::debug_context()->global();
1778 } 1796 }
1779 1797
1780 1798
1781 void Debug::ClearMirrorCache() { 1799 void Debug::ClearMirrorCache() {
1782 HandleScope scope; 1800 HandleScope scope;
(...skipping 1213 matching lines...) Expand 10 before | Expand all | Expand 10 after
2996 { 3014 {
2997 Locker locker; 3015 Locker locker;
2998 Debugger::CallMessageDispatchHandler(); 3016 Debugger::CallMessageDispatchHandler();
2999 } 3017 }
3000 } 3018 }
3001 } 3019 }
3002 3020
3003 #endif // ENABLE_DEBUGGER_SUPPORT 3021 #endif // ENABLE_DEBUGGER_SUPPORT
3004 3022
3005 } } // namespace v8::internal 3023 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/debug.h ('k') | src/debug-debugger.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698