Bug 1276908 - Add an extra field to the arena header r=terrence
authorJon Coppeard <jcoppeard@mozilla.com>
Tue, 21 Jun 2016 15:30:34 +0100
changeset 327274 b1c44ce827f75356115509db7a18075247c18d53
parent 327273 6a5167669bd2e88fd0eeb6f1232dbe2838c22c49
child 327275 85911372f2765079241357835fe84901b49c24c2
push id9858
push userjlund@mozilla.com
push dateMon, 01 Aug 2016 14:37:10 +0000
treeherdermozilla-aurora@203106ef6cb6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersterrence
bugs1276908
milestone50.0a1
Bug 1276908 - Add an extra field to the arena header r=terrence
js/public/HeapAPI.h
js/src/gc/Heap.h
--- a/js/public/HeapAPI.h
+++ b/js/public/HeapAPI.h
@@ -52,17 +52,18 @@ const size_t ChunkMarkBitmapBits = 31744
 #else
 const size_t ChunkMarkBitmapOffset = 1032352;
 const size_t ChunkMarkBitmapBits = 129024;
 #endif
 const size_t ChunkRuntimeOffset = ChunkSize - sizeof(void*);
 const size_t ChunkTrailerSize = 2 * sizeof(uintptr_t) + sizeof(uint64_t);
 const size_t ChunkLocationOffset = ChunkSize - ChunkTrailerSize;
 const size_t ArenaZoneOffset = sizeof(size_t);
-const size_t ArenaHeaderSize = sizeof(size_t) + 2 * sizeof(uintptr_t) + sizeof(size_t);
+const size_t ArenaHeaderSize = sizeof(size_t) + 2 * sizeof(uintptr_t) +
+                               sizeof(size_t) + sizeof(uintptr_t);
 
 /*
  * Live objects are marked black. How many other additional colors are available
  * depends on the size of the GCThing. Objects marked gray are eligible for
  * cycle collection.
  */
 static const uint32_t BLACK = 0;
 static const uint32_t GRAY = 1;
--- a/js/src/gc/Heap.h
+++ b/js/src/gc/Heap.h
@@ -515,16 +515,20 @@ class Arena
      */
     size_t hasDelayedMarking : 1;
     size_t allocatedDuringIncremental : 1;
     size_t markOverflow : 1;
     size_t auxNextLink : JS_BITS_PER_WORD - 8 - 1 - 1 - 1;
     static_assert(ArenaShift >= 8 + 1 + 1 + 1,
                   "Arena::auxNextLink packing assumes that ArenaShift has "
                   "enough bits to cover allocKind and hasDelayedMarking.");
+
+    /* Extra field for content-specific data. */
+    void* extra;
+
     /*
      * The size of data should be |ArenaSize - offsetof(data)|, but the offset
      * is not yet known to the compiler, so we do it by hand. |firstFreeSpan|
      * takes up 8 bytes on 64-bit due to alignment requirements; the rest are
      * obvious. This constant is stored in js/HeapAPI.h.
      */
     uint8_t data[ArenaSize - ArenaHeaderSize];
 
@@ -535,16 +539,17 @@ class Arena
         MOZ_ASSERT(!hasDelayedMarking);
         MOZ_ASSERT(!allocatedDuringIncremental);
         MOZ_ASSERT(!markOverflow);
         MOZ_ASSERT(!auxNextLink);
 
         zone = zoneArg;
         allocKind = size_t(kind);
         setAsFullyUnused();
+        extra = nullptr;
     }
 
     // Sets |firstFreeSpan| to the Arena's entire valid range, and
     // also sets the next span stored at |firstFreeSpan.last| as empty.
     void setAsFullyUnused() {
         AllocKind kind = getAllocKind();
         firstFreeSpan.first = firstThingOffset(kind);
         firstFreeSpan.last = lastThingOffset(kind);
@@ -684,18 +689,21 @@ class Arena
     static void staticAsserts();
 
     void unmarkAll();
 };
 
 static_assert(ArenaZoneOffset == offsetof(Arena, zone),
               "The hardcoded API zone offset must match the actual offset.");
 
-static_assert(sizeof(Arena) == ArenaSize, "The hardcoded API header size (ArenaHeaderSize) "
-                                          "must match the actual size of the header fields.");
+static_assert(sizeof(Arena) == ArenaSize,
+              "ArenaSize must match the actual size of the Arena structure.");
+
+static_assert(offsetof(Arena, data) == ArenaHeaderSize,
+              "ArenaHeaderSize must match the actual size of the header fields.");
 
 inline Arena*
 FreeSpan::getArena()
 {
     Arena* arena = getArenaUnchecked();
     arena->checkAddress();
     return arena;
 }