Bug 935136 - Always barrier assignments to Heap<Value> r=terrence
authorJon Coppeard <jcoppeard@mozilla.com>
Tue, 12 Nov 2013 11:21:01 +0000
changeset 169119 c8ddb7e587612fe767fc3d44463faffa763e74d3
parent 169068 44cce34b707327a7cec92402b47ba9d91e9b5d60
child 169120 787d6637b724273e10f099297a56b05fa735414e
push id3224
push userlsblakk@mozilla.com
push dateTue, 04 Feb 2014 01:06:49 +0000
treeherdermozilla-beta@60c04d0987f1 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersterrence
bugs935136
milestone28.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 935136 - Always barrier assignments to Heap<Value> r=terrence
js/public/Value.h
--- a/js/public/Value.h
+++ b/js/public/Value.h
@@ -1597,43 +1597,61 @@ class MutableValueOperations : public Un
     void setObjectOrNull(JSObject *arg) { this->value()->setObjectOrNull(arg); }
 };
 
 /*
  * Augment the generic Heap<T> interface when T = Value with
  * type-querying, value-extracting, and mutating operations.
  */
 template <>
-class HeapBase<JS::Value> : public UnbarrieredMutableValueOperations<JS::Heap<JS::Value> >
+class HeapBase<JS::Value> : public ValueOperations<JS::Heap<JS::Value> >
 {
     typedef JS::Heap<JS::Value> Outer;
 
     friend class ValueOperations<Outer>;
-    friend class UnbarrieredMutableValueOperations<Outer>;
 
     const JS::Value * extract() const { return static_cast<const Outer*>(this)->address(); }
-    JS::Value * extractMutable() { return static_cast<Outer*>(this)->unsafeGet(); }
 
-    /*
-     * Setters that potentially change the value to a GC thing from a non-GC
-     * thing must call JS::Heap::set() to trigger the post barrier.
-     *
-     * Changing from a GC thing to a non-GC thing value will leave the heap
-     * value in the store buffer, but it will be ingored so this is not a
-     * problem.
-     */
     void setBarriered(const JS::Value &v) {
         static_cast<JS::Heap<JS::Value> *>(this)->set(v);
     }
 
   public:
+    void setNull() { setBarriered(JS::NullValue()); }
+    void setUndefined() { setBarriered(JS::UndefinedValue()); }
+    void setInt32(int32_t i) { setBarriered(JS::Int32Value(i)); }
+    void setDouble(double d) { setBarriered(JS::DoubleValue(d)); }
+    void setNaN() { setDouble(JS::GenericNaN()); }
+    void setBoolean(bool b) { setBarriered(JS::BooleanValue(b)); }
+    void setMagic(JSWhyMagic why) { setBarriered(JS::MagicValue(why)); }
     void setString(JSString *str) { setBarriered(JS::StringValue(str)); }
     void setString(const JS::Anchor<JSString *> &str) { setBarriered(JS::StringValue(str.get())); }
     void setObject(JSObject &obj) { setBarriered(JS::ObjectValue(obj)); }
 
+    bool setNumber(uint32_t ui) {
+        if (ui > JSVAL_INT_MAX) {
+            setDouble((double)ui);
+            return false;
+        } else {
+            setInt32((int32_t)ui);
+            return true;
+        }
+    }
+
+    bool setNumber(double d) {
+        int32_t i;
+        if (mozilla::DoubleIsInt32(d, &i)) {
+            setInt32(i);
+            return true;
+        }
+
+        setDouble(d);
+        return false;
+    }
+
     void setObjectOrNull(JSObject *arg) {
         if (arg)
             setObject(*arg);
         else
             setNull();
     }
 };