OLD | NEW |
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 Loading... |
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 Loading... |
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 Loading... |
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 |
OLD | NEW |