OLD | NEW |
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 4518 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4529 } | 4529 } |
4530 | 4530 |
4531 | 4531 |
4532 static Object* Runtime_Break(Arguments args) { | 4532 static Object* Runtime_Break(Arguments args) { |
4533 ASSERT(args.length() == 0); | 4533 ASSERT(args.length() == 0); |
4534 StackGuard::DebugBreak(); | 4534 StackGuard::DebugBreak(); |
4535 return Heap::undefined_value(); | 4535 return Heap::undefined_value(); |
4536 } | 4536 } |
4537 | 4537 |
4538 | 4538 |
| 4539 // Find the length of the prototype chain that is to to handled as one. If a |
| 4540 // prototype object is hidden it is to be viewed as part of the the object it |
| 4541 // is prototype for. |
| 4542 static int LocalPrototypeChainLength(JSObject* obj) { |
| 4543 int count = 1; |
| 4544 Object* proto = obj->GetPrototype(); |
| 4545 while (proto->IsJSObject() && |
| 4546 JSObject::cast(proto)->map()->is_hidden_prototype()) { |
| 4547 count++; |
| 4548 proto = JSObject::cast(proto)->GetPrototype(); |
| 4549 } |
| 4550 return count; |
| 4551 } |
| 4552 |
| 4553 |
4539 static Object* DebugLookupResultValue(Object* receiver, LookupResult* result, | 4554 static Object* DebugLookupResultValue(Object* receiver, LookupResult* result, |
4540 bool* caught_exception) { | 4555 bool* caught_exception) { |
4541 Object* value; | 4556 Object* value; |
4542 switch (result->type()) { | 4557 switch (result->type()) { |
4543 case NORMAL: { | 4558 case NORMAL: { |
4544 Dictionary* dict = | 4559 Dictionary* dict = |
4545 JSObject::cast(result->holder())->property_dictionary(); | 4560 JSObject::cast(result->holder())->property_dictionary(); |
4546 value = dict->ValueAt(result->GetDictionaryEntry()); | 4561 value = dict->ValueAt(result->GetDictionaryEntry()); |
4547 if (value->IsTheHole()) { | 4562 if (value->IsTheHole()) { |
4548 return Heap::undefined_value(); | 4563 return Heap::undefined_value(); |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4604 // Items 2-4 are only filled if the property has either a getter or a setter | 4619 // Items 2-4 are only filled if the property has either a getter or a setter |
4605 // defined through __defineGetter__ and/or __defineSetter__. | 4620 // defined through __defineGetter__ and/or __defineSetter__. |
4606 static Object* Runtime_DebugGetPropertyDetails(Arguments args) { | 4621 static Object* Runtime_DebugGetPropertyDetails(Arguments args) { |
4607 HandleScope scope; | 4622 HandleScope scope; |
4608 | 4623 |
4609 ASSERT(args.length() == 2); | 4624 ASSERT(args.length() == 2); |
4610 | 4625 |
4611 CONVERT_ARG_CHECKED(JSObject, obj, 0); | 4626 CONVERT_ARG_CHECKED(JSObject, obj, 0); |
4612 CONVERT_ARG_CHECKED(String, name, 1); | 4627 CONVERT_ARG_CHECKED(String, name, 1); |
4613 | 4628 |
| 4629 // Skip the global proxy as it has no properties and always delegates to the |
| 4630 // real global object. |
| 4631 if (obj->IsJSGlobalProxy()) { |
| 4632 obj = Handle<JSObject>(JSObject::cast(obj->GetPrototype())); |
| 4633 } |
| 4634 |
| 4635 |
4614 // Check if the name is trivially convertible to an index and get the element | 4636 // Check if the name is trivially convertible to an index and get the element |
4615 // if so. | 4637 // if so. |
4616 uint32_t index; | 4638 uint32_t index; |
4617 if (name->AsArrayIndex(&index)) { | 4639 if (name->AsArrayIndex(&index)) { |
4618 Handle<FixedArray> details = Factory::NewFixedArray(2); | 4640 Handle<FixedArray> details = Factory::NewFixedArray(2); |
4619 details->set(0, Runtime::GetElementOrCharAt(obj, index)); | 4641 details->set(0, Runtime::GetElementOrCharAt(obj, index)); |
4620 details->set(1, PropertyDetails(NONE, NORMAL).AsSmi()); | 4642 details->set(1, PropertyDetails(NONE, NORMAL).AsSmi()); |
4621 return *Factory::NewJSArrayWithElements(details); | 4643 return *Factory::NewJSArrayWithElements(details); |
4622 } | 4644 } |
4623 | 4645 |
4624 // Perform standard local lookup on the object. | 4646 // Find the number of objects making up this. |
| 4647 int length = LocalPrototypeChainLength(*obj); |
| 4648 |
| 4649 // Try local lookup on each of the objects. |
4625 LookupResult result; | 4650 LookupResult result; |
4626 obj->LocalLookup(*name, &result); | 4651 Handle<JSObject> jsproto = obj; |
| 4652 for (int i = 0; i < length; i++) { |
| 4653 jsproto->LocalLookup(*name, &result); |
| 4654 if (result.IsProperty()) { |
| 4655 break; |
| 4656 } |
| 4657 if (i < length - 1) { |
| 4658 jsproto = Handle<JSObject>(JSObject::cast(jsproto->GetPrototype())); |
| 4659 } |
| 4660 } |
| 4661 |
4627 if (result.IsProperty()) { | 4662 if (result.IsProperty()) { |
4628 bool caught_exception = false; | 4663 bool caught_exception = false; |
4629 Handle<Object> value(DebugLookupResultValue(*obj, &result, | 4664 Handle<Object> value(DebugLookupResultValue(*obj, &result, |
4630 &caught_exception)); | 4665 &caught_exception)); |
4631 // If the callback object is a fixed array then it contains JavaScript | 4666 // If the callback object is a fixed array then it contains JavaScript |
4632 // getter and/or setter. | 4667 // getter and/or setter. |
4633 bool hasJavaScriptAccessors = result.type() == CALLBACKS && | 4668 bool hasJavaScriptAccessors = result.type() == CALLBACKS && |
4634 result.GetCallbackObject()->IsFixedArray(); | 4669 result.GetCallbackObject()->IsFixedArray(); |
4635 Handle<FixedArray> details = | 4670 Handle<FixedArray> details = |
4636 Factory::NewFixedArray(hasJavaScriptAccessors ? 5 : 2); | 4671 Factory::NewFixedArray(hasJavaScriptAccessors ? 5 : 2); |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4669 // Return the names of the local named properties. | 4704 // Return the names of the local named properties. |
4670 // args[0]: object | 4705 // args[0]: object |
4671 static Object* Runtime_DebugLocalPropertyNames(Arguments args) { | 4706 static Object* Runtime_DebugLocalPropertyNames(Arguments args) { |
4672 HandleScope scope; | 4707 HandleScope scope; |
4673 ASSERT(args.length() == 1); | 4708 ASSERT(args.length() == 1); |
4674 if (!args[0]->IsJSObject()) { | 4709 if (!args[0]->IsJSObject()) { |
4675 return Heap::undefined_value(); | 4710 return Heap::undefined_value(); |
4676 } | 4711 } |
4677 CONVERT_ARG_CHECKED(JSObject, obj, 0); | 4712 CONVERT_ARG_CHECKED(JSObject, obj, 0); |
4678 | 4713 |
| 4714 // Skip the global proxy as it has no properties and always delegates to the |
| 4715 // real global object. |
4679 if (obj->IsJSGlobalProxy()) { | 4716 if (obj->IsJSGlobalProxy()) { |
4680 obj = Handle<JSObject>(JSObject::cast(obj->GetPrototype())); | 4717 obj = Handle<JSObject>(JSObject::cast(obj->GetPrototype())); |
4681 } | 4718 } |
4682 int n = obj->NumberOfLocalProperties(static_cast<PropertyAttributes>(NONE)); | 4719 |
4683 Handle<FixedArray> names = Factory::NewFixedArray(n); | 4720 // Find the number of objects making up this. |
4684 obj->GetLocalPropertyNames(*names); | 4721 int length = LocalPrototypeChainLength(*obj); |
| 4722 |
| 4723 // Find the number of local properties for each of the objects. |
| 4724 int* local_property_count = NewArray<int>(length); |
| 4725 int total_property_count = 0; |
| 4726 Handle<JSObject> jsproto = obj; |
| 4727 for (int i = 0; i < length; i++) { |
| 4728 int n; |
| 4729 n = jsproto->NumberOfLocalProperties(static_cast<PropertyAttributes>(NONE)); |
| 4730 local_property_count[i] = n; |
| 4731 total_property_count += n; |
| 4732 if (i < length - 1) { |
| 4733 jsproto = Handle<JSObject>(JSObject::cast(jsproto->GetPrototype())); |
| 4734 } |
| 4735 } |
| 4736 |
| 4737 // Allocate an array with storage for all the property names. |
| 4738 Handle<FixedArray> names = Factory::NewFixedArray(total_property_count); |
| 4739 |
| 4740 // Get the property names. |
| 4741 jsproto = obj; |
| 4742 for (int i = 0; i < length; i++) { |
| 4743 jsproto->GetLocalPropertyNames(*names, |
| 4744 i == 0 ? 0 : local_property_count[i - 1]); |
| 4745 if (i < length - 1) { |
| 4746 jsproto = Handle<JSObject>(JSObject::cast(jsproto->GetPrototype())); |
| 4747 } |
| 4748 } |
| 4749 |
| 4750 DeleteArray(local_property_count); |
4685 return *Factory::NewJSArrayWithElements(names); | 4751 return *Factory::NewJSArrayWithElements(names); |
4686 } | 4752 } |
4687 | 4753 |
4688 | 4754 |
4689 // Return the names of the local indexed properties. | 4755 // Return the names of the local indexed properties. |
4690 // args[0]: object | 4756 // args[0]: object |
4691 static Object* Runtime_DebugLocalElementNames(Arguments args) { | 4757 static Object* Runtime_DebugLocalElementNames(Arguments args) { |
4692 HandleScope scope; | 4758 HandleScope scope; |
4693 ASSERT(args.length() == 1); | 4759 ASSERT(args.length() == 1); |
4694 if (!args[0]->IsJSObject()) { | 4760 if (!args[0]->IsJSObject()) { |
(...skipping 1107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5802 | 5868 |
5803 // Return result as JS array. | 5869 // Return result as JS array. |
5804 Object* result = | 5870 Object* result = |
5805 Heap::AllocateJSObject( | 5871 Heap::AllocateJSObject( |
5806 Top::context()->global_context()->array_function()); | 5872 Top::context()->global_context()->array_function()); |
5807 if (!result->IsFailure()) JSArray::cast(result)->SetContent(instances); | 5873 if (!result->IsFailure()) JSArray::cast(result)->SetContent(instances); |
5808 return result; | 5874 return result; |
5809 } | 5875 } |
5810 | 5876 |
5811 | 5877 |
5812 static Object* Runtime_GetPrototype(Arguments args) { | 5878 // Find the effective prototype object as returned by __proto__. |
| 5879 // args[0]: the object to find the prototype for. |
| 5880 static Object* Runtime_DebugGetPrototype(Arguments args) { |
5813 ASSERT(args.length() == 1); | 5881 ASSERT(args.length() == 1); |
5814 | 5882 |
5815 CONVERT_CHECKED(JSObject, obj, args[0]); | 5883 CONVERT_CHECKED(JSObject, obj, args[0]); |
5816 | 5884 |
5817 return obj->GetPrototype(); | 5885 // Use the __proto__ accessor. |
| 5886 return Accessors::ObjectPrototype.getter(obj, NULL); |
5818 } | 5887 } |
5819 | 5888 |
5820 | 5889 |
5821 static Object* Runtime_SystemBreak(Arguments args) { | 5890 static Object* Runtime_SystemBreak(Arguments args) { |
5822 ASSERT(args.length() == 0); | 5891 ASSERT(args.length() == 0); |
5823 CPU::DebugBreak(); | 5892 CPU::DebugBreak(); |
5824 return Heap::undefined_value(); | 5893 return Heap::undefined_value(); |
5825 } | 5894 } |
5826 | 5895 |
5827 | 5896 |
(...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5981 } else { | 6050 } else { |
5982 // Handle last resort GC and make sure to allow future allocations | 6051 // Handle last resort GC and make sure to allow future allocations |
5983 // to grow the heap without causing GCs (if possible). | 6052 // to grow the heap without causing GCs (if possible). |
5984 Counters::gc_last_resort_from_js.Increment(); | 6053 Counters::gc_last_resort_from_js.Increment(); |
5985 Heap::CollectAllGarbage(); | 6054 Heap::CollectAllGarbage(); |
5986 } | 6055 } |
5987 } | 6056 } |
5988 | 6057 |
5989 | 6058 |
5990 } } // namespace v8::internal | 6059 } } // namespace v8::internal |
OLD | NEW |