| Index: src/runtime.cc
|
| ===================================================================
|
| --- src/runtime.cc (revision 1052)
|
| +++ src/runtime.cc (working copy)
|
| @@ -4503,30 +4503,32 @@
|
| }
|
|
|
|
|
| -static Object* DebugLookupResultValue(LookupResult* result) {
|
| - Object* value;
|
| +static Object* DebugLookupResultValue(Object* obj, String* name,
|
| + LookupResult* result,
|
| + bool* caught_exception) {
|
| switch (result->type()) {
|
| - case NORMAL: {
|
| - Dictionary* dict =
|
| - JSObject::cast(result->holder())->property_dictionary();
|
| - value = dict->ValueAt(result->GetDictionaryEntry());
|
| - if (value->IsTheHole()) {
|
| - return Heap::undefined_value();
|
| + case NORMAL:
|
| + case FIELD:
|
| + case CONSTANT_FUNCTION:
|
| + return obj->GetProperty(name);
|
| + case CALLBACKS: {
|
| + // Get the property value. If there is an exception it must be thown from
|
| + // a JavaScript getter.
|
| + Object* value;
|
| + value = obj->GetProperty(name);
|
| + if (value->IsException()) {
|
| + if (caught_exception != NULL) {
|
| + *caught_exception = true;
|
| + }
|
| + value = Top::pending_exception();
|
| + Top::optional_reschedule_exception(true);
|
| }
|
| + ASSERT(!Top::has_pending_exception());
|
| + ASSERT(!Top::external_caught_exception());
|
| return value;
|
| }
|
| - case FIELD:
|
| - value =
|
| - JSObject::cast(
|
| - result->holder())->FastPropertyAt(result->GetFieldIndex());
|
| - if (value->IsTheHole()) {
|
| - return Heap::undefined_value();
|
| - }
|
| - return value;
|
| - case CONSTANT_FUNCTION:
|
| - return result->GetConstantFunction();
|
| - case CALLBACKS:
|
| case INTERCEPTOR:
|
| + return obj->GetProperty(name);
|
| case MAP_TRANSITION:
|
| case CONSTANT_TRANSITION:
|
| case NULL_DESCRIPTOR:
|
| @@ -4539,6 +4541,18 @@
|
| }
|
|
|
|
|
| +// Get debugger related details for an object property.
|
| +// args[0]: object holding property
|
| +// args[1]: name of the property
|
| +//
|
| +// The array returned contains the following information:
|
| +// 0: Property value
|
| +// 1: Property details
|
| +// 2: Property value is exception
|
| +// 3: Getter function if defined
|
| +// 4: Setter function if defined
|
| +// Items 2-4 are only filled if the property has either a getter or a setter
|
| +// defined through __defineGetter__ and/or __defineSetter__.
|
| static Object* Runtime_DebugGetPropertyDetails(Arguments args) {
|
| HandleScope scope;
|
|
|
| @@ -4559,12 +4573,26 @@
|
|
|
| // Perform standard local lookup on the object.
|
| LookupResult result;
|
| - obj->Lookup(*name, &result);
|
| + obj->LocalLookup(*name, &result);
|
| if (result.IsProperty()) {
|
| - Handle<Object> value(DebugLookupResultValue(&result));
|
| - Handle<FixedArray> details = Factory::NewFixedArray(2);
|
| + bool caught_exception = false;
|
| + Handle<Object> value(DebugLookupResultValue(*obj, *name, &result,
|
| + &caught_exception));
|
| + // If the callback object is a fixed array then it contains JavaScript
|
| + // getter and/or setter.
|
| + bool hasJavaScriptAccessors = result.type() == CALLBACKS &&
|
| + result.GetCallbackObject()->IsFixedArray();
|
| + Handle<FixedArray> details =
|
| + Factory::NewFixedArray(hasJavaScriptAccessors ? 5 : 2);
|
| details->set(0, *value);
|
| details->set(1, result.GetPropertyDetails().AsSmi());
|
| + if (hasJavaScriptAccessors) {
|
| + details->set(2,
|
| + caught_exception ? Heap::true_value() : Heap::false_value());
|
| + details->set(3, FixedArray::cast(result.GetCallbackObject())->get(0));
|
| + details->set(4, FixedArray::cast(result.GetCallbackObject())->get(1));
|
| + }
|
| +
|
| return *Factory::NewJSArrayWithElements(details);
|
| }
|
| return Heap::undefined_value();
|
| @@ -4582,7 +4610,7 @@
|
| LookupResult result;
|
| obj->Lookup(*name, &result);
|
| if (result.IsProperty()) {
|
| - return DebugLookupResultValue(&result);
|
| + return DebugLookupResultValue(*obj, *name, &result, NULL);
|
| }
|
| return Heap::undefined_value();
|
| }
|
| @@ -4676,10 +4704,11 @@
|
| HandleScope scope;
|
| ASSERT(args.length() == 1);
|
| CONVERT_ARG_CHECKED(JSObject, obj, 0);
|
| - RUNTIME_ASSERT(obj->HasNamedInterceptor());
|
|
|
| - v8::Handle<v8::Array> result = GetKeysForNamedInterceptor(obj, obj);
|
| - if (!result.IsEmpty()) return *v8::Utils::OpenHandle(*result);
|
| + if (obj->HasNamedInterceptor()) {
|
| + v8::Handle<v8::Array> result = GetKeysForNamedInterceptor(obj, obj);
|
| + if (!result.IsEmpty()) return *v8::Utils::OpenHandle(*result);
|
| + }
|
| return Heap::undefined_value();
|
| }
|
|
|
| @@ -4690,10 +4719,11 @@
|
| HandleScope scope;
|
| ASSERT(args.length() == 1);
|
| CONVERT_ARG_CHECKED(JSObject, obj, 0);
|
| - RUNTIME_ASSERT(obj->HasIndexedInterceptor());
|
|
|
| - v8::Handle<v8::Array> result = GetKeysForIndexedInterceptor(obj, obj);
|
| - if (!result.IsEmpty()) return *v8::Utils::OpenHandle(*result);
|
| + if (obj->HasIndexedInterceptor()) {
|
| + v8::Handle<v8::Array> result = GetKeysForIndexedInterceptor(obj, obj);
|
| + if (!result.IsEmpty()) return *v8::Utils::OpenHandle(*result);
|
| + }
|
| return Heap::undefined_value();
|
| }
|
|
|
|
|