Merge autoland to mozilla-central. a=merge FIREFOX_BETA_91_BASE
authorCsoregi Natalia <ncsoregi@mozilla.com>
Mon, 12 Jul 2021 12:29:34 +0300
changeset 585270 5dee15cf3f2810ccc3bb9ec24c652f6f9d72b62d
parent 585262 464e45ce39e01898784fea28fb8bc7ff98a11752 (current diff)
parent 585269 693f792b89888a2cc6837a71743cf3720a428538 (diff)
child 585271 41ae2b104b93c1779db0f34ba1c045e3e696898b
child 585276 a7575fc80dea73b55c9d60d153b5571491204826
push id38605
push userncsoregi@mozilla.com
push dateMon, 12 Jul 2021 09:30:40 +0000
treeherdermozilla-central@5dee15cf3f28 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmerge
milestone91.0a1
first release with
nightly linux32
5dee15cf3f28 / 91.0a1 / 20210712093040 / files
nightly linux64
5dee15cf3f28 / 91.0a1 / 20210712093040 / files
nightly mac
5dee15cf3f28 / 91.0a1 / 20210712093040 / files
nightly win32
5dee15cf3f28 / 91.0a1 / 20210712093040 / files
nightly win64
5dee15cf3f28 / 91.0a1 / 20210712093040 / 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 autoland to mozilla-central. a=merge
--- a/browser/base/content/test/performance/browser_preferences_usage.js
+++ b/browser/base/content/test/performance/browser_preferences_usage.js
@@ -200,21 +200,24 @@ add_task(async function navigate_around(
   let knownProblematicPrefs = {
     "browser.zoom.full": {
       min: 100,
       max: 110,
     },
     "network.loadinfo.skip_type_assertion": {
       // This is accessed in debug only.
     },
-    "toolkit.telemetry.cachedClientID": {
+  };
+
+  if (AppConstants.NIGHTLY_BUILD) {
+    knownProblematicPrefs["toolkit.telemetry.cachedClientID"] = {
       // Bug 1712391: Only an issue in tests where pref is not populated early on
-      // in startup
-    },
-  };
+      // in startup. Code path is only accessed in Nightly builds.
+    };
+  }
 
   if (SpecialPowers.useRemoteSubframes) {
     // We access this when considering starting a new content process.
     // Because there is no complete list of content process types,
     // caching this is not trivial. Opening 50 different content
     // processes and throwing them away immediately is a bit artificial;
     // we're more likely to keep some around so this shouldn't be quite
     // this bad in practice. Fixing this is
--- a/dom/html/HTMLInputElement.cpp
+++ b/dom/html/HTMLInputElement.cpp
@@ -436,17 +436,20 @@ void GetDOMFileOrDirectoryPath(const Own
 
 }  // namespace
 
 NS_IMETHODIMP
 HTMLInputElement::nsFilePickerShownCallback::Done(int16_t aResult) {
   mInput->PickerClosed();
 
   if (aResult == nsIFilePicker::returnCancel) {
-    return NS_OK;
+    RefPtr<HTMLInputElement> inputElement(mInput);
+    return nsContentUtils::DispatchTrustedEvent(
+        inputElement->OwnerDoc(), static_cast<Element*>(inputElement.get()),
+        u"cancel"_ns, CanBubble::eYes, Cancelable::eNo);
   }
 
   int16_t mode;
   mFilePicker->GetMode(&mode);
 
   // Collect new selected filenames
   nsTArray<OwningFileOrDirectory> newFilesOrDirectories;
   if (mode == static_cast<int16_t>(nsIFilePicker::modeOpenMultiple)) {
--- a/dom/html/HTMLInputElement.h
+++ b/dom/html/HTMLInputElement.h
@@ -1644,16 +1644,16 @@ class HTMLInputElement final : public Te
     nsFilePickerShownCallback(HTMLInputElement* aInput,
                               nsIFilePicker* aFilePicker);
     NS_DECL_ISUPPORTS
 
     NS_IMETHOD Done(int16_t aResult) override;
 
    private:
     nsCOMPtr<nsIFilePicker> mFilePicker;
-    RefPtr<HTMLInputElement> mInput;
+    const RefPtr<HTMLInputElement> mInput;
   };
 };
 
 }  // namespace dom
 }  // namespace mozilla
 
 #endif
--- a/dom/html/test/mochitest.ini
+++ b/dom/html/test/mochitest.ini
@@ -519,16 +519,17 @@ tags = openwindow
 [test_q_attributes_reflection.html]
 [test_restore_from_parser_fragment.html]
 [test_rowscollection.html]
 [test_srcdoc-2.html]
 [test_srcdoc.html]
 [test_style_attributes_reflection.html]
 [test_track.html]
 [test_ul_attributes_reflection.html]
+[test_input_file_cancel_event.html]
 [test_input_files_not_nsIFile.html]
 [test_fragment_form_pointer.html]
 [test_bug1682.html]
 [test_bug1823.html]
 [test_bug57600.html]
 [test_bug196523.html]
 [test_bug199692.html]
 [test_bug255820.html]
new file mode 100644
--- /dev/null
+++ b/dom/html/test/test_input_file_cancel_event.html
@@ -0,0 +1,43 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <title>Test for the input type=file cancel event</title>
+  <script src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script src="/tests/SimpleTest/EventUtils.js"></script>
+  <link rel="stylesheet" href="/tests/SimpleTest/test.css"/>
+</head>
+<body>
+
+<input type=file></input>
+
+<script>
+SimpleTest.waitForExplicitFinish();
+
+var MockFilePicker = SpecialPowers.MockFilePicker;
+MockFilePicker.init(window);
+MockFilePicker.useBlobFile();
+MockFilePicker.returnValue = MockFilePicker.returnCancel;
+
+let input = document.querySelector('input[type=file]');
+input.addEventListener('cancel', event => {
+  ok(true, "cancel event correctly sent");
+
+  is(event.target, input, "Has correct event target");
+  is(event.isTrusted, true, "Event is trusted");
+  is(event.bubbles, true, "Event bubbles");
+  is(event.cancelable, false, "Event is not cancelable");
+  is(event.composed, false, "Event is not composed");
+
+  SimpleTest.executeSoon(function() {
+    MockFilePicker.cleanup();
+    SimpleTest.finish();
+  });
+});
+input.addEventListener('change' , () => {
+  ok(false, "unexpected change event");
+})
+input.click();
+</script>
+</body>
+</html>
+
--- a/editor/libeditor/HTMLEditSubActionHandler.cpp
+++ b/editor/libeditor/HTMLEditSubActionHandler.cpp
@@ -1009,17 +1009,19 @@ EditActionResult HTMLEditor::HandleInser
       NS_WARN_IF(!pointToInsert.IsInContentNode())) {
     return EditActionHandled(NS_ERROR_FAILURE);
   }
   MOZ_ASSERT(pointToInsert.IsSetAndValid());
 
   // If the point is not in an element which can contain text nodes, climb up
   // the DOM tree.
   if (!pointToInsert.IsInTextNode()) {
-    Element* editingHost = GetActiveEditingHost();
+    Element* editingHost = GetActiveEditingHost(GetDocument()->IsXMLDocument()
+                                                    ? LimitInBodyElement::No
+                                                    : LimitInBodyElement::Yes);
     if (NS_WARN_IF(!editingHost)) {
       return EditActionHandled(NS_ERROR_EDITOR_UNEXPECTED_DOM_TREE);
     }
     while (!HTMLEditUtils::CanNodeContain(*pointToInsert.GetContainer(),
                                           *nsGkAtoms::textTagName)) {
       if (NS_WARN_IF(pointToInsert.GetContainer() == editingHost) ||
           NS_WARN_IF(!pointToInsert.GetContainerParentAsContent())) {
         NS_WARNING("Selection start point couldn't have text nodes");
--- a/editor/libeditor/tests/mochitest.ini
+++ b/editor/libeditor/tests/mochitest.ini
@@ -294,16 +294,17 @@ skip-if = headless
 [test_nsITableEditor_getTableSize.html]
 [test_nsITableEditor_insertTableCell.html]
 [test_nsITableEditor_insertTableColumn.html]
 [test_nsITableEditor_insertTableRow.html]
 [test_password_input_with_unmasked_range.html]
 [test_password_paste.html]
 [test_password_per_word_operation.html]
 [test_password_unmask_API.html]
+[test_pasting_in_root_element.xhtml]
 [test_pasting_text_longer_than_maxlength.html]
 [test_resizers_appearance.html]
 [test_resizers_resizing_elements.html]
 skip-if = (verify && debug && os == 'win') # bug 1485293
 [test_root_element_replacement.html]
 [test_select_all_without_body.html]
 [test_setting_value_longer_than_maxlength_with_setUserInput.html]
 [test_spellcheck_pref.html]
--- a/editor/libeditor/tests/test_bug795418-2.html
+++ b/editor/libeditor/tests/test_bug795418-2.html
@@ -22,25 +22,19 @@ https://bugzilla.mozilla.org/show_bug.cg
 
 <pre id="test">
 
 <script type="application/javascript">
 
 /** Test for Bug 795418 **/
 SimpleTest.waitForExplicitFinish();
 SimpleTest.waitForFocus(function() {
-  var div = document.getElementById("copySource");
-  var sel = window.getSelection();
-  sel.removeAllRanges();
-
-  // Select the text from the text node in div.
-  var r = document.createRange();
-  r.setStart(div.firstChild, 0);
-  r.setEnd(div.firstChild, 9);
-  sel.addRange(r);
+  const div = document.getElementById("copySource");
+  getSelection().setBaseAndExtent(div.firstChild, 0, div.firstChild, "Copy this".length);
+  info(`Selected test: "${getSelection().getRangeAt(0).toString()}"`);
 
   function checkResult() {
     var iframe = document.querySelector("iframe");
     var theEdit = iframe.contentDocument.firstChild;
     theEdit.offsetHeight;
     is(theEdit.innerHTML,
        "<blockquote xmlns=\"http://www.w3.org/1999/xhtml\" type=\"cite\">Copy this</blockquote><span xmlns=\"http://www.w3.org/1999/xhtml\">AB</span>",
        "unexpected HTML for test");
@@ -61,30 +55,33 @@ SimpleTest.waitForFocus(function() {
 
       SpecialPowers.doCommand(iframeWindow, "cmd_pasteQuote");
       setTimeout(checkResult, 0);
     }, iframeWindow);
   }
 
   SimpleTest.waitForClipboard(
     aData => {
-      // XXX Oddly, specifying `r.toString()` causes timeout in headless mode.
-      info(`copied text: "${aData}"`);
-      return true;
+      if (aData.includes(`${getSelection().getRangeAt(0)?.toString()}`)) {
+        return true;
+      }
+      info(`Text in the clipboard: "${aData}"`);
+      return false;
     },
     function setup() {
-      synthesizeKey("C", {accelKey: true});
+      synthesizeKey("c", {accelKey: true});
     },
     function onSuccess() {
-      setTimeout(pasteQuote, 0);
+      SimpleTest.executeSoon(pasteQuote);
     },
     function onFailure() {
       SimpleTest.finish();
     },
-    "text/html"
+    // TODO: bug 1686012
+    SpecialPowers.isHeadless ? "text/unicode" : "text/html"
   );
 });
 
 </script>
 
 </pre>
 </body>
 </html>
new file mode 100644
--- /dev/null
+++ b/editor/libeditor/tests/test_pasting_in_root_element.xhtml
@@ -0,0 +1,74 @@
+<!DOCTYPE HTML>
+<html contenteditable="" xmlns="http://www.w3.org/1999/xhtml"><head>
+  <!-- https://bugzilla.mozilla.org/show_bug.cgi?id=1719387 -->
+  <meta charset="utf-8"/>
+  <title>Test to paste plaintext in the clipboard into the html element which does not have body element</title>
+  <script src="/tests/SimpleTest/SimpleTest.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+</head><span>Text outside body</span><script><![CDATA[
+"use strict";
+
+SimpleTest.waitForExplicitFinish();
+SimpleTest.waitForFocus(async () => {
+  info("Waiting for initializing clipboard...");
+  await SimpleTest.promiseClipboardChange(
+    "plain text",
+    () => {
+      SpecialPowers.clipboardCopyString("plain text");
+    }
+  );
+
+  focus();
+
+  function getInnerHTMLOfBody() {
+    return document.documentElement.innerHTML.replace(/\n/g, "")
+                                             .replace(/ xmlns="http:\/\/www.w3.org\/1999\/xhtml"/g, "")
+                                             .replace(/<head.+[\/]head>/g, "")
+                                             .replace(/<script.+[\/]script>/g, "");
+  }
+
+  try {
+    getSelection().collapse(document.documentElement, 1); // collapse to before the <span> element.
+    document.execCommand("insertText", false, "plain text");
+    todo_is(
+      getInnerHTMLOfBody(),
+      "plain text<span>Text outside body</span>",  // Chrome's result: "<span>plain textText outside body</span>"
+      "Typing text should insert the text before the <span> element"
+    );
+  } catch (ex) {
+    ok(false, `Failed to typing text due to ${ex}`);
+  } finally {
+    SpecialPowers.doCommand(window, "cmd_undo");
+  }
+
+  try {
+    getSelection().collapse(document.documentElement, 1); // collapse to before the <span> element.
+    SpecialPowers.doCommand(window, "cmd_paste");
+    is(
+      getInnerHTMLOfBody(),
+      "plain text<span>Text outside body</span>",  // Chrome's result: "<span>plain textText outside body</span>"
+      "\"cmd_paste\" should insert text in the clipboard before the <span> element"
+    );
+  } catch (ex) {
+    todo(false, `Failed to typing text due to ${ex}`);
+  } finally {
+    SpecialPowers.doCommand(window, "cmd_undo");
+  }
+
+  try {
+    getSelection().collapse(document.documentElement, 1); // collapse to before the <span> element.
+    SpecialPowers.doCommand(window, "cmd_pasteQuote");
+    is(
+      getInnerHTMLOfBody(),
+      "<blockquote type=\"cite\">plain text</blockquote><span>Text outside body</span>",
+      "\"cmd_pasteQuote\" should insert the text wrapping with <blockquote> element before the <span> element"
+    );
+  } catch (ex) {
+    ok(false, `Failed to typing text due to ${ex}`);
+  } finally {
+    SpecialPowers.doCommand(window, "cmd_undo");
+  }
+
+  SimpleTest.finish();
+});
+]]></script></html>
--- a/servo/components/style/style_adjuster.rs
+++ b/servo/components/style/style_adjuster.rs
@@ -830,17 +830,17 @@ impl<'a, 'b: 'a> StyleAdjuster<'a, 'b> {
     #[cfg(feature = "gecko")]
     fn adjust_for_marker_pseudo(&mut self) {
         use crate::values::computed::font::{FontFamily, FontSynthesis};
         use crate::values::computed::text::{LetterSpacing, WordSpacing};
         use crate::values::computed::counters::{Content};
 
         let is_legacy_marker = self.style.pseudo.map_or(false, |p| p.is_marker()) &&
             self.style.get_list().clone_list_style_type().is_bullet() &&
-	    self.style.get_counters().clone_content() == Content::Normal;
+            self.style.get_counters().clone_content() == Content::Normal;
         if !is_legacy_marker {
             return;
         }
         if !self.style.flags.get().contains(ComputedValueFlags::HAS_AUTHOR_SPECIFIED_FONT_FAMILY) {
             self.style.mutate_font().set_font_family(FontFamily::moz_bullet().clone());
 
             // FIXME(mats): We can remove this if support for font-synthesis is added to @font-face rules.
             // Then we can add it to the @font-face rule in html.css instead.
--- a/testing/specialpowers/content/SpecialPowersChild.jsm
+++ b/testing/specialpowers/content/SpecialPowersChild.jsm
@@ -707,16 +707,20 @@ class SpecialPowersChild extends JSWindo
   }
   get Cu() {
     return Cu;
   }
   get Cr() {
     return Cr;
   }
 
+  get isHeadless() {
+    return Cc["@mozilla.org/gfx/info;1"].getService(Ci.nsIGfxInfo).isHeadless;
+  }
+
   get addProfilerMarker() {
     return ChromeUtils.addProfilerMarker;
   }
 
   get DOMWindowUtils() {
     return this.contentWindow.windowUtils;
   }