Bug 818023 - fun_getProperty: Use non-buitin script iterator. r=waldo a=bajaj
authorNicolas B. Pierron <nicolas.b.pierron@mozilla.com>
Thu, 10 Jan 2013 11:19:21 -0800
changeset 127148 6ffa766f5cb8e771674c6d9920e803b38ab0ed30
parent 127147 0cce5a78c72716560e125b2907344dae657ed32e
child 127149 3f9116d9a244098690be39f6665ee10438dd8015
push id2151
push userlsblakk@mozilla.com
push dateTue, 19 Feb 2013 18:06:57 +0000
treeherdermozilla-beta@4952e88741ec [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerswaldo, bajaj
bugs818023
milestone20.0a2
Bug 818023 - fun_getProperty: Use non-buitin script iterator. r=waldo a=bajaj
js/src/jit-test/tests/ion/bug818023.js
js/src/jsfun.cpp
new file mode 100644
--- /dev/null
+++ b/js/src/jit-test/tests/ion/bug818023.js
@@ -0,0 +1,53 @@
+Function.prototype.callX = Function.prototype.call;
+var x;
+function f() {
+    x = f.caller;
+    return x;
+}
+
+function g() {
+    return f.callX(null);
+}
+
+function h1() {
+    // native
+    return ([0].map(f))[0];
+}
+
+function h2() {
+    // self-hosted
+    x = null;
+    [0].forEach(f);
+    return x;
+}
+
+function k() {
+    x = null;
+    [0, 1].sort(f);
+    return x;
+}
+
+function l() {
+    return f();
+}
+
+assertEq(g(), g);
+assertEq(h1(), h1);
+assertEq(h2(), h2);
+assertEq(k(), k);
+assertEq(l(), l);
+
+var baz;
+var foo = {callX: function() { return "m"; }};
+function bar() {
+    return baz.caller;
+}
+function m() {
+    return baz.callX(null);
+}
+
+baz = foo;
+assertEq(m(), "m");
+baz = bar;
+assertEq(m(), m);
+assertEq(m(), m);
--- a/js/src/jsfun.cpp
+++ b/js/src/jsfun.cpp
@@ -94,17 +94,17 @@ fun_getProperty(JSContext *cx, HandleObj
         fun->getOrCreateScript(cx)->uninlineable = true;
         MarkTypeObjectFlags(cx, fun, OBJECT_FLAG_UNINLINEABLE);
     }
 
     /* Set to early to null in case of error */
     vp.setNull();
 
     /* Find fun's top-most activation record. */
-    StackIter iter(cx);
+    NonBuiltinScriptFrameIter iter(cx);
     for (; !iter.done(); ++iter) {
         if (!iter.isFunctionFrame() || iter.isEvalFrame())
             continue;
         if (iter.callee() == fun)
             break;
     }
     if (iter.done())
         return true;