Add checks for interceptors to negative lookup code in Crankshaft.
authorerik.corry@gmail.com <erik.corry@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Tue, 7 Aug 2012 14:48:19 +0000 (14:48 +0000)
committererik.corry@gmail.com <erik.corry@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Tue, 7 Aug 2012 14:48:19 +0000 (14:48 +0000)
BUG=140473
Review URL: https://chromiumcodereview.appspot.com/10837141

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@12271 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

src/hydrogen-instructions.cc
test/cctest/test-api.cc

index 353d94b..67ee5bd 100644 (file)
@@ -1714,6 +1714,7 @@ static bool PrototypeChainCanNeverResolve(
     if (current->IsJSGlobalProxy() ||
         current->IsGlobalObject() ||
         !current->IsJSObject() ||
+        JSObject::cast(current)->map()->has_named_interceptor() ||
         JSObject::cast(current)->IsAccessCheckNeeded() ||
         !JSObject::cast(current)->HasFastProperties()) {
       return false;
@@ -1779,6 +1780,7 @@ HLoadNamedFieldPolymorphic::HLoadNamedFieldPolymorphic(HValue* context,
                // contain the property so we cannot generate a negative lookup
                // (which would just be a map check and return undefined).
                !map->is_dictionary_map() &&
+               !map->has_named_interceptor() &&
                PrototypeChainCanNeverResolve(map, name)) {
       negative_lookups.Add(types->at(i), zone);
     }
index 1aad006..a6046a8 100644 (file)
@@ -14737,6 +14737,22 @@ static void SetterWhichSetsYOnThisTo23(Local<String> name,
 }
 
 
+Handle<Value> FooGetInterceptor(Local<String> name,
+                                const AccessorInfo& info) {
+  if (!name->Equals(v8_str("foo"))) return Handle<Value>();
+  return v8_num(42);
+}
+
+
+Handle<Value> FooSetInterceptor(Local<String> name,
+                                Local<Value> value,
+                                const AccessorInfo& info) {
+  if (!name->Equals(v8_str("foo"))) return Handle<Value>();
+  info.This()->Set(v8_str("y"), v8_num(23));
+  return v8_num(23);
+}
+
+
 TEST(SetterOnConstructorPrototype) {
   v8::HandleScope scope;
   Local<ObjectTemplate> templ = ObjectTemplate::New();
@@ -16975,12 +16991,17 @@ TEST(TryFinallyMessage) {
 
 static void Helper137002(bool do_store,
                          bool polymorphic,
-                         bool remove_accessor) {
+                         bool remove_accessor,
+                         bool interceptor) {
   LocalContext context;
   Local<ObjectTemplate> templ = ObjectTemplate::New();
-  templ->SetAccessor(v8_str("foo"),
-                     GetterWhichReturns42,
-                     SetterWhichSetsYOnThisTo23);
+  if (interceptor) {
+    templ->SetNamedPropertyHandler(FooGetInterceptor, FooSetInterceptor);
+  } else {
+    templ->SetAccessor(v8_str("foo"),
+                       GetterWhichReturns42,
+                       SetterWhichSetsYOnThisTo23);
+  }
   context->Global()->Set(v8_str("obj"), templ->NewInstance());
 
   // Turn monomorphic on slow object with native accessor, then turn
@@ -16988,10 +17009,12 @@ static void Helper137002(bool do_store,
   CompileRun(do_store ?
              "function f(x) { x.foo = void 0; }" :
              "function f(x) { return x.foo; }");
-  CompileRun("obj.y = void 0;"
-             "%OptimizeObjectForAddingMultipleProperties(obj, 1);"
-             "obj.__proto__ = null;"
-             "f(obj); f(obj);");
+  CompileRun("obj.y = void 0;");
+  if (!interceptor) {
+    CompileRun("%OptimizeObjectForAddingMultipleProperties(obj, 1);");
+  }
+  CompileRun("obj.__proto__ = null;"
+             "f(obj); f(obj); f(obj);");
   if (polymorphic) {
     CompileRun("f({});");
   }
@@ -17004,7 +17027,7 @@ static void Helper137002(bool do_store,
   if (do_store) {
     CompileRun("result = obj.y;");
   }
-  if (remove_accessor) {
+  if (remove_accessor && !interceptor) {
     CHECK(context->Global()->Get(v8_str("result"))->IsUndefined());
   } else {
     CHECK_EQ(do_store ? 23 : 42,
@@ -17017,14 +17040,9 @@ THREADED_TEST(Regress137002a) {
   i::FLAG_allow_natives_syntax = true;
   i::FLAG_compilation_cache = false;
   v8::HandleScope scope;
-  Helper137002(false, false, false);
-  Helper137002(false, false, true);
-  Helper137002(false, true, false);
-  Helper137002(false, true, true);
-  Helper137002(true, false, false);
-  Helper137002(true, false, true);
-  Helper137002(true, true, false);
-  Helper137002(true, true, true);
+  for (int i = 0; i < 16; i++) {
+    Helper137002(i & 8, i & 4, i & 2, i & 1);
+  }
 }