Reviewers: Yang,

Message:
Yang, I'm sorry to keep picking you as a reviewer but according to `git shortlog
-ns src/api.cc`, you're the most prolific contributor by a wide margin. :-)

Description:
Add v8::Object::GetRealNamedPropertyAttributes()

Add v8::Object::GetRealNamedPropertyAttributes() and
v8::Object::GetRealNamedPropertyAttributesInPrototypeChain().

See https://github.com/iojs/io.js/issues/864 for background.

Please review this at https://codereview.chromium.org/942003003/

Base URL: https://chromium.googlesource.com/v8/v8.git@master

Affected files (+80, -1 lines):
  M include/v8.h
  M src/api.cc
  M test/cctest/test-api.cc


Index: include/v8.h
diff --git a/include/v8.h b/include/v8.h
index fa32ba3cdfb3cf77c803da527e480832230c591b..3229da106a4db4a1df5bd85c6fcea3bae0aef20a 100644
--- a/include/v8.h
+++ b/include/v8.h
@@ -2617,12 +2617,27 @@ class V8_EXPORT Object : public Value {
   Local<Value> GetRealNamedPropertyInPrototypeChain(Handle<String> key);

   /**
+ * Gets the property attributes of a real property in the prototype chain, + * which can be None or any combination of ReadOnly, DontEnum and DontDelete.
+   * Interceptors in the prototype chain are not called.
+   */
+  Maybe<PropertyAttribute> GetRealNamedPropertyAttributesInPrototypeChain(
+      Handle<String> key);
+
+  /**
    * If result.IsEmpty() no real property was located on the object or
    * in the prototype chain.
    * This means interceptors in the prototype chain are not called.
    */
   Local<Value> GetRealNamedProperty(Handle<String> key);

+  /**
+   * Gets the property attributes of a real property which can be
+   * None or any combination of ReadOnly, DontEnum and DontDelete.
+   * Interceptors in the prototype chain are not called.
+   */
+ Maybe<PropertyAttribute> GetRealNamedPropertyAttributes(Handle<String> key);
+
   /** Tests for a named lookup interceptor.*/
   bool HasNamedLookupInterceptor();

Index: src/api.cc
diff --git a/src/api.cc b/src/api.cc
index 6e19af4ed5c19c7a0fadb34d2f82451f8ad64efb..cc3a2882f95ba54a8f4b500fcd9a484bb65948cb 100644
--- a/src/api.cc
+++ b/src/api.cc
@@ -3757,6 +3757,14 @@ static Local<Value> GetPropertyByLookup(i::LookupIterator* it) {
 }


+static Maybe<PropertyAttribute> GetPropertyAttributesByLookup(
+    i::LookupIterator* it) {
+ Maybe<PropertyAttributes> attr = i::JSReceiver::GetPropertyAttributes(it);
+  if (!it->IsFound()) return Maybe<PropertyAttribute>();
+ return Maybe<PropertyAttribute>(static_cast<PropertyAttribute>(attr.value));
+}
+
+
 Local<Value> v8::Object::GetRealNamedPropertyInPrototypeChain(
     Handle<String> key) {
   i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
@@ -3775,6 +3783,24 @@ Local<Value> v8::Object::GetRealNamedPropertyInPrototypeChain(
 }


+Maybe<PropertyAttribute>
+v8::Object::GetRealNamedPropertyAttributesInPrototypeChain(Handle<String> key) {
+  i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
+  ON_BAILOUT(isolate,
+             "v8::Object::GetRealNamedPropertyAttributesInPrototypeChain()",
+             return Maybe<PropertyAttribute>());
+  ENTER_V8(isolate);
+  i::Handle<i::JSObject> self_obj = Utils::OpenHandle(this);
+  i::Handle<i::String> key_obj = Utils::OpenHandle(*key);
+  i::PrototypeIterator iter(isolate, self_obj);
+  if (iter.IsAtEnd()) return Maybe<PropertyAttribute>();
+  i::Handle<i::Object> proto = i::PrototypeIterator::GetCurrent(iter);
+ i::LookupIterator it(self_obj, key_obj, i::Handle<i::JSReceiver>::cast(proto), + i::LookupIterator::PROTOTYPE_CHAIN_SKIP_INTERCEPTOR);
+  return GetPropertyAttributesByLookup(&it);
+}
+
+
 Local<Value> v8::Object::GetRealNamedProperty(Handle<String> key) {
   i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
   ON_BAILOUT(isolate, "v8::Object::GetRealNamedProperty()",
@@ -3788,6 +3814,20 @@ Local<Value> v8::Object::GetRealNamedProperty(Handle<String> key) {
 }


+Maybe<PropertyAttribute> v8::Object::GetRealNamedPropertyAttributes(
+    Handle<String> key) {
+  i::Isolate* isolate = Utils::OpenHandle(this)->GetIsolate();
+  ON_BAILOUT(isolate, "v8::Object::GetRealNamedPropertyAttributes()",
+             return Maybe<PropertyAttribute>());
+  ENTER_V8(isolate);
+  i::Handle<i::JSObject> self_obj = Utils::OpenHandle(this);
+  i::Handle<i::String> key_obj = Utils::OpenHandle(*key);
+  i::LookupIterator it(self_obj, key_obj,
+ i::LookupIterator::PROTOTYPE_CHAIN_SKIP_INTERCEPTOR);
+  return GetPropertyAttributesByLookup(&it);
+}
+
+
 // Turns on access checks by copying the map and setting the check flag.
 // Because the object gets a new map, existing inline cache caching
 // the old map of this object will fail.
Index: test/cctest/test-api.cc
diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc
index adc7c0921693934bd42eab414a7a18fa655b1835..06fe1fca9a1d7a5a9ad9989819b0f2d4aeec0c0c 100644
--- a/test/cctest/test-api.cc
+++ b/test/cctest/test-api.cc
@@ -61,12 +61,15 @@ using ::v8::FunctionTemplate;
 using ::v8::Handle;
 using ::v8::HandleScope;
 using ::v8::Local;
-using ::v8::Name;
+using ::v8::Maybe;
 using ::v8::Message;
 using ::v8::MessageCallback;
+using ::v8::Name;
+using ::v8::None;
 using ::v8::Object;
 using ::v8::ObjectTemplate;
 using ::v8::Persistent;
+using ::v8::PropertyAttribute;
 using ::v8::Script;
 using ::v8::StackTrace;
 using ::v8::String;
@@ -10869,16 +10872,32 @@ THREADED_TEST(VariousGetPropertiesAndThrowingCallbacks) {
   try_catch.Reset();
   CHECK(result.IsEmpty());

+  Maybe<PropertyAttribute> attr =
+      instance->GetRealNamedPropertyAttributes(v8_str("f"));
+  CHECK(!try_catch.HasCaught());
+  CHECK(attr.has_value);
+  CHECK_EQ(attr.value, None);
+
   result = another->GetRealNamedProperty(v8_str("f"));
   CHECK(try_catch.HasCaught());
   try_catch.Reset();
   CHECK(result.IsEmpty());

+  attr = another->GetRealNamedPropertyAttributes(v8_str("f"));
+  CHECK(!try_catch.HasCaught());
+  CHECK(attr.has_value);
+  CHECK_EQ(attr.value, None);
+
   result = another->GetRealNamedPropertyInPrototypeChain(v8_str("f"));
   CHECK(try_catch.HasCaught());
   try_catch.Reset();
   CHECK(result.IsEmpty());

+ attr = another->GetRealNamedPropertyAttributesInPrototypeChain(v8_str("f"));
+  CHECK(!try_catch.HasCaught());
+  CHECK(attr.has_value);
+  CHECK_EQ(attr.value, None);
+
   result = another->Get(v8_str("f"));
   CHECK(try_catch.HasCaught());
   try_catch.Reset();
@@ -10889,6 +10908,11 @@ THREADED_TEST(VariousGetPropertiesAndThrowingCallbacks) {
   try_catch.Reset();
   CHECK(result.IsEmpty());

+  attr = with_js_getter->GetRealNamedPropertyAttributes(v8_str("f"));
+  CHECK(!try_catch.HasCaught());
+  CHECK(attr.has_value);
+  CHECK_EQ(attr.value, None);
+
   result = with_js_getter->Get(v8_str("f"));
   CHECK(try_catch.HasCaught());
   try_catch.Reset();


--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
--- You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to