bug 465032 - operationCount as the first field in JSContext. r=brendan
authorIgor Bukanov <igor@mir2.org>
Thu, 18 Dec 2008 16:24:34 +0100
changeset 23092 e6c176faad6bd208cd006056e7197abb20989679
parent 23091 8353e26475a8866498ad1da8d2fa8848b9f033a5
child 23093 cc3cbf3ea6761a33ad74feb33c6c8fb6c8d0d62a
push id4346
push userrsayre@mozilla.com
push dateFri, 26 Dec 2008 01:26:36 +0000
treeherdermozilla-central@8eb5a5b83a93 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbrendan
bugs465032
milestone1.9.2a1pre
bug 465032 - operationCount as the first field in JSContext. r=brendan
js/src/jscntxt.cpp
js/src/jscntxt.h
--- a/js/src/jscntxt.cpp
+++ b/js/src/jscntxt.cpp
@@ -272,17 +272,17 @@ js_NewContext(JSRuntime *rt, size_t stac
         }
         if (rt->state == JSRTS_DOWN) {
             JS_ASSERT(first);
             rt->state = JSRTS_LAUNCHING;
             break;
         }
         JS_WAIT_CONDVAR(rt->stateChange, JS_NO_TIMEOUT);
     }
-    JS_APPEND_LINK(&cx->links, &rt->contextList);
+    JS_APPEND_LINK(&cx->link, &rt->contextList);
     JS_UNLOCK_GC(rt);
 
     /*
      * First we do the infallible, every-time per-context initializations.
      * Should a later, fallible initialization (js_InitRegExpStatics, e.g.,
      * or the stuff under 'if (first)' below) fail, at least the version
      * and arena-pools will be valid and safe to use (say, from the last GC
      * done by js_DestroyContext).
@@ -386,17 +386,17 @@ js_DestroyContext(JSContext *cx, JSDestr
             cxCallback(cx, JSCONTEXT_DESTROY);
             JS_ASSERT(callbackStatus);
         }
     }
 
     /* Remove cx from context list first. */
     JS_LOCK_GC(rt);
     JS_ASSERT(rt->state == JSRTS_UP || rt->state == JSRTS_LAUNCHING);
-    JS_REMOVE_LINK(&cx->links);
+    JS_REMOVE_LINK(&cx->link);
     last = (rt->contextList.next == &rt->contextList);
     if (last)
         rt->state = JSRTS_LANDING;
 #ifdef JS_THREADSAFE
     js_RevokeGCLocalFreeLists(cx);
 #endif
     JS_UNLOCK_GC(rt);
 
@@ -514,32 +514,32 @@ js_DestroyContext(JSContext *cx, JSDestr
 }
 
 JSBool
 js_ValidContextPointer(JSRuntime *rt, JSContext *cx)
 {
     JSCList *cl;
 
     for (cl = rt->contextList.next; cl != &rt->contextList; cl = cl->next) {
-        if (cl == &cx->links)
+        if (cl == &cx->link)
             return JS_TRUE;
     }
     JS_RUNTIME_METER(rt, deadContexts);
     return JS_FALSE;
 }
 
 JSContext *
 js_ContextIterator(JSRuntime *rt, JSBool unlocked, JSContext **iterp)
 {
     JSContext *cx = *iterp;
 
     if (unlocked)
         JS_LOCK_GC(rt);
-    cx = (JSContext *) (cx ? cx->links.next : rt->contextList.next);
-    if (&cx->links == &rt->contextList)
+    cx = js_ContextFromLinkField(cx ? cx->link.next : rt->contextList.next);
+    if (&cx->link == &rt->contextList)
         cx = NULL;
     *iterp = cx;
     if (unlocked)
         JS_UNLOCK_GC(rt);
     return cx;
 }
 
 static JSDHashNumber
--- a/js/src/jscntxt.h
+++ b/js/src/jscntxt.h
@@ -729,25 +729,25 @@ JS_STATIC_ASSERT(sizeof(JSTempValueUnion
 
 #define JS_PUSH_TEMP_ROOT_SCRIPT(cx,script_,tvr)                              \
     JS_PUSH_TEMP_ROOT_COMMON(cx, script_, tvr, JSTVU_SCRIPT, script)
 
 
 #define JSRESOLVE_INFER         0xffff  /* infer bits from current bytecode */
 
 struct JSContext {
-    /* JSRuntime contextList linkage. */
-    JSCList             links;
-
     /*
-     * Operation count. It is declared early in the structure as a frequently
-     * accessed field.
+     * Operation count. It is declared as the first field in the struct to
+     * ensure the fastest possible access.
      */
     int32               operationCount;
 
+    /* JSRuntime contextList linkage. */
+    JSCList             link;
+
 #if JS_HAS_XML_SUPPORT
     /*
      * Bit-set formed from binary exponentials of the XML_* tiny-ids defined
      * for boolean settings in jsxml.c, plus an XSF_CACHE_VALID bit.  Together
      * these act as a cache of the boolean XML.ignore* and XML.prettyPrinting
      * property values associated with this context's global object.
      */
     uint8               xmlSettingFlags;
@@ -1042,16 +1042,23 @@ js_DestroyContext(JSContext *cx, JSDestr
 
 /*
  * Return true if cx points to a context in rt->contextList, else return false.
  * NB: the caller (see jslock.c:ClaimTitle) must hold rt->gcLock.
  */
 extern JSBool
 js_ValidContextPointer(JSRuntime *rt, JSContext *cx);
 
+static JS_INLINE JSContext *
+js_ContextFromLinkField(JSCList *link)
+{
+    JS_ASSERT(link);
+    return (JSContext *) ((uint8 *) link - offsetof(JSContext, link));
+}
+
 /*
  * If unlocked, acquire and release rt->gcLock around *iterp update; otherwise
  * the caller must be holding rt->gcLock.
  */
 extern JSContext *
 js_ContextIterator(JSRuntime *rt, JSBool unlocked, JSContext **iterp);
 
 /*