Bug 1155208 - In ToPropertyDescriptor, update attributes immediately after storing a getter or setter in a descriptor. r=jandem, a=abillings
authorJason Orendorff <jorendorff@mozilla.com>
Sun, 07 Jun 2015 08:20:39 -0500
changeset 266226 8de5d18494ab
parent 266225 dd38d3ccbacd
child 266227 c569e4e29be6
push id4792
push userryanvm@gmail.com
push date2015-06-10 20:30 +0000
treeherdermozilla-beta@f137fedd1455 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjandem, abillings
bugs1155208
milestone39.0
Bug 1155208 - In ToPropertyDescriptor, update attributes immediately after storing a getter or setter in a descriptor. r=jandem, a=abillings
js/src/jit-test/tests/gc/bug-1155208.js
js/src/jsobj.cpp
new file mode 100644
--- /dev/null
+++ b/js/src/jit-test/tests/gc/bug-1155208.js
@@ -0,0 +1,11 @@
+var handler = {
+    get: function get(t, pk, r) {},
+    has: function has(t = has = parseInt) {}
+};
+Object.prototype.__proto__ = new Proxy(Object.create(null), handler);
+function f() {
+    var desc = { get: function() {} };
+    var arr = Object.defineProperty([], "0", desc);
+}
+schedulegc(24);
+evaluate("f()");
--- a/js/src/jsobj.cpp
+++ b/js/src/jsobj.cpp
@@ -785,16 +785,17 @@ js::ToPropertyDescriptor(JSContext* cx, 
     if (!GetPropertyIfPresent(cx, obj, id, &v, &found))
         return false;
     hasGetOrSet = found;
     if (found) {
         if (v.isObject()) {
             if (checkAccessors && !CheckCallable(cx, &v.toObject(), js_getter_str))
                 return false;
             desc.setGetterObject(&v.toObject());
+            desc.attributesRef() |= JSPROP_GETTER;
         } else if (!v.isUndefined()) {
             JS_ReportErrorNumber(cx, GetErrorMessage, nullptr, JSMSG_BAD_GET_SET_FIELD,
                                  js_getter_str);
             return false;
         }
         attrs |= JSPROP_GETTER | JSPROP_SHARED;
     }
 
@@ -803,16 +804,17 @@ js::ToPropertyDescriptor(JSContext* cx, 
     if (!GetPropertyIfPresent(cx, obj, id, &v, &found))
         return false;
     hasGetOrSet |= found;
     if (found) {
         if (v.isObject()) {
             if (checkAccessors && !CheckCallable(cx, &v.toObject(), js_setter_str))
                 return false;
             desc.setSetterObject(&v.toObject());
+            desc.attributesRef() |= JSPROP_SETTER;
         } else if (!v.isUndefined()) {
             JS_ReportErrorNumber(cx, GetErrorMessage, nullptr, JSMSG_BAD_GET_SET_FIELD,
                                  js_setter_str);
             return false;
         }
         attrs |= JSPROP_SETTER | JSPROP_SHARED;
     }