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

Side by Side Diff: src/runtime.cc

Issue 2783002: Better handling of stepping out of a function... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 10 years, 6 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 | Annotate | Revision Log
« no previous file with comments | « src/mirror-debugger.js ('k') | src/x64/full-codegen-x64.cc » ('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-2009 the V8 project authors. All rights reserved. 1 // Copyright 2006-2009 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 8225 matching lines...) Expand 10 before | Expand all | Expand 10 after
8236 } 8236 }
8237 8237
8238 8238
8239 static const int kFrameDetailsFrameIdIndex = 0; 8239 static const int kFrameDetailsFrameIdIndex = 0;
8240 static const int kFrameDetailsReceiverIndex = 1; 8240 static const int kFrameDetailsReceiverIndex = 1;
8241 static const int kFrameDetailsFunctionIndex = 2; 8241 static const int kFrameDetailsFunctionIndex = 2;
8242 static const int kFrameDetailsArgumentCountIndex = 3; 8242 static const int kFrameDetailsArgumentCountIndex = 3;
8243 static const int kFrameDetailsLocalCountIndex = 4; 8243 static const int kFrameDetailsLocalCountIndex = 4;
8244 static const int kFrameDetailsSourcePositionIndex = 5; 8244 static const int kFrameDetailsSourcePositionIndex = 5;
8245 static const int kFrameDetailsConstructCallIndex = 6; 8245 static const int kFrameDetailsConstructCallIndex = 6;
8246 static const int kFrameDetailsDebuggerFrameIndex = 7; 8246 static const int kFrameDetailsAtReturnIndex = 7;
8247 static const int kFrameDetailsFirstDynamicIndex = 8; 8247 static const int kFrameDetailsDebuggerFrameIndex = 8;
8248 static const int kFrameDetailsFirstDynamicIndex = 9;
8248 8249
8249 // Return an array with frame details 8250 // Return an array with frame details
8250 // args[0]: number: break id 8251 // args[0]: number: break id
8251 // args[1]: number: frame index 8252 // args[1]: number: frame index
8252 // 8253 //
8253 // The array returned contains the following information: 8254 // The array returned contains the following information:
8254 // 0: Frame id 8255 // 0: Frame id
8255 // 1: Receiver 8256 // 1: Receiver
8256 // 2: Function 8257 // 2: Function
8257 // 3: Argument count 8258 // 3: Argument count
8258 // 4: Local count 8259 // 4: Local count
8259 // 5: Source position 8260 // 5: Source position
8260 // 6: Constructor call 8261 // 6: Constructor call
8261 // 7: Debugger frame 8262 // 7: Is at return
8263 // 8: Debugger frame
8262 // Arguments name, value 8264 // Arguments name, value
8263 // Locals name, value 8265 // Locals name, value
8266 // Return value if any
8264 static Object* Runtime_GetFrameDetails(Arguments args) { 8267 static Object* Runtime_GetFrameDetails(Arguments args) {
8265 HandleScope scope; 8268 HandleScope scope;
8266 ASSERT(args.length() == 2); 8269 ASSERT(args.length() == 2);
8267 8270
8268 // Check arguments. 8271 // Check arguments.
8269 Object* check = Runtime_CheckExecutionState(args); 8272 Object* check = Runtime_CheckExecutionState(args);
8270 if (check->IsFailure()) return check; 8273 if (check->IsFailure()) return check;
8271 CONVERT_NUMBER_CHECKED(int, index, Int32, args[1]); 8274 CONVERT_NUMBER_CHECKED(int, index, Int32, args[1]);
8272 8275
8273 // Find the relevant frame with the requested index. 8276 // Find the relevant frame with the requested index.
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
8329 while (!context->is_function_context()) { 8332 while (!context->is_function_context()) {
8330 context = Handle<Context>(context->previous()); 8333 context = Handle<Context>(context->previous());
8331 } 8334 }
8332 ASSERT(context->is_function_context()); 8335 ASSERT(context->is_function_context());
8333 locals->set(i * 2 + 1, 8336 locals->set(i * 2 + 1,
8334 context->get(ScopeInfo<>::ContextSlotIndex(*code, *name, 8337 context->get(ScopeInfo<>::ContextSlotIndex(*code, *name,
8335 NULL))); 8338 NULL)));
8336 } 8339 }
8337 } 8340 }
8338 8341
8339 // Now advance to the arguments adapter frame (if any). If contains all 8342 // Check whether this frame is positioned at return.
8340 // the provided parameters and 8343 int at_return = (index == 0) ? Debug::IsBreakAtReturn(it.frame()) : false;
8344
8345 // If positioned just before return find the value to be returned and add it
8346 // to the frame information.
8347 Handle<Object> return_value = Factory::undefined_value();
8348 if (at_return) {
8349 StackFrameIterator it2;
8350 Address internal_frame_sp = NULL;
8351 while (!it2.done()) {
8352 if (it2.frame()->is_internal()) {
8353 internal_frame_sp = it2.frame()->sp();
8354 } else {
8355 if (it2.frame()->is_java_script()) {
8356 if (it2.frame()->id() == it.frame()->id()) {
8357 // The internal frame just before the JavaScript frame contains the
8358 // value to return on top. A debug break at return will create an
8359 // internal frame to store the return value (eax/rax/r0) before
8360 // entering the debug break exit frame.
8361 if (internal_frame_sp != NULL) {
8362 return_value =
8363 Handle<Object>(Memory::Object_at(internal_frame_sp));
8364 break;
8365 }
8366 }
8367 }
8368
8369 // Indicate that the previous frame was not an internal frame.
8370 internal_frame_sp = NULL;
8371 }
8372 it2.Advance();
8373 }
8374 }
8341 8375
8342 // Now advance to the arguments adapter frame (if any). It contains all 8376 // Now advance to the arguments adapter frame (if any). It contains all
8343 // the provided parameters whereas the function frame always have the number 8377 // the provided parameters whereas the function frame always have the number
8344 // of arguments matching the functions parameters. The rest of the 8378 // of arguments matching the functions parameters. The rest of the
8345 // information (except for what is collected above) is the same. 8379 // information (except for what is collected above) is the same.
8346 it.AdvanceToArgumentsFrame(); 8380 it.AdvanceToArgumentsFrame();
8347 8381
8348 // Find the number of arguments to fill. At least fill the number of 8382 // Find the number of arguments to fill. At least fill the number of
8349 // parameters for the function and fill more if more parameters are provided. 8383 // parameters for the function and fill more if more parameters are provided.
8350 int argument_count = info.number_of_parameters(); 8384 int argument_count = info.number_of_parameters();
8351 if (argument_count < it.frame()->GetProvidedParametersCount()) { 8385 if (argument_count < it.frame()->GetProvidedParametersCount()) {
8352 argument_count = it.frame()->GetProvidedParametersCount(); 8386 argument_count = it.frame()->GetProvidedParametersCount();
8353 } 8387 }
8354 8388
8355 // Calculate the size of the result. 8389 // Calculate the size of the result.
8356 int details_size = kFrameDetailsFirstDynamicIndex + 8390 int details_size = kFrameDetailsFirstDynamicIndex +
8357 2 * (argument_count + info.NumberOfLocals()); 8391 2 * (argument_count + info.NumberOfLocals()) +
8392 (at_return ? 1 : 0);
8358 Handle<FixedArray> details = Factory::NewFixedArray(details_size); 8393 Handle<FixedArray> details = Factory::NewFixedArray(details_size);
8359 8394
8360 // Add the frame id. 8395 // Add the frame id.
8361 details->set(kFrameDetailsFrameIdIndex, *frame_id); 8396 details->set(kFrameDetailsFrameIdIndex, *frame_id);
8362 8397
8363 // Add the function (same as in function frame). 8398 // Add the function (same as in function frame).
8364 details->set(kFrameDetailsFunctionIndex, it.frame()->function()); 8399 details->set(kFrameDetailsFunctionIndex, it.frame()->function());
8365 8400
8366 // Add the arguments count. 8401 // Add the arguments count.
8367 details->set(kFrameDetailsArgumentCountIndex, Smi::FromInt(argument_count)); 8402 details->set(kFrameDetailsArgumentCountIndex, Smi::FromInt(argument_count));
8368 8403
8369 // Add the locals count 8404 // Add the locals count
8370 details->set(kFrameDetailsLocalCountIndex, 8405 details->set(kFrameDetailsLocalCountIndex,
8371 Smi::FromInt(info.NumberOfLocals())); 8406 Smi::FromInt(info.NumberOfLocals()));
8372 8407
8373 // Add the source position. 8408 // Add the source position.
8374 if (position != RelocInfo::kNoPosition) { 8409 if (position != RelocInfo::kNoPosition) {
8375 details->set(kFrameDetailsSourcePositionIndex, Smi::FromInt(position)); 8410 details->set(kFrameDetailsSourcePositionIndex, Smi::FromInt(position));
8376 } else { 8411 } else {
8377 details->set(kFrameDetailsSourcePositionIndex, Heap::undefined_value()); 8412 details->set(kFrameDetailsSourcePositionIndex, Heap::undefined_value());
8378 } 8413 }
8379 8414
8380 // Add the constructor information. 8415 // Add the constructor information.
8381 details->set(kFrameDetailsConstructCallIndex, Heap::ToBoolean(constructor)); 8416 details->set(kFrameDetailsConstructCallIndex, Heap::ToBoolean(constructor));
8382 8417
8418 // Add the at return information.
8419 details->set(kFrameDetailsAtReturnIndex, Heap::ToBoolean(at_return));
8420
8383 // Add information on whether this frame is invoked in the debugger context. 8421 // Add information on whether this frame is invoked in the debugger context.
8384 details->set(kFrameDetailsDebuggerFrameIndex, 8422 details->set(kFrameDetailsDebuggerFrameIndex,
8385 Heap::ToBoolean(*save->context() == *Debug::debug_context())); 8423 Heap::ToBoolean(*save->context() == *Debug::debug_context()));
8386 8424
8387 // Fill the dynamic part. 8425 // Fill the dynamic part.
8388 int details_index = kFrameDetailsFirstDynamicIndex; 8426 int details_index = kFrameDetailsFirstDynamicIndex;
8389 8427
8390 // Add arguments name and value. 8428 // Add arguments name and value.
8391 for (int i = 0; i < argument_count; i++) { 8429 for (int i = 0; i < argument_count; i++) {
8392 // Name of the argument. 8430 // Name of the argument.
8393 if (i < info.number_of_parameters()) { 8431 if (i < info.number_of_parameters()) {
8394 details->set(details_index++, *info.parameter_name(i)); 8432 details->set(details_index++, *info.parameter_name(i));
8395 } else { 8433 } else {
8396 details->set(details_index++, Heap::undefined_value()); 8434 details->set(details_index++, Heap::undefined_value());
8397 } 8435 }
8398 8436
8399 // Parameter value. 8437 // Parameter value.
8400 if (i < it.frame()->GetProvidedParametersCount()) { 8438 if (i < it.frame()->GetProvidedParametersCount()) {
8401 details->set(details_index++, it.frame()->GetParameter(i)); 8439 details->set(details_index++, it.frame()->GetParameter(i));
8402 } else { 8440 } else {
8403 details->set(details_index++, Heap::undefined_value()); 8441 details->set(details_index++, Heap::undefined_value());
8404 } 8442 }
8405 } 8443 }
8406 8444
8407 // Add locals name and value from the temporary copy from the function frame. 8445 // Add locals name and value from the temporary copy from the function frame.
8408 for (int i = 0; i < info.NumberOfLocals() * 2; i++) { 8446 for (int i = 0; i < info.NumberOfLocals() * 2; i++) {
8409 details->set(details_index++, locals->get(i)); 8447 details->set(details_index++, locals->get(i));
8410 } 8448 }
8411 8449
8450 // Add the value being returned.
8451 if (at_return) {
8452 details->set(details_index++, *return_value);
8453 }
8454
8412 // Add the receiver (same as in function frame). 8455 // Add the receiver (same as in function frame).
8413 // THIS MUST BE DONE LAST SINCE WE MIGHT ADVANCE 8456 // THIS MUST BE DONE LAST SINCE WE MIGHT ADVANCE
8414 // THE FRAME ITERATOR TO WRAP THE RECEIVER. 8457 // THE FRAME ITERATOR TO WRAP THE RECEIVER.
8415 Handle<Object> receiver(it.frame()->receiver()); 8458 Handle<Object> receiver(it.frame()->receiver());
8416 if (!receiver->IsJSObject()) { 8459 if (!receiver->IsJSObject()) {
8417 // If the receiver is NOT a JSObject we have hit an optimization 8460 // If the receiver is NOT a JSObject we have hit an optimization
8418 // where a value object is not converted into a wrapped JS objects. 8461 // where a value object is not converted into a wrapped JS objects.
8419 // To hide this optimization from the debugger, we wrap the receiver 8462 // To hide this optimization from the debugger, we wrap the receiver
8420 // by creating correct wrapper object based on the calling frame's 8463 // by creating correct wrapper object based on the calling frame's
8421 // global context. 8464 // global context.
(...skipping 1907 matching lines...) Expand 10 before | Expand all | Expand 10 after
10329 } else { 10372 } else {
10330 // Handle last resort GC and make sure to allow future allocations 10373 // Handle last resort GC and make sure to allow future allocations
10331 // to grow the heap without causing GCs (if possible). 10374 // to grow the heap without causing GCs (if possible).
10332 Counters::gc_last_resort_from_js.Increment(); 10375 Counters::gc_last_resort_from_js.Increment();
10333 Heap::CollectAllGarbage(false); 10376 Heap::CollectAllGarbage(false);
10334 } 10377 }
10335 } 10378 }
10336 10379
10337 10380
10338 } } // namespace v8::internal 10381 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/mirror-debugger.js ('k') | src/x64/full-codegen-x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698