merge mozilla-inbound to mozilla-central. r=merge a=merge
authorSebastian Hengst <archaeopteryx@coole-files.de>
Mon, 31 Jul 2017 11:11:05 +0200
changeset 420670 26516ba270816a6cc90f5c42a9b66701369a551f
parent 420663 b1dcb20102b7598ec4d467530cd20ba9e8754de6 (current diff)
parent 420669 748a817e823e076f483cee7e26e69dcf8a807a4c (diff)
child 420671 1be0c1da06076f85c69cd8a9d244e0164ec544d9
child 420686 ef73974af658a8ccdb723a0ef151c609534539cc
child 420769 d8a326479290fdebaff3e555613d30bcf54a0536
push id7566
push usermtabara@mozilla.com
push dateWed, 02 Aug 2017 08:25:16 +0000
treeherdermozilla-beta@86913f512c3c [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmerge, merge
milestone56.0a1
first release with
nightly linux32
26516ba27081 / 56.0a1 / 20170731100325 / files
nightly linux64
26516ba27081 / 56.0a1 / 20170731100325 / files
nightly mac
26516ba27081 / 56.0a1 / 20170731100325 / files
nightly win32
26516ba27081 / 56.0a1 / 20170731100325 / files
nightly win64
26516ba27081 / 56.0a1 / 20170731100325 / files
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
releases
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
merge mozilla-inbound to mozilla-central. r=merge a=merge MozReview-Commit-ID: 2ICgX7IDEYO
--- a/browser/base/content/test/forms/browser_selectpopup_colors.js
+++ b/browser/base/content/test/forms/browser_selectpopup_colors.js
@@ -125,25 +125,34 @@ const SELECT_STYLE_OF_OPTION_CHANGES_AFT
   '  <option>{"color": "rgb(255, 0, 0)", "backgroundColor": "rgba(0, 0, 0, 0)"}</option>' +
   '  <option selected="true">{"end": "true"}</option>' +
   "</select></body><scr" +
   "ipt>" +
   "  var select = document.getElementById('one');" +
   "  select.addEventListener('focus', () => select.style.color = 'red');" +
   "</script></html>";
 
-const SELECT_STYLE_OF_OPTION_CHANGES_AFTER_TRANSITIONEND =
+const SELECT_COLOR_OF_OPTION_CHANGES_AFTER_TRANSITIONEND =
   "<html><head><style>" +
   "  select { transition: all .1s; }" +
   "  select:focus { background-color: orange; }" +
   "</style></head><body><select id='one'>" +
   '  <option>{"color": "rgb(0, 0, 0)", "backgroundColor": "rgba(0, 0, 0, 0)"}</option>' +
   '  <option selected="true">{"end": "true"}</option>' +
   "</select></body></html>";
 
+const SELECT_TEXTSHADOW_OF_OPTION_CHANGES_AFTER_TRANSITIONEND =
+  "<html><head><style>" +
+  "  select { transition: all .1s; }" +
+  "  select:focus { text-shadow: 0 0 0 #303030; }" +
+  "</style></head><body><select id='one'>" +
+  '  <option>{"color": "rgb(0, 0, 0)", "backgroundColor": "rgba(0, 0, 0, 0)", "textShadow": "rgb(48, 48, 48) 0px 0px 0px"}</option>' +
+  '  <option selected="true">{"end": "true"}</option>' +
+  "</select></body></html>";
+
 const SELECT_TRANSPARENT_COLOR_WITH_TEXT_SHADOW =
   "<html><head><style>" +
   "  select { color: transparent; text-shadow: 0 0 0 #303030; }" +
   "</style></head><body><select id='one'>" +
   '  <option>{"color": "rgba(0, 0, 0, 0)", "backgroundColor": "rgba(0, 0, 0, 0)", "textShadow": "rgb(48, 48, 48) 0px 0px 0px"}</option>' +
   '  <option selected="true">{"end": "true"}</option>' +
   "</select></body></html>";
 
@@ -401,27 +410,39 @@ add_task(async function test_style_of_op
     waitForComputedStyle: {
       property: "color",
       value: "rgb(255, 0, 0)"
     }
   };
   await testSelectColors(SELECT_STYLE_OF_OPTION_CHANGES_AFTER_FOCUS_EVENT, 2, options);
 });
 
-add_task(async function test_style_of_options_is_dependent_on_transitionend() {
+add_task(async function test_color_of_options_is_dependent_on_transitionend() {
   let options = {
     selectColor: "rgb(0, 0, 0)",
     selectBgColor: "rgb(255, 165, 0)",
     waitForComputedStyle: {
       property: "background-image",
       value: "linear-gradient(rgb(255, 165, 0), rgb(255, 165, 0))"
     }
   };
 
-  await testSelectColors(SELECT_STYLE_OF_OPTION_CHANGES_AFTER_TRANSITIONEND, 2, options);
+  await testSelectColors(SELECT_COLOR_OF_OPTION_CHANGES_AFTER_TRANSITIONEND, 2, options);
+});
+
+add_task(async function test_textshadow_of_options_is_dependent_on_transitionend() {
+  let options = {
+    skipSelectColorTest: true,
+    waitForComputedStyle: {
+      property: "text-shadow",
+      value: "rgb(48, 48, 48) 0px 0px 0px"
+    }
+  };
+
+  await testSelectColors(SELECT_TEXTSHADOW_OF_OPTION_CHANGES_AFTER_TRANSITIONEND, 2, options);
 });
 
 add_task(async function test_transparent_color_with_text_shadow() {
   let options = {
     selectColor: "rgba(0, 0, 0, 0)",
     selectTextShadow: "rgb(48, 48, 48) 0px 0px 0px",
     selectBgColor: "rgb(255, 255, 255)"
   };
--- a/gfx/layers/wr/AsyncImagePipelineManager.h
+++ b/gfx/layers/wr/AsyncImagePipelineManager.h
@@ -3,16 +3,17 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef MOZILLA_GFX_WEBRENDERCOMPOSITABLE_HOLDER_H
 #define MOZILLA_GFX_WEBRENDERCOMPOSITABLE_HOLDER_H
 
 #include <queue>
 
+#include "CompositableHost.h"
 #include "mozilla/gfx/Point.h"
 #include "mozilla/layers/TextureHost.h"
 #include "mozilla/Maybe.h"
 #include "mozilla/webrender/WebRenderTypes.h"
 #include "nsClassHashtable.h"
 
 namespace mozilla {
 
@@ -74,16 +75,26 @@ public:
   void UpdateAsyncImagePipeline(const wr::PipelineId& aPipelineId,
                                 const LayerRect& aScBounds,
                                 const gfx::Matrix4x4& aScTransform,
                                 const gfx::MaybeIntSize& aScaleToSize,
                                 const wr::ImageRendering& aFilter,
                                 const wr::MixBlendMode& aMixBlendMode);
   void ApplyAsyncImages(wr::WebRenderAPI* aApi);
 
+  void AppendImageCompositeNotification(const ImageCompositeNotificationInfo& aNotification)
+  {
+    mImageCompositeNotifications.AppendElement(aNotification);
+  }
+
+  void FlushImageNotifications(nsTArray<ImageCompositeNotificationInfo>* aNotifications)
+  {
+    aNotifications->AppendElements(Move(mImageCompositeNotifications));
+  }
+
 private:
   void DeleteOldAsyncImages(wr::WebRenderAPI* aApi);
 
   uint32_t GetNextResourceId() { return ++mResourceId; }
   uint32_t GetNamespace() { return mIdNamespace; }
   wr::ImageKey GenerateImageKey()
   {
     wr::ImageKey key;
@@ -141,14 +152,16 @@ private:
 
   // Render time for the current composition.
   TimeStamp mCompositionTime;
 
   // When nonnull, during rendering, some compositable indicated that it will
   // change its rendering at this time. In order not to miss it, we composite
   // on every vsync until this time occurs (this is the latest such time).
   TimeStamp mCompositeUntilTime;
+
+  nsTArray<ImageCompositeNotificationInfo> mImageCompositeNotifications;
 };
 
 } // namespace layers
 } // namespace mozilla
 
 #endif /* MOZILLA_GFX_WEBRENDERCOMPOSITABLE_HOLDER_H */
--- a/gfx/layers/wr/WebRenderBridgeParent.cpp
+++ b/gfx/layers/wr/WebRenderBridgeParent.cpp
@@ -1436,10 +1436,17 @@ WebRenderBridgeParent::GetTextureFactory
 
 uint32_t
 WebRenderBridgeParent::GetNextWrEpoch()
 {
   MOZ_RELEASE_ASSERT(mWrEpoch != UINT32_MAX);
   return ++mWrEpoch;
 }
 
+void
+WebRenderBridgeParent::ExtractImageCompositeNotifications(nsTArray<ImageCompositeNotificationInfo>* aNotifications)
+{
+  MOZ_ASSERT(mWidget);
+  mAsyncImageManager->FlushImageNotifications(aNotifications);
+}
+
 } // namespace layers
 } // namespace mozilla
--- a/gfx/layers/wr/WebRenderBridgeParent.h
+++ b/gfx/layers/wr/WebRenderBridgeParent.h
@@ -171,27 +171,17 @@ public:
 
   void HoldPendingTransactionId(uint32_t aWrEpoch, uint64_t aTransactionId, const TimeStamp& aFwdTime);
   uint64_t LastPendingTransactionId();
   uint64_t FlushPendingTransactionIds();
   uint64_t FlushTransactionIdsForEpoch(const wr::Epoch& aEpoch, const TimeStamp& aEndTime);
 
   TextureFactoryIdentifier GetTextureFactoryIdentifier();
 
-  void AppendImageCompositeNotification(const ImageCompositeNotificationInfo& aNotification)
-  {
-    MOZ_ASSERT(mWidget);
-    mImageCompositeNotifications.AppendElement(aNotification);
-  }
-
-  void ExtractImageCompositeNotifications(nsTArray<ImageCompositeNotificationInfo>* aNotifications)
-  {
-    MOZ_ASSERT(mWidget);
-    aNotifications->AppendElements(Move(mImageCompositeNotifications));
-  }
+  void ExtractImageCompositeNotifications(nsTArray<ImageCompositeNotificationInfo>* aNotifications);
 
   uint32_t GetIdNameSpace()
   {
     return mIdNameSpace;
   }
 
   void UpdateAPZ();
   const WebRenderScrollData& GetScrollData() const;
@@ -281,17 +271,16 @@ private:
   // WebRenderBridgeParent is destroyed abnormally and Tab move between different windows.
   std::unordered_set<uint64_t> mActiveImageKeys;
   std::unordered_set<uint64_t> mFontKeys;
   // mActiveAnimations is used to avoid leaking animations when WebRenderBridgeParent is
   // destroyed abnormally and Tab move between different windows.
   std::unordered_set<uint64_t> mActiveAnimations;
   nsDataHashtable<nsUint64HashKey, RefPtr<WebRenderImageHost>> mAsyncCompositables;
   nsDataHashtable<nsUint64HashKey, RefPtr<WebRenderImageHost>> mExternalImageIds;
-  nsTArray<ImageCompositeNotificationInfo> mImageCompositeNotifications;
 
   TimeStamp mPreviousFrameTimeStamp;
   // These fields keep track of the latest layer observer epoch values in the child and the
   // parent. mChildLayerObserverEpoch is the latest epoch value received from the child.
   // mParentLayerObserverEpoch is the latest epoch value that we have told TabParent about
   // (via ObserveLayerUpdate).
   uint64_t mChildLayerObserverEpoch;
   uint64_t mParentLayerObserverEpoch;
--- a/gfx/layers/wr/WebRenderImageHost.cpp
+++ b/gfx/layers/wr/WebRenderImageHost.cpp
@@ -138,34 +138,50 @@ WebRenderImageHost::GetAsTextureHost(Int
     return img->mTextureHost;
   }
   return nullptr;
 }
 
 TextureHost*
 WebRenderImageHost::GetAsTextureHostForComposite()
 {
+  if (!mWrBridge) {
+    return nullptr;
+  }
+
   int imageIndex = ChooseImageIndex();
   if (imageIndex < 0) {
     SetCurrentTextureHost(nullptr);
     return nullptr;
   }
 
-  if (mWrBridge && uint32_t(imageIndex) + 1 < mImages.Length()) {
+  if (uint32_t(imageIndex) + 1 < mImages.Length()) {
     MOZ_ASSERT(mWrBridge->AsyncImageManager());
     mWrBridge->AsyncImageManager()->CompositeUntil(mImages[imageIndex + 1].mTimeStamp + TimeDuration::FromMilliseconds(BIAS_TIME_MS));
   }
 
   TimedImage* img = &mImages[imageIndex];
 
   if (mLastFrameID != img->mFrameID || mLastProducerID != img->mProducerID) {
+    if (mAsyncRef) {
+      ImageCompositeNotificationInfo info;
+      info.mImageBridgeProcessId = mAsyncRef.mProcessId;
+      info.mNotification = ImageCompositeNotification(
+        mAsyncRef.mHandle,
+        img->mTimeStamp, mWrBridge->AsyncImageManager()->GetCompositionTime(),
+        img->mFrameID, img->mProducerID);
+      mWrBridge->AsyncImageManager()->AppendImageCompositeNotification(info);
+    }
     mLastFrameID = img->mFrameID;
     mLastProducerID = img->mProducerID;
   }
   SetCurrentTextureHost(img->mTextureHost);
+
+  // XXX Add UpdateBias()
+
   return mCurrentTextureHost;
 }
 
 void
 WebRenderImageHost::SetCurrentTextureHost(TextureHost* aTexture)
 {
   if (aTexture == mCurrentTextureHost.get()) {
     return;
--- a/gfx/webrender_bindings/src/bindings.rs
+++ b/gfx/webrender_bindings/src/bindings.rs
@@ -561,16 +561,17 @@ pub extern "C" fn wr_window_new(window_i
     let opts = RendererOptions {
         enable_aa: true,
         enable_subpixel_aa: true,
         enable_profiler: enable_profiler,
         recorder: recorder,
         blob_image_renderer: Some(Box::new(Moz2dImageRenderer::new(workers.clone()))),
         workers: Some(workers.clone()),
         cache_expiry_frames: 60, // see https://github.com/servo/webrender/pull/1294#issuecomment-304318800
+        enable_render_on_scroll: false,
         ..Default::default()
     };
 
     let window_size = DeviceUintSize::new(window_width, window_height);
     let (renderer, sender) = match Renderer::new(gl, opts, window_size) {
         Ok((renderer, sender)) => (renderer, sender),
         Err(e) => {
             println!(" Failed to create a Renderer: {:?}", e);
--- a/js/public/HashTable.h
+++ b/js/public/HashTable.h
@@ -1767,19 +1767,17 @@ class HashTable : private AllocPolicy
     }
 
     MOZ_ALWAYS_INLINE AddPtr lookupForAdd(const Lookup& l) const
     {
         mozilla::ReentrancyGuard g(*this);
         if (!EnsureHash<HashPolicy>(l))
             return AddPtr();
         HashNumber keyHash = prepareHash(l);
-        Entry& entry = lookup(l, keyHash, sCollisionBit);
-        AddPtr p(entry, *this, keyHash);
-        return p;
+        return AddPtr(lookup(l, keyHash, sCollisionBit), *this, keyHash);
     }
 
     template <typename... Args>
     MOZ_MUST_USE bool add(AddPtr& p, Args&&... args)
     {
         mozilla::ReentrancyGuard g(*this);
         MOZ_ASSERT(table);
         MOZ_ASSERT_IF(p.isValid(), p.table_ == this);
--- a/testing/marionette/components/marionette.js
+++ b/testing/marionette/components/marionette.js
@@ -2,23 +2,25 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this file,
  * You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 "use strict";
 
 const {Constructor: CC, interfaces: Ci, utils: Cu, classes: Cc} = Components;
 
 Cu.import("resource://gre/modules/Log.jsm");
-Cu.import("resource://gre/modules/Preferences.jsm");
 Cu.import("resource://gre/modules/Services.jsm");
 Cu.import("resource://gre/modules/XPCOMUtils.jsm");
 
 XPCOMUtils.defineLazyServiceGetter(
     this, "env", "@mozilla.org/process/environment;1", "nsIEnvironment");
 
+XPCOMUtils.defineLazyModuleGetter(this, "Preferences",
+  "resource://gre/modules/Preferences.jsm");
+
 const MARIONETTE_CONTRACT_ID = "@mozilla.org/remote/marionette;1";
 const MARIONETTE_CID = Components.ID("{786a1369-dca5-4adc-8486-33d23c88010a}");
 
 const PREF_PORT = "marionette.port";
 const PREF_PORT_FALLBACK = "marionette.defaultPrefs.port";
 const PREF_LOG_LEVEL = "marionette.log.level";
 const PREF_LOG_LEVEL_FALLBACK = "marionette.logging";
 
@@ -62,23 +64,54 @@ const ENV_ENABLED = "MOZ_MARIONETTE";
 // something like {"port": 4444} would result in the marionette.port
 // pref being set to 4444.
 const ENV_PRESERVE_PREFS = "MOZ_MARIONETTE_PREF_STATE_ACROSS_RESTARTS";
 
 const ServerSocket = CC("@mozilla.org/network/server-socket;1",
     "nsIServerSocket",
     "initSpecialConnection");
 
+const {PREF_STRING, PREF_BOOL, PREF_INT, PREF_INVALID} = Ci.nsIPrefBranch;
+
+function getPrefVal(pref) {
+  let prefType = Services.prefs.getPrefType(pref);
+  let prefValue;
+  switch (prefType) {
+    case PREF_STRING:
+      prefValue = Services.prefs.getStringPref(pref);
+      break;
+
+    case PREF_BOOL:
+      prefValue = Services.prefs.getBoolPref(pref);
+      break;
+
+    case PREF_INT:
+      prefValue = Services.prefs.getIntPref(pref);
+      break;
+
+    case PREF_INVALID:
+      prefValue = undefined;
+      break;
+
+    default:
+      throw new TypeError(`Unexpected preference type (${prefType}) for ` +
+                          `${pref}`);
+  }
+
+  return prefValue;
+}
+
 // Get preference value of |preferred|, falling back to |fallback|
 // if |preferred| is not user-modified and |fallback| exists.
 function getPref(preferred, fallback) {
-  if (!Preferences.isSet(preferred) && Preferences.has(fallback)) {
-    return Preferences.get(fallback, Preferences.get(preferred));
+  if (!Services.prefs.prefHasUserValue(preferred) &&
+      Services.prefs.getPrefType(fallback) != Ci.nsIPrefBranch.PREF_INVALID) {
+    return getPrefVal(fallback, getPrefVal(preferred));
   }
-  return Preferences.get(preferred);
+  return getPrefVal(preferred);
 }
 
 // Marionette preferences recently changed names.  This is an abstraction
 // that first looks for the new name, but falls back to using the old name
 // if the new does not exist.
 //
 // This shim can be removed when Firefox 55 ships.
 const prefs = {
--- a/toolkit/modules/SelectContentHelper.jsm
+++ b/toolkit/modules/SelectContentHelper.jsm
@@ -15,16 +15,22 @@ XPCOMUtils.defineLazyModuleGetter(this, 
 XPCOMUtils.defineLazyServiceGetter(this, "DOMUtils",
                                    "@mozilla.org/inspector/dom-utils;1", "inIDOMUtils");
 XPCOMUtils.defineLazyModuleGetter(this, "DeferredTask",
                                   "resource://gre/modules/DeferredTask.jsm");
 
 const kStateActive = 0x00000001; // NS_EVENT_STATE_ACTIVE
 const kStateHover = 0x00000004; // NS_EVENT_STATE_HOVER
 
+const SUPPORTED_PROPERTIES = [
+  "color",
+  "background-color",
+  "text-shadow",
+];
+
 // A process global state for whether or not content thinks
 // that a <select> dropdown is open or not. This is managed
 // entirely within this module, and is read-only accessible
 // via SelectContentHelper.open.
 var gOpen = false;
 
 this.EXPORTED_SYMBOLS = [
   "SelectContentHelper"
@@ -354,17 +360,19 @@ this.SelectContentHelper.prototype = {
       }
       case "mozhidedropdown":
         if (this.element === event.target) {
           this.global.sendAsyncMessage("Forms:HideDropDown", {});
           this.uninit();
         }
         break;
       case "transitionend":
-        this._update();
+        if (SUPPORTED_PROPERTIES.indexOf(event.propertyName) != -1) {
+          this._updateTimer.arm();
+        }
         break;
     }
   }
 
 }
 
 function getComputedStyles(element) {
   return element.ownerGlobal.getComputedStyle(element);
@@ -385,16 +393,20 @@ function buildOptionListForChildren(node
         tagName == "OPTGROUP" ? child.getAttribute("label")
                               : child.text;
       if (textContent == null) {
         textContent = "";
       }
 
       let cs = getComputedStyles(child);
 
+      // Note: If you add any more CSS properties support here,
+      // please add the property name to the SUPPORTED_PROPERTIES
+      // list so that the menu can be correctly updated when CSS
+      // transitions are used.
       let info = {
         index: child.index,
         tagName,
         textContent,
         disabled: child.disabled,
         display: cs.display,
         // We need to do this for every option element as each one can have
         // an individual style set for direction