Bug 1382329 - Part 1: Enable lazy source whenever compiling for the preloader. r=mccr8, r=nbp, a=jcristau
authorKris Maglione <maglione.k@gmail.com>
Wed, 19 Jul 2017 11:57:18 -0700
changeset 414476 f7f4ce9889d271ebc1885a0c74615dc0b9950bbe
parent 414475 53381d5b4d72270cef138d050cc2f51c7a00426c
child 414477 0dc750f5253da3b132d30e85a2876d161ae607fc
push id1490
push usermtabara@mozilla.com
push dateMon, 31 Jul 2017 14:08:16 +0000
treeherdermozilla-release@70e32e6bf15e [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmccr8, nbp, jcristau
bugs1382329, 1367896
milestone55.0
Bug 1382329 - Part 1: Enable lazy source whenever compiling for the preloader. r=mccr8, r=nbp, a=jcristau In general, we always want to compile with lazy source whenever we intend to store code in the startup bytecode cache. Currently, we only do so when the main StartupCache is available (which is only in the parent process), even if we'll be storing code in the ScriptPreloader cache. The main side-effect of this is that scripts which are used in a content process do not use lazy source, but *do* use lazy parsing. And since we need to clone pre-loaded scripts into their target compartment before executing, we end up eagerly compiling those lazy functions on the main thread as soon as we execute the script, in order to clone them. And this causes two side-effects of its own: 1) It's terrible for startup performance. 2) It creates new scope chains which didn't exist when the clone began, and which are likely responsible for bug 1367896. MozReview-Commit-ID: 6lZLb68zitp
js/xpconnect/loader/ScriptPreloader.cpp
js/xpconnect/loader/ScriptPreloader.h
js/xpconnect/loader/mozJSComponentLoader.cpp
--- a/js/xpconnect/loader/ScriptPreloader.cpp
+++ b/js/xpconnect/loader/ScriptPreloader.cpp
@@ -688,17 +688,17 @@ ScriptPreloader::Run()
 }
 
 void
 ScriptPreloader::NoteScript(const nsCString& url, const nsCString& cachePath,
                             JS::HandleScript jsscript)
 {
     // Don't bother trying to cache any URLs with cache-busting query
     // parameters.
-    if (mStartupFinished || !mCacheInitialized || cachePath.FindChar('?') >= 0) {
+    if (!Active() || cachePath.FindChar('?') >= 0) {
         return;
     }
 
     // Don't bother caching files that belong to the mochitest harness.
     NS_NAMED_LITERAL_CSTRING(mochikitPrefix, "chrome://mochikit/");
     if (StringHead(url, mochikitPrefix.Length()) == mochikitPrefix) {
         return;
     }
@@ -930,17 +930,18 @@ ScriptPreloader::DecodeNextBatch(size_t 
         return;
     }
 
     AutoJSAPI jsapi;
     MOZ_RELEASE_ASSERT(jsapi.Init(xpc::CompilationScope()));
     JSContext* cx = jsapi.cx();
 
     JS::CompileOptions options(cx, JSVERSION_LATEST);
-    options.setNoScriptRval(true);
+    options.setNoScriptRval(true)
+           .setSourceIsLazy(true);
 
     if (!JS::CanCompileOffThread(cx, options, size) ||
         !JS::DecodeMultiOffThreadScripts(cx, options, mParsingSources,
                                          OffThreadDecodeCallback,
                                          static_cast<void*>(this))) {
         // If we fail here, we don't move on to process the next batch, so make
         // sure we don't have any other scripts left to process.
         MOZ_ASSERT(mPendingScripts.isEmpty());
--- a/js/xpconnect/loader/ScriptPreloader.h
+++ b/js/xpconnect/loader/ScriptPreloader.h
@@ -86,16 +86,21 @@ public:
                     ProcessType processType, nsTArray<uint8_t>&& xdrData,
                     TimeStamp loadTime);
 
     // Initializes the script cache from the startup script cache file.
     Result<Ok, nsresult> InitCache(const nsAString& = NS_LITERAL_STRING("scriptCache"));
 
     Result<Ok, nsresult> InitCache(const Maybe<ipc::FileDescriptor>& cacheFile, ScriptCacheChild* cacheChild);
 
+    bool Active()
+    {
+      return mCacheInitialized && !mStartupFinished;
+    }
+
 private:
     Result<Ok, nsresult> InitCacheInternal();
 
 public:
     void Trace(JSTracer* trc);
 
     static ProcessType CurrentProcessType()
     {
--- a/js/xpconnect/loader/mozJSComponentLoader.cpp
+++ b/js/xpconnect/loader/mozJSComponentLoader.cpp
@@ -648,17 +648,17 @@ mozJSComponentLoader::ObjectForLocation(
         // XDR encoded modules in omni.ja). Also, XDR decoding is relatively
         // fast. When we're not using the startup cache, we want to use non-lazy
         // source code so that we can use lazy parsing.
         // See bug 1303754.
         CompileOptions options(cx);
         options.setNoScriptRval(true)
                .setVersion(JSVERSION_LATEST)
                .setFileAndLine(nativePath.get(), 1)
-               .setSourceIsLazy(!!cache);
+               .setSourceIsLazy(cache || ScriptPreloader::GetSingleton().Active());
 
         if (realFile) {
             AutoMemMap map;
             MOZ_TRY(map.init(aComponentFile));
 
             // Note: exceptions will get handled further down;
             // don't early return for them here.
             auto buf = map.get<char>();