Merge mozilla-central to fx-team

This commit is contained in:
Carsten "Tomcat" Book 2016-07-28 17:44:58 +02:00
commit 1e0260eddf
385 changed files with 9797 additions and 2894 deletions

View File

@ -19,6 +19,7 @@
#include "nsWinUtils.h"
#include "nsRange.h"
#include "mozilla/dom/BorrowedAttrInfo.h"
#include "mozilla/dom/Element.h"
using namespace mozilla;
@ -149,10 +150,11 @@ sdnAccessible::get_attributes(unsigned short aMaxAttribs,
aAttribValues[index] = aAttribNames[index] = nullptr;
nsAutoString attributeValue;
const nsAttrName* name = elm->GetAttrNameAt(index);
aNameSpaceIDs[index] = static_cast<short>(name->NamespaceID());
aAttribNames[index] = ::SysAllocString(name->LocalName()->GetUTF16String());
elm->GetAttr(name->NamespaceID(), name->LocalName(), attributeValue);
dom::BorrowedAttrInfo attr = elm->GetAttrInfoAt(index);
attr.mValue->ToString(attributeValue);
aNameSpaceIDs[index] = static_cast<short>(attr.mName->NamespaceID());
aAttribNames[index] = ::SysAllocString(attr.mName->LocalName()->GetUTF16String());
aAttribValues[index] = ::SysAllocString(attributeValue.get());
}

View File

@ -5617,7 +5617,7 @@ function middleMousePaste(event) {
function stripUnsafeProtocolOnPaste(pasteData) {
// Don't allow pasting javascript URIs since we don't support
// LOAD_FLAGS_DISALLOW_INHERIT_OWNER for those.
// LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL for those.
return pasteData.replace(/^(?:\s*javascript:)+/i, "");
}

View File

@ -46,6 +46,8 @@ XPCOMUtils.defineLazyGetter(this, "PageMenuChild", function() {
XPCOMUtils.defineLazyModuleGetter(this, "Feeds",
"resource:///modules/Feeds.jsm");
Cu.importGlobalProperties(["URL"]);
// TabChildGlobal
var global = this;
@ -792,9 +794,11 @@ addMessageListener("ContextMenu:MediaCommand", (message) => {
}
});
addMessageListener("ContextMenu:Canvas:ToDataURL", (message) => {
let dataURL = message.objects.target.toDataURL();
sendAsyncMessage("ContextMenu:Canvas:ToDataURL:Result", { dataURL });
addMessageListener("ContextMenu:Canvas:ToBlobURL", (message) => {
message.objects.target.toBlob((blob) => {
let blobURL = URL.createObjectURL(blob);
sendAsyncMessage("ContextMenu:Canvas:ToBlobURL:Result", { blobURL });
});
});
addMessageListener("ContextMenu:ReloadFrame", (message) => {

View File

@ -1141,16 +1141,16 @@ nsContextMenu.prototype = {
null, { target: this.target });
},
_canvasToDataURL: function(target) {
_canvasToBlobURL: function(target) {
let mm = this.browser.messageManager;
return new Promise(function(resolve) {
mm.sendAsyncMessage("ContextMenu:Canvas:ToDataURL", {}, { target });
mm.sendAsyncMessage("ContextMenu:Canvas:ToBlobURL", {}, { target });
let onMessage = (message) => {
mm.removeMessageListener("ContextMenu:Canvas:ToDataURL:Result", onMessage);
resolve(message.data.dataURL);
mm.removeMessageListener("ContextMenu:Canvas:ToBlobURL:Result", onMessage);
resolve(message.data.blobURL);
};
mm.addMessageListener("ContextMenu:Canvas:ToDataURL:Result", onMessage);
mm.addMessageListener("ContextMenu:Canvas:ToBlobURL:Result", onMessage);
});
},
@ -1158,8 +1158,8 @@ nsContextMenu.prototype = {
viewMedia: function(e) {
let referrerURI = gContextMenuContentData.documentURIObject;
if (this.onCanvas) {
this._canvasToDataURL(this.target).then(function(dataURL) {
openUILink(dataURL, e, { disallowInheritPrincipal: true,
this._canvasToBlobURL(this.target).then(function(blobURL) {
openUILink(blobURL, e, { disallowInheritPrincipal: true,
referrerURI: referrerURI });
}, Cu.reportError);
}
@ -1436,8 +1436,8 @@ nsContextMenu.prototype = {
let isPrivate = PrivateBrowsingUtils.isBrowserPrivate(this.browser);
if (this.onCanvas) {
// Bypass cache, since it's a data: URL.
this._canvasToDataURL(this.target).then(function(dataURL) {
saveImageURL(dataURL, "canvas.png", "SaveImageTitle",
this._canvasToBlobURL(this.target).then(function(blobURL) {
saveImageURL(blobURL, "canvas.png", "SaveImageTitle",
true, false, referrerURI, null, null, null,
isPrivate);
}, Cu.reportError);

View File

@ -3035,8 +3035,6 @@
let wasFocused = (document.activeElement == this.mCurrentTab);
aIndex = aIndex < aTab._tPos ? aIndex: aIndex+1;
this.mCurrentTab._logicallySelected = false;
this.mCurrentTab._visuallySelected = false;
// invalidate cache
this._visibleTabs = null;
@ -3047,11 +3045,25 @@
for (let i = 0; i < this.tabs.length; i++) {
this.tabs[i]._tPos = i;
this.tabs[i]._logicallySelected = false;
this.tabs[i]._visuallySelected = false;
this.tabs[i]._selected = false;
}
this.mCurrentTab._logicallySelected = true;
this.mCurrentTab._visuallySelected = true;
// If we're in the midst of an async tab switch while calling
// moveTabTo, we can get into a case where _visuallySelected
// is set to true on two different tabs.
//
// What we want to do in moveTabTo is to remove logical selection
// from all tabs, and then re-add logical selection to mCurrentTab
// (and visual selection as well if we're not running with e10s, which
// setting _selected will do automatically).
//
// If we're running with e10s, then the visual selection will not
// be changed, which is fine, since if we weren't in the midst of a
// tab switch, the previously visually selected tab should still be
// correct, and if we are in the midst of a tab switch, then the async
// tab switcher will set the visually selected tab once the tab switch
// has completed.
this.mCurrentTab._selected = true;
if (wasFocused)
this.mCurrentTab.focus();
@ -6288,26 +6300,16 @@
</setter>
</property>
<property name="_logicallySelected">
<setter>
<![CDATA[
if (val)
this.setAttribute("selected", "true");
else
this.removeAttribute("selected");
return val;
]]>
</setter>
</property>
<property name="_selected">
<setter>
<![CDATA[
// in e10s we want to only pseudo-select a tab before its rendering is done, so that
// the rest of the system knows that the tab is selected, but we don't want to update its
// visual status to selected until after we receive confirmation that its content has painted.
this._logicallySelected = val;
if (val)
this.setAttribute("selected", "true");
else
this.removeAttribute("selected");
// If we're non-e10s we should update the visual selection as well at the same time,
// *or* if we're e10s and the visually selected tab isn't changing, in which case the

View File

@ -335,12 +335,12 @@ function openLinkIn(url, where, params) {
flags |= Ci.nsIWebNavigation.LOAD_FLAGS_FIXUP_SCHEME_TYPOS;
}
// LOAD_FLAGS_DISALLOW_INHERIT_OWNER isn't supported for javascript URIs,
// LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL isn't supported for javascript URIs,
// i.e. it causes them not to load at all. Callers should strip
// "javascript:" from pasted strings to protect users from malicious URIs
// (see stripUnsafeProtocolOnPaste).
if (aDisallowInheritPrincipal && !(uriObj && uriObj.schemeIs("javascript"))) {
flags |= Ci.nsIWebNavigation.LOAD_FLAGS_DISALLOW_INHERIT_OWNER;
flags |= Ci.nsIWebNavigation.LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL;
}
if (aAllowPopups) {

View File

@ -9,6 +9,7 @@ support-files =
worker.js
[browser_aboutURLs.js]
skip-if = (debug && (os == "win" || os == "linux")) # intermittent negative leak bug 1271182
[browser_eme.js]
[browser_favicon.js]
[browser_forgetaboutsite.js]

View File

@ -4,11 +4,13 @@
const {classes: Cc, interfaces: Ci, utils: Cu} = Components;
Cu.import("resource://gre/modules/PlacesUtils.jsm");
var Bookmarks = PlacesUtils.bookmarks;
Cu.import("resource://gre/modules/ExtensionUtils.jsm");
XPCOMUtils.defineLazyGetter(this, "Bookmarks", () => {
Cu.import("resource://gre/modules/PlacesUtils.jsm");
return PlacesUtils.bookmarks;
});
XPCOMUtils.defineLazyModuleGetter(this, "Task",
"resource://gre/modules/Task.jsm");

View File

@ -77,10 +77,12 @@ CommandList.prototype = {
for (let name of Object.keys(manifest.commands)) {
let command = manifest.commands[name];
let shortcut = command.suggested_key[os] || command.suggested_key.default;
commands.set(name, {
description: command.description,
shortcut: shortcut.replace(/\s+/g, ""),
});
if (shortcut) {
commands.set(name, {
description: command.description,
shortcut: shortcut.replace(/\s+/g, ""),
});
}
}
return commands;
},

View File

@ -5,7 +5,12 @@
const {classes: Cc, interfaces: Ci, utils: Cu} = Components;
Cu.import("resource://gre/modules/ExtensionUtils.jsm");
Cu.import("resource://gre/modules/PlacesUtils.jsm");
XPCOMUtils.defineLazyGetter(this, "History", () => {
Cu.import("resource://gre/modules/PlacesUtils.jsm");
return PlacesUtils.history;
});
XPCOMUtils.defineLazyModuleGetter(this, "EventEmitter",
"resource://devtools/shared/event-emitter.js");
XPCOMUtils.defineLazyModuleGetter(this, "NetUtil",
@ -16,13 +21,13 @@ const {
SingletonEventManager,
} = ExtensionUtils;
const History = PlacesUtils.history;
let nsINavHistoryService = Ci.nsINavHistoryService;
const TRANSITION_TO_TRANSITION_TYPES_MAP = new Map([
["link", History.TRANSITION_LINK],
["typed", History.TRANSITION_TYPED],
["auto_bookmark", History.TRANSITION_BOOKMARK],
["auto_subframe", History.TRANSITION_EMBED],
["manual_subframe", History.TRANSITION_FRAMED_LINK],
["link", nsINavHistoryService.TRANSITION_LINK],
["typed", nsINavHistoryService.TRANSITION_TYPED],
["auto_bookmark", nsINavHistoryService.TRANSITION_BOOKMARK],
["auto_subframe", nsINavHistoryService.TRANSITION_EMBED],
["manual_subframe", nsINavHistoryService.TRANSITION_FRAMED_LINK],
]);
let TRANSITION_TYPE_TO_TRANSITIONS_MAP = new Map();
@ -123,7 +128,7 @@ function getObserver() {
},
};
EventEmitter.decorate(_observer);
PlacesUtils.history.addObserver(_observer, false);
History.addObserver(_observer, false);
}
return _observer;
}

View File

@ -0,0 +1,22 @@
# scripts
category webextension-scripts bookmarks chrome://browser/content/ext-bookmarks.js
category webextension-scripts browserAction chrome://browser/content/ext-browserAction.js
category webextension-scripts commands chrome://browser/content/ext-commands.js
category webextension-scripts contextMenus chrome://browser/content/ext-contextMenus.js
category webextension-scripts desktop-runtime chrome://browser/content/ext-desktop-runtime.js
category webextension-scripts history chrome://browser/content/ext-history.js
category webextension-scripts pageAction chrome://browser/content/ext-pageAction.js
category webextension-scripts tabs chrome://browser/content/ext-tabs.js
category webextension-scripts utils chrome://browser/content/ext-utils.js
category webextension-scripts windows chrome://browser/content/ext-windows.js
# schemas
category webextension-schemas bookmarks chrome://browser/content/schemas/bookmarks.json
category webextension-schemas browser_action chrome://browser/content/schemas/browser_action.json
category webextension-schemas commands chrome://browser/content/schemas/commands.json
category webextension-schemas context_menus chrome://browser/content/schemas/context_menus.json
category webextension-schemas context_menus_internal chrome://browser/content/schemas/context_menus_internal.json
category webextension-schemas history chrome://browser/content/schemas/history.json
category webextension-schemas page_action chrome://browser/content/schemas/page_action.json
category webextension-schemas tabs chrome://browser/content/schemas/tabs.json
category webextension-schemas windows chrome://browser/content/schemas/windows.json

View File

@ -6,6 +6,10 @@
JAR_MANIFESTS += ['jar.mn']
EXTRA_COMPONENTS += [
'extensions-browser.manifest',
]
DIRS += ['schemas']
BROWSER_CHROME_MANIFESTS += ['test/browser/browser.ini']

View File

@ -15,8 +15,6 @@ XPCOMUtils.defineLazyModuleGetter(this, "Schemas",
XPCOMUtils.defineLazyModuleGetter(this, "Services",
"resource://gre/modules/Services.jsm");
Cu.import("resource://gre/modules/ExtensionManagement.jsm");
/* exported normalizeManifest */
let BASE_MANIFEST = {
@ -28,11 +26,8 @@ let BASE_MANIFEST = {
"version": "0",
};
ExtensionManagement.registerSchema("chrome://browser/content/schemas/commands.json");
function* normalizeManifest(manifest, baseManifest = BASE_MANIFEST) {
const {Management} = Cu.import("resource://gre/modules/Extension.jsm", {});
yield Management.lazyInit();
let errors = [];

View File

@ -158,9 +158,6 @@ XPCOMUtils.defineLazyModuleGetter(this, "AddonWatcher",
XPCOMUtils.defineLazyModuleGetter(this, "LightweightThemeManager",
"resource://gre/modules/LightweightThemeManager.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "ExtensionManagement",
"resource://gre/modules/ExtensionManagement.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "ShellService",
"resource:///modules/ShellService.jsm");
@ -560,29 +557,15 @@ BrowserGlue.prototype = {
os.addObserver(this, AddonWatcher.TOPIC_SLOW_ADDON_DETECTED, false);
}
ExtensionManagement.registerScript("chrome://browser/content/ext-bookmarks.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-browserAction.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-commands.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-contextMenus.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-desktop-runtime.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-history.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-pageAction.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-tabs.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-utils.js");
ExtensionManagement.registerScript("chrome://browser/content/ext-windows.js");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/bookmarks.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/browser_action.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/commands.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/context_menus.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/context_menus_internal.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/history.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/page_action.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/tabs.json");
ExtensionManagement.registerSchema("chrome://browser/content/schemas/windows.json");
this._flashHangCount = 0;
this._firstWindowReady = new Promise(resolve => this._firstWindowLoaded = resolve);
if (AppConstants.platform == "win" ||
AppConstants.platform == "macosx") {
// Handles prompting to inform about incompatibilites when accessibility
// and e10s are active together.
E10SAccessibilityCheck.init();
}
},
// cleanup (called on application shutdown)
@ -1356,12 +1339,7 @@ BrowserGlue.prototype = {
}
}
if (AppConstants.platform == "win" ||
AppConstants.platform == "macosx") {
// Handles prompting to inform about incompatibilites when accessibility
// and e10s are active together.
E10SAccessibilityCheck.init();
}
E10SAccessibilityCheck.onWindowsRestored();
},
_createExtraDefaultProfile: function () {
@ -3024,6 +3002,10 @@ var DefaultBrowserCheck = {
};
var E10SAccessibilityCheck = {
// tracks when an a11y init observer fires prior to the
// first window being opening.
_wantsPrompt: false,
init: function() {
Services.obs.addObserver(this, "a11y-init-or-shutdown", true);
Services.obs.addObserver(this, "quit-application-granted", true);
@ -3056,6 +3038,13 @@ var E10SAccessibilityCheck = {
}
},
onWindowsRestored: function() {
if (this._wantsPrompt) {
this._wantsPrompt = false;
this._showE10sAccessibilityWarning();
}
},
_warnedAboutAccessibility: false,
_showE10sAccessibilityWarning: function() {
@ -3077,11 +3066,14 @@ var E10SAccessibilityCheck = {
this._warnedAboutAccessibility = true;
let win = RecentWindow.getMostRecentBrowserWindow();
let browser = win.gBrowser.selectedBrowser;
if (!win) {
Services.console.logStringMessage("Accessibility support is partially disabled due to compatibility issues with new features.");
if (!win || !win.gBrowser || !win.gBrowser.selectedBrowser) {
Services.console.logStringMessage(
"Accessibility support is partially disabled due to compatibility issues with new features.");
this._wantsPrompt = true;
this._warnedAboutAccessibility = false;
return;
}
let browser = win.gBrowser.selectedBrowser;
// We disable a11y for content and prompt on the chrome side letting
// a11y users know they need to disable e10s and restart.

View File

@ -170,16 +170,16 @@ var SessionHistoryInternal = {
entry.scroll = x.value + "," + y.value;
}
// Collect owner data for the current history entry.
// Collect triggeringPrincipal data for the current history entry.
try {
let owner = this.serializeOwner(shEntry);
if (owner) {
entry.owner_b64 = owner;
let triggeringPrincipal = this.serializeTriggeringPrincipal(shEntry);
if (triggeringPrincipal) {
entry.triggeringPrincipal_b64 = triggeringPrincipal;
}
} catch (ex) {
// Not catching anything specific here, just possible errors
// from writeCompoundObject() and the like.
debug("Failed serializing owner data: " + ex);
debug("Failed serializing triggeringPrincipal data: " + ex);
}
entry.docIdentifier = shEntry.BFCacheEntry.ID;
@ -219,14 +219,14 @@ var SessionHistoryInternal = {
},
/**
* Serialize owner data contained in the given session history entry.
* Serialize triggeringPrincipal data contained in the given session history entry.
*
* @param shEntry
* The session history entry.
* @return The base64 encoded owner data.
* @return The base64 encoded triggeringPrincipal data.
*/
serializeOwner: function (shEntry) {
if (!shEntry.owner) {
serializeTriggeringPrincipal: function (shEntry) {
if (!shEntry.triggeringPrincipal) {
return null;
}
@ -235,20 +235,20 @@ var SessionHistoryInternal = {
let pipe = Cc["@mozilla.org/pipe;1"].createInstance(Ci.nsIPipe);
pipe.init(false, false, 0, 0xffffffff, null);
binaryStream.setOutputStream(pipe.outputStream);
binaryStream.writeCompoundObject(shEntry.owner, Ci.nsISupports, true);
binaryStream.writeCompoundObject(shEntry.triggeringPrincipal, Ci.nsIPrincipal, true);
binaryStream.close();
// Now we want to read the data from the pipe's input end and encode it.
let scriptableStream = Cc["@mozilla.org/binaryinputstream;1"].
createInstance(Ci.nsIBinaryInputStream);
scriptableStream.setInputStream(pipe.inputStream);
let ownerBytes =
let triggeringPrincipalBytes =
scriptableStream.readByteArray(scriptableStream.available());
// We can stop doing base64 encoding once our serialization into JSON
// is guaranteed to handle all chars in strings, including embedded
// nulls.
return btoa(String.fromCharCode.apply(null, ownerBytes));
return btoa(String.fromCharCode.apply(null, triggeringPrincipalBytes));
},
/**
@ -379,16 +379,24 @@ var SessionHistoryInternal = {
}
}
// The field entry.owner_b64 got renamed to entry.triggeringPricipal_b64 in
// Bug 1286472. To remain backward compatible we still have to support that
// field for a few cycles before we can remove it within Bug 1289785.
if (entry.owner_b64) {
var ownerInput = Cc["@mozilla.org/io/string-input-stream;1"].
createInstance(Ci.nsIStringInputStream);
var binaryData = atob(entry.owner_b64);
ownerInput.setData(binaryData, binaryData.length);
entry.triggeringPricipal_b64 = entry.owner_b64;
delete entry.owner_b64;
}
if (entry.triggeringPrincipal_b64) {
var triggeringPrincipalInput = Cc["@mozilla.org/io/string-input-stream;1"]
.createInstance(Ci.nsIStringInputStream);
var binaryData = atob(entry.triggeringPrincipal_b64);
triggeringPrincipalInput.setData(binaryData, binaryData.length);
var binaryStream = Cc["@mozilla.org/binaryinputstream;1"].
createInstance(Ci.nsIObjectInputStream);
binaryStream.setInputStream(ownerInput);
binaryStream.setInputStream(triggeringPrincipalInput);
try { // Catch possible deserialization exceptions
shEntry.owner = binaryStream.readObject(true);
shEntry.triggeringPrincipal = binaryStream.readObject(true);
} catch (ex) { debug(ex); }
}

View File

@ -2,6 +2,7 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* 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 {classes: Cc, interfaces: Ci, utils: Cu} = Components;
@ -14,13 +15,18 @@ const TEST_THRESHOLD = {
"beta" : 0.5, // 50%
};
const ADDON_ROLLOUT_POLICY = {
"beta" : "2a", // Set 2 + any WebExtension
};
const PREF_COHORT_SAMPLE = "e10s.rollout.cohortSample";
const PREF_COHORT_NAME = "e10s.rollout.cohort";
const PREF_E10S_OPTED_IN = "browser.tabs.remote.autostart";
const PREF_E10S_FORCE_ENABLED = "browser.tabs.remote.force-enable";
const PREF_E10S_FORCE_DISABLED = "browser.tabs.remote.force-disable";
const PREF_TOGGLE_E10S = "browser.tabs.remote.autostart.2";
const PREF_E10S_ADDON_POLICY = "extensions.e10s.rollout.policy";
const PREF_E10S_HAS_NONEXEMPT_ADDON = "extensions.e10s.rollout.hasAddon";
function startup() {
// In theory we only need to run this once (on install()), but
@ -53,20 +59,38 @@ function defineCohort() {
return;
}
let addonPolicy = "unknown";
if (updateChannel in ADDON_ROLLOUT_POLICY) {
addonPolicy = ADDON_ROLLOUT_POLICY[updateChannel];
Preferences.set(PREF_E10S_ADDON_POLICY, ADDON_ROLLOUT_POLICY[updateChannel]);
// This is also the proper place to set the blocklist pref
// in case it is necessary.
} else {
Preferences.reset(PREF_E10S_ADDON_POLICY);
}
let userOptedOut = optedOut();
let userOptedIn = optedIn();
let disqualified = (Services.appinfo.multiprocessBlockPolicy != 0);
let testGroup = (getUserSample() < TEST_THRESHOLD[updateChannel]);
let hasNonExemptAddon = Preferences.get(PREF_E10S_HAS_NONEXEMPT_ADDON, false);
let cohortPrefix = "";
if (disqualified) {
cohortPrefix = "disqualified-";
} else if (hasNonExemptAddon) {
cohortPrefix = `addons-set${addonPolicy}-`;
}
if (userOptedOut) {
setCohort("optedOut");
} else if (userOptedIn) {
setCohort("optedIn");
} else if (testGroup) {
setCohort(disqualified ? "disqualified-test" : "test");
setCohort(`${cohortPrefix}test`);
Preferences.set(PREF_TOGGLE_E10S, true);
} else {
setCohort(disqualified ? "disqualified-control" : "control");
setCohort(`${cohortPrefix}control`);
Preferences.reset(PREF_TOGGLE_E10S);
}
}

View File

@ -574,6 +574,10 @@
@RESPATH@/components/PACGenerator.js
@RESPATH@/components/PACGenerator.manifest
; [Extensions]
@RESPATH@/components/extensions-toolkit.manifest
@RESPATH@/browser/components/extensions-browser.manifest
; Modules
@RESPATH@/browser/modules/*
@RESPATH@/modules/*

View File

@ -47,6 +47,36 @@ def windows_sdk_dir(value, host):
r'HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows Kits\Installed Roots'
r'\KitsRoot*'))
# The Windows SDK 8.1 and 10 have different layouts. The former has
# $SDK/include/$subdir, while the latter has $SDK/include/$version/$subdir.
# The vcvars* scripts don't actually care about the version, they just take
# the last.
@imports('os')
@imports('re')
@imports(_from='__builtin__', _import='sorted')
@imports(_from='__builtin__', _import='WindowsError')
def get_include_dir(sdk, subdir):
base = os.path.join(sdk, 'include')
try:
subdirs = [d for d in os.listdir(base)
if os.path.isdir(os.path.join(base, d))]
except WindowsError:
subdirs = []
if not subdirs:
return None
if subdir in subdirs:
return os.path.join(base, subdir)
# At this point, either we have an incomplete or invalid SDK directory,
# or we exclusively have version numbers in subdirs.
versions = sorted((Version(d) for d in subdirs), reverse=True)
# Version('non-number').major is 0, so if the biggest version we have is
# 0, we have a problem.
if versions[0].major == 0:
return None
path = os.path.join(base, str(versions[0]), subdir)
return path if os.path.isdir(path) else None
@imports(_from='mozbuild.shellutil', _import='quote')
def valid_windows_sdk_dir_result(value):
if value:
@ -63,9 +93,9 @@ def valid_windows_sdk_dir(compiler, windows_sdk_dir, target_version,
windows_sdk_dir_env = windows_sdk_dir_env[0]
sdks = {}
for d in windows_sdk_dir:
um_dir = os.path.join(d, 'include', 'um')
shared_dir = os.path.join(d, 'include', 'shared')
if os.path.isdir(um_dir) and os.path.isdir(shared_dir):
um_dir = get_include_dir(d, 'um')
shared_dir = get_include_dir(d, 'shared')
if um_dir and shared_dir:
check = dedent('''\
#include <winsdkver.h>
WINVER_MAXVER

View File

@ -367,8 +367,7 @@ nsScriptSecurityManager::GetChannelResultPrincipal(nsIChannel* aChannel,
// Check if SEC_FORCE_INHERIT_PRINCIPAL was dropped because of
// sandboxing:
if (loadInfo->GetLoadingSandboxed() &&
(loadInfo->GetSecurityFlags() &
nsILoadInfo::SEC_FORCE_INHERIT_PRINCIPAL_WAS_DROPPED)) {
loadInfo->GetForceInheritPrincipalDropped()) {
forceInterit = true;
}
}

View File

@ -2092,7 +2092,7 @@ Toolbox.prototype = {
this._threadClient = null;
// We need to grab a reference to win before this._host is destroyed.
let win = this.frame.ownerGlobal;
let win = this.frame.ownerDocument.defaultView;
if (this._requisition) {
CommandUtils.destroyRequisition(this._requisition, this.target);

View File

@ -23,7 +23,7 @@ responsive.exit=Close Responsive Design Mode
responsive.deviceListLoading=Loading…
# LOCALIZATION NOTE (responsive.deviceListError): placeholder text for
# device selector when an error occured
# device selector when an error occurred
responsive.deviceListError=No list available
# LOCALIZATION NOTE (responsive.done): button text in the device list modal

View File

@ -119,7 +119,7 @@ const SPECIAL_VALUES = new Set(["none", "unset", "initial", "inherit"]);
*/
function CSSFilterEditorWidget(el, value = "") {
this.doc = el.ownerDocument;
this.win = this.doc.ownerGlobal;
this.win = this.doc.defaultView;
this.el = el;
this._addButtonClick = this._addButtonClick.bind(this);

View File

@ -1778,7 +1778,7 @@ EditableFieldsEngine.prototype = {
* The node to copy styles to.
*/
copyStyles: function (source, destination) {
let style = source.ownerGlobal.getComputedStyle(source);
let style = source.ownerDocument.defaultView.getComputedStyle(source);
let props = [
"borderTopWidth",
"borderRightWidth",

View File

@ -957,7 +957,7 @@ StyleEditorUI.prototype = {
*/
_launchResponsiveMode: Task.async(function* (options = {}) {
let tab = this._target.tab;
let win = this._target.tab.ownerGlobal;
let win = this._target.tab.ownerDocument.defaultView;
yield ResponsiveUIManager.runIfNeeded(win, tab);
if (options.width && options.height) {

View File

@ -78,7 +78,7 @@ const nodeFilterConstants = require("devtools/shared/dom-node-filter-constants")
loader.lazyRequireGetter(this, "CSS", "CSS");
const {EventParsers} = require("devtools/shared/event-parsers");
const {EventParsers} = require("devtools/server/event-parsers");
const {nodeSpec, nodeListSpec, walkerSpec, inspectorSpec} = require("devtools/shared/specs/inspector");
const FONT_FAMILY_PREVIEW_TEXT = "The quick brown fox jumps over the lazy dog";

View File

@ -33,6 +33,7 @@ DevToolsModules(
'content-globals.js',
'content-server.jsm',
'css-logic.js',
'event-parsers.js',
'main.js',
'primitive.js',
'service-worker-child.js',

View File

@ -1457,7 +1457,7 @@ folderOpenDirResult=Opened %1$S
# use of 'mdn' command.
mdnDesc=Retrieve documentation from MDN
# LOCALIZATION NOTE (mdnCssDesc) A very short string used to describe the
# result of the 'mdn css' commmand.
# result of the 'mdn css' command.
mdnCssDesc=Retrieve documentation about a given CSS property name from MDN
# LOCALIZATION NOTE (mdnCssProp) String used to describe the 'property name'
# parameter used in the 'mdn css' command.

View File

@ -53,7 +53,6 @@ DevToolsModules(
'dom-node-constants.js',
'dom-node-filter-constants.js',
'event-emitter.js',
'event-parsers.js',
'indentation.js',
'Loader.jsm',
'Parser.jsm',

View File

@ -1260,9 +1260,9 @@ nsDocShell::LoadURI(nsIURI* aURI,
bool loadReplace = false;
nsCOMPtr<nsIInputStream> postStream;
nsCOMPtr<nsIInputStream> headersStream;
nsCOMPtr<nsISupports> owner;
bool inheritOwner = false;
bool ownerIsExplicit = false;
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
bool inheritPrincipal = false;
bool principalIsExplicit = false;
bool sendReferrer = true;
uint32_t referrerPolicy = mozilla::net::RP_Default;
bool isSrcdoc = false;
@ -1291,9 +1291,9 @@ nsDocShell::LoadURI(nsIURI* aURI,
// Get the appropriate loadType from nsIDocShellLoadInfo type
loadType = ConvertDocShellLoadInfoToLoadType(lt);
aLoadInfo->GetOwner(getter_AddRefs(owner));
aLoadInfo->GetInheritOwner(&inheritOwner);
aLoadInfo->GetOwnerIsExplicit(&ownerIsExplicit);
aLoadInfo->GetTriggeringPrincipal(getter_AddRefs(triggeringPrincipal));
aLoadInfo->GetInheritPrincipal(&inheritPrincipal);
aLoadInfo->GetPrincipalIsExplicit(&principalIsExplicit);
aLoadInfo->GetSHEntry(getter_AddRefs(shEntry));
aLoadInfo->GetTarget(getter_Copies(target));
aLoadInfo->GetPostDataStream(getter_AddRefs(postStream));
@ -1449,9 +1449,9 @@ nsDocShell::LoadURI(nsIURI* aURI,
// Perform the load...
// We need an owner (a referring principal).
// We need a triggeringPrincipal (a referring principal).
//
// If ownerIsExplicit is not set there are 4 possibilities:
// If principalIsExplicit is not set there are 4 possibilities:
// (1) If the system principal or an expanded principal was passed
// in and we're a typeContent docshell, inherit the principal
// from the current document instead.
@ -1459,37 +1459,33 @@ nsDocShell::LoadURI(nsIURI* aURI,
// use that principal.
// (3) If the caller has allowed inheriting from the current document,
// or if we're being called from system code (eg chrome JS or pure
// C++) then inheritOwner should be true and InternalLoad will get
// an owner from the current document. If none of these things are
// C++) then inheritPrincipal should be true and InternalLoad will get
// a principal from the current document. If none of these things are
// true, then
// (4) we pass a null owner into the channel, and an owner will be
// (4) we don't pass a principal into the channel, and a principal will be
// created later from the channel's internal data.
//
// If ownerIsExplicit *is* set, there are 4 possibilities
// If principalIsExplicit *is* set, there are 4 possibilities
// (1) If the system principal or an expanded principal was passed in
// and we're a typeContent docshell, return an error.
// (2) In all other cases when the principal passed in is not null,
// use that principal.
// (3) If the caller has allowed inheriting from the current document,
// then inheritOwner should be true and InternalLoad will get an owner
// from the current document. If none of these things are true, then
// (4) we pass a null owner into the channel, and an owner will be
// then inheritPrincipal should be true and InternalLoad will get
// a principal from the current document. If none of these things are
// true, then
// (4) we dont' pass a principal into the channel, and a principal will be
// created later from the channel's internal data.
//
// NOTE: This all only works because the only thing the owner is used
// for in InternalLoad is data:, javascript:, and about:blank
// URIs. For other URIs this would all be dead wrong!
nsCOMPtr<nsIPrincipal> ownerPrincipal = do_QueryInterface(owner);
if (owner && mItemType != typeChrome) {
if (nsContentUtils::IsSystemPrincipal(ownerPrincipal)) {
if (ownerIsExplicit) {
nsCOMPtr<nsIPrincipal> principalToInheritAttributesFrom = triggeringPrincipal;
if (triggeringPrincipal && mItemType != typeChrome) {
if (nsContentUtils::IsSystemPrincipal(principalToInheritAttributesFrom)) {
if (principalIsExplicit) {
return NS_ERROR_DOM_SECURITY_ERR;
}
owner = nullptr;
inheritOwner = true;
} else if (nsContentUtils::IsExpandedPrincipal(ownerPrincipal)) {
if (ownerIsExplicit) {
triggeringPrincipal = nullptr;
inheritPrincipal = true;
} else if (nsContentUtils::IsExpandedPrincipal(principalToInheritAttributesFrom)) {
if (principalIsExplicit) {
return NS_ERROR_DOM_SECURITY_ERR;
}
// Don't inherit from the current page. Just do the safe thing
@ -1497,26 +1493,26 @@ nsDocShell::LoadURI(nsIURI* aURI,
//
// We didn't inherit OriginAttributes here as ExpandedPrincipal doesn't
// have origin attributes.
owner = nsNullPrincipal::CreateWithInheritedAttributes(this);
inheritOwner = false;
triggeringPrincipal = nsNullPrincipal::CreateWithInheritedAttributes(this);
inheritPrincipal = false;
}
}
if (!owner && !inheritOwner && !ownerIsExplicit) {
if (!triggeringPrincipal && !inheritPrincipal && !principalIsExplicit) {
// See if there's system or chrome JS code running
inheritOwner = nsContentUtils::LegacyIsCallerChromeOrNativeCode();
inheritPrincipal = nsContentUtils::LegacyIsCallerChromeOrNativeCode();
}
if (aLoadFlags & LOAD_FLAGS_DISALLOW_INHERIT_OWNER) {
inheritOwner = false;
owner = ownerPrincipal ?
nsNullPrincipal::CreateWithInheritedAttributes(ownerPrincipal) :
nsNullPrincipal::CreateWithInheritedAttributes(this);
if (aLoadFlags & LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL) {
inheritPrincipal = false;
triggeringPrincipal = principalToInheritAttributesFrom ?
nsNullPrincipal::CreateWithInheritedAttributes(principalToInheritAttributesFrom) :
nsNullPrincipal::CreateWithInheritedAttributes(this);
}
uint32_t flags = 0;
if (inheritOwner) {
flags |= INTERNAL_LOAD_FLAGS_INHERIT_OWNER;
if (inheritPrincipal) {
flags |= INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL;
}
if (!sendReferrer) {
@ -1548,7 +1544,7 @@ nsDocShell::LoadURI(nsIURI* aURI,
loadReplace,
referrer,
referrerPolicy,
owner,
triggeringPrincipal,
flags,
target.get(),
nullptr, // No type hint
@ -1595,24 +1591,21 @@ nsDocShell::LoadStream(nsIInputStream* aStream, nsIURI* aURI,
}
uint32_t loadType = LOAD_NORMAL;
nsCOMPtr<nsIPrincipal> requestingPrincipal;
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
if (aLoadInfo) {
nsDocShellInfoLoadType lt = nsIDocShellLoadInfo::loadNormal;
(void)aLoadInfo->GetLoadType(&lt);
// Get the appropriate LoadType from nsIDocShellLoadInfo type
loadType = ConvertDocShellLoadInfoToLoadType(lt);
nsCOMPtr<nsISupports> owner;
aLoadInfo->GetOwner(getter_AddRefs(owner));
requestingPrincipal = do_QueryInterface(owner);
aLoadInfo->GetTriggeringPrincipal(getter_AddRefs(triggeringPrincipal));
}
NS_ENSURE_SUCCESS(Stop(nsIWebNavigation::STOP_NETWORK), NS_ERROR_FAILURE);
mLoadType = loadType;
if (!requestingPrincipal) {
requestingPrincipal = nsContentUtils::GetSystemPrincipal();
if (!triggeringPrincipal) {
triggeringPrincipal = nsContentUtils::GetSystemPrincipal();
}
// build up a channel for this stream.
@ -1620,7 +1613,7 @@ nsDocShell::LoadStream(nsIInputStream* aStream, nsIURI* aURI,
nsresult rv = NS_NewInputStreamChannel(getter_AddRefs(channel),
uri,
aStream,
requestingPrincipal,
triggeringPrincipal,
nsILoadInfo::SEC_NORMAL,
nsIContentPolicy::TYPE_OTHER,
aContentType,
@ -5358,7 +5351,7 @@ nsDocShell::LoadErrorPage(nsIURI* aURI, const char16_t* aURL,
return InternalLoad(errorPageURI, nullptr, false, nullptr,
mozilla::net::RP_Default,
nullptr, INTERNAL_LOAD_FLAGS_INHERIT_OWNER, nullptr,
nullptr, INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL, nullptr,
nullptr, NullString(), nullptr, nullptr, LOAD_ERROR_PAGE,
nullptr, true, NullString(), this, nullptr, nullptr,
nullptr);
@ -6772,10 +6765,10 @@ nsDocShell::ForceRefreshURI(nsIURI* aURI, int32_t aDelay, bool aMetaRefresh)
*/
loadInfo->SetReferrer(mCurrentURI);
/* Don't ever "guess" on which owner to use to avoid picking
* the current owner.
/* Don't ever "guess" on which principal to use to avoid picking
* the current principal.
*/
loadInfo->SetOwnerIsExplicit(true);
loadInfo->SetPrincipalIsExplicit(true);
/* Check if this META refresh causes a redirection
* to another site.
@ -9584,7 +9577,7 @@ public:
InternalLoadEvent(nsDocShell* aDocShell, nsIURI* aURI,
nsIURI* aOriginalURI, bool aLoadReplace,
nsIURI* aReferrer, uint32_t aReferrerPolicy,
nsISupports* aOwner, uint32_t aFlags,
nsIPrincipal* aTriggeringPrincipal, uint32_t aFlags,
const char* aTypeHint, nsIInputStream* aPostData,
nsIInputStream* aHeadersData, uint32_t aLoadType,
nsISHEntry* aSHEntry, bool aFirstParty,
@ -9597,7 +9590,7 @@ public:
, mLoadReplace(aLoadReplace)
, mReferrer(aReferrer)
, mReferrerPolicy(aReferrerPolicy)
, mOwner(aOwner)
, mTriggeringPrincipal(aTriggeringPrincipal)
, mPostData(aPostData)
, mHeadersData(aHeadersData)
, mSHEntry(aSHEntry)
@ -9620,7 +9613,7 @@ public:
mLoadReplace,
mReferrer,
mReferrerPolicy,
mOwner, mFlags,
mTriggeringPrincipal, mFlags,
nullptr, mTypeHint.get(),
NullString(), mPostData, mHeadersData,
mLoadType, mSHEntry, mFirstParty,
@ -9640,7 +9633,7 @@ private:
bool mLoadReplace;
nsCOMPtr<nsIURI> mReferrer;
uint32_t mReferrerPolicy;
nsCOMPtr<nsISupports> mOwner;
nsCOMPtr<nsIPrincipal> mTriggeringPrincipal;
nsCOMPtr<nsIInputStream> mPostData;
nsCOMPtr<nsIInputStream> mHeadersData;
nsCOMPtr<nsISHEntry> mSHEntry;
@ -9707,7 +9700,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
bool aLoadReplace,
nsIURI* aReferrer,
uint32_t aReferrerPolicy,
nsISupports* aOwner,
nsIPrincipal* aTriggeringPrincipal,
uint32_t aFlags,
const char16_t* aWindowTarget,
const char* aTypeHint,
@ -9825,7 +9818,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
}
// XXXbz would be nice to know the loading principal here... but we don't
nsCOMPtr<nsIPrincipal> loadingPrincipal = do_QueryInterface(aOwner);
nsCOMPtr<nsIPrincipal> loadingPrincipal = aTriggeringPrincipal;
if (!loadingPrincipal && aReferrer) {
rv =
CreatePrincipalFromReferrer(aReferrer, getter_AddRefs(loadingPrincipal));
@ -9848,26 +9841,26 @@ nsDocShell::InternalLoad(nsIURI* aURI,
return NS_ERROR_CONTENT_BLOCKED;
}
nsCOMPtr<nsISupports> owner(aOwner);
nsCOMPtr<nsIPrincipal> triggeringPrincipal = aTriggeringPrincipal;
//
// Get an owner from the current document if necessary. Note that we only
// Get a principal from the current document if necessary. Note that we only
// do this for URIs that inherit a security context and local file URIs;
// in particular we do NOT do this for about:blank. This way, random
// about:blank loads that have no owner (which basically means they were
// about:blank loads that have no principal (which basically means they were
// done by someone from chrome manually messing with our nsIWebNavigation
// or by C++ setting document.location) don't get a funky principal. If
// callers want something interesting to happen with the about:blank
// principal in this case, they should pass an owner in.
// principal in this case, they should pass aTriggeringPrincipal in.
//
{
bool inherits;
// One more twist: Don't inherit the owner for external loads.
if (aLoadType != LOAD_NORMAL_EXTERNAL && !owner &&
(aFlags & INTERNAL_LOAD_FLAGS_INHERIT_OWNER) &&
// One more twist: Don't inherit the principal for external loads.
if (aLoadType != LOAD_NORMAL_EXTERNAL && !triggeringPrincipal &&
(aFlags & INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL) &&
NS_SUCCEEDED(nsContentUtils::URIInheritsSecurityContext(aURI,
&inherits)) &&
inherits) {
owner = GetInheritedPrincipal(true);
triggeringPrincipal = GetInheritedPrincipal(true);
}
}
@ -9908,7 +9901,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
// We've already done our owner-inheriting. Mask out that bit, so we
// don't try inheriting an owner from the target window if we came up
// with a null owner above.
aFlags = aFlags & ~INTERNAL_LOAD_FLAGS_INHERIT_OWNER;
aFlags = aFlags & ~INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL;
bool isNewWindow = false;
if (!targetDocShell) {
@ -9971,7 +9964,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
aLoadReplace,
aReferrer,
aReferrerPolicy,
owner,
triggeringPrincipal,
aFlags,
nullptr, // No window target
aTypeHint,
@ -10050,8 +10043,8 @@ nsDocShell::InternalLoad(nsIURI* aURI,
// Do this asynchronously
nsCOMPtr<nsIRunnable> ev =
new InternalLoadEvent(this, aURI, aOriginalURI, aLoadReplace,
aReferrer, aReferrerPolicy, aOwner, aFlags,
aTypeHint, aPostData, aHeadersData,
aReferrer, aReferrerPolicy, aTriggeringPrincipal,
aFlags, aTypeHint, aPostData, aHeadersData,
aLoadType, aSHEntry, aFirstParty, aSrcdoc,
aSourceDocShell, aBaseURI);
return NS_DispatchToCurrentThread(ev);
@ -10223,9 +10216,9 @@ nsDocShell::InternalLoad(nsIURI* aURI,
* call OnNewURI() so that, this traversal will be
* recorded in session and global history.
*/
nsCOMPtr<nsISupports> owner;
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
if (mOSHE) {
mOSHE->GetOwner(getter_AddRefs(owner));
mOSHE->GetTriggeringPrincipal(getter_AddRefs(triggeringPrincipal));
}
// Pass true for aCloneSHChildren, since we're not
// changing documents here, so all of our subframes are
@ -10235,7 +10228,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
// flag on firing onLocationChange(...).
// Anyway, aCloneSHChildren param is simply reflecting
// doShortCircuitedLoad in this scope.
OnNewURI(aURI, nullptr, owner, mLoadType, true, true, true);
OnNewURI(aURI, nullptr, triggeringPrincipal, mLoadType, true, true, true);
nsCOMPtr<nsIInputStream> postData;
nsCOMPtr<nsISupports> cacheKey;
@ -10569,7 +10562,7 @@ nsDocShell::InternalLoad(nsIURI* aURI,
rv = DoURILoad(aURI, aOriginalURI, aLoadReplace, aReferrer,
!(aFlags & INTERNAL_LOAD_FLAGS_DONT_SEND_REFERRER),
aReferrerPolicy,
owner, aTypeHint, aFileName, aPostData, aHeadersData,
triggeringPrincipal, aTypeHint, aFileName, aPostData, aHeadersData,
aFirstParty, aDocShell, getter_AddRefs(req),
(aFlags & INTERNAL_LOAD_FLAGS_FIRST_LOAD) != 0,
(aFlags & INTERNAL_LOAD_FLAGS_BYPASS_CLASSIFIER) != 0,
@ -10648,7 +10641,7 @@ nsDocShell::DoURILoad(nsIURI* aURI,
nsIURI* aReferrerURI,
bool aSendReferrer,
uint32_t aReferrerPolicy,
nsISupports* aOwner,
nsIPrincipal* aTriggeringPrincipal,
const char* aTypeHint,
const nsAString& aFileName,
nsIInputStream* aPostData,
@ -10789,7 +10782,7 @@ nsDocShell::DoURILoad(nsIURI* aURI,
// Until then, we cannot rely on the triggeringPrincipal for TYPE_DOCUMENT
// or TYPE_SUBDOCUMENT loads. Notice the triggeringPrincipal falls back to
// systemPrincipal below.
nsCOMPtr<nsIPrincipal> triggeringPrincipal = do_QueryInterface(aOwner);
nsCOMPtr<nsIPrincipal> triggeringPrincipal = aTriggeringPrincipal;
if (triggeringPrincipal) {
inherit = nsContentUtils::ChannelShouldInheritPrincipal(
triggeringPrincipal,
@ -11430,12 +11423,13 @@ nsDocShell::SetupReferrerFromChannel(nsIChannel* aChannel)
}
bool
nsDocShell::OnNewURI(nsIURI* aURI, nsIChannel* aChannel, nsISupports* aOwner,
nsDocShell::OnNewURI(nsIURI* aURI, nsIChannel* aChannel,
nsIPrincipal* aTriggeringPrincipal,
uint32_t aLoadType, bool aFireOnLocationChange,
bool aAddToGlobalHistory, bool aCloneSHChildren)
{
NS_PRECONDITION(aURI, "uri is null");
NS_PRECONDITION(!aChannel || !aOwner, "Shouldn't have both set");
NS_PRECONDITION(!aChannel || !aTriggeringPrincipal, "Shouldn't have both set");
#if defined(DEBUG)
if (MOZ_LOG_TEST(gDocShellLog, LogLevel::Debug)) {
@ -11614,8 +11608,8 @@ nsDocShell::OnNewURI(nsIURI* aURI, nsIChannel* aChannel, nsISupports* aOwner,
*.Create a Entry for it and add it to SH, if this is the
* rootDocShell
*/
(void)AddToSessionHistory(aURI, aChannel, aOwner, aCloneSHChildren,
getter_AddRefs(mLSHE));
(void)AddToSessionHistory(aURI, aChannel, aTriggeringPrincipal,
aCloneSHChildren, getter_AddRefs(mLSHE));
}
}
@ -12076,11 +12070,12 @@ nsDocShell::ShouldAddToSessionHistory(nsIURI* aURI)
nsresult
nsDocShell::AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
nsISupports* aOwner, bool aCloneChildren,
nsIPrincipal* aTriggeringPrincipal,
bool aCloneChildren,
nsISHEntry** aNewEntry)
{
NS_PRECONDITION(aURI, "uri is null");
NS_PRECONDITION(!aChannel || !aOwner, "Shouldn't have both set");
NS_PRECONDITION(!aChannel || !aTriggeringPrincipal, "Shouldn't have both set");
#if defined(DEBUG)
if (MOZ_LOG_TEST(gDocShellLog, LogLevel::Debug)) {
@ -12148,7 +12143,7 @@ nsDocShell::AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
nsCOMPtr<nsIURI> referrerURI;
uint32_t referrerPolicy = mozilla::net::RP_Default;
nsCOMPtr<nsISupports> cacheKey;
nsCOMPtr<nsISupports> owner = aOwner;
nsCOMPtr<nsIPrincipal> triggeringPrincipal = aTriggeringPrincipal;
bool expired = false;
bool discardLayoutState = false;
nsCOMPtr<nsICacheInfoChannel> cacheChannel;
@ -12181,15 +12176,19 @@ nsDocShell::AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
discardLayoutState = ShouldDiscardLayoutState(httpChannel);
}
// XXX Bug 1286838: Replace channel owner with loadInfo triggeringPrincipal
nsCOMPtr<nsISupports> owner;
aChannel->GetOwner(getter_AddRefs(owner));
if (!owner) {
triggeringPrincipal = do_QueryInterface(owner);
if (!triggeringPrincipal) {
nsCOMPtr<nsILoadInfo> loadInfo;
aChannel->GetLoadInfo(getter_AddRefs(loadInfo));
if (loadInfo) {
// For now keep storing just the principal in the SHEntry.
if (loadInfo->GetLoadingSandboxed()) {
if (loadInfo->LoadingPrincipal()) {
owner = nsNullPrincipal::CreateWithInheritedAttributes(
triggeringPrincipal = nsNullPrincipal::CreateWithInheritedAttributes(
loadInfo->LoadingPrincipal());
} else {
// get the OriginAttributes
@ -12198,23 +12197,23 @@ nsDocShell::AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
PrincipalOriginAttributes pAttrs;
pAttrs.InheritFromNecko(nAttrs);
owner = nsNullPrincipal::Create(pAttrs);
triggeringPrincipal = nsNullPrincipal::Create(pAttrs);
}
} else if (loadInfo->GetForceInheritPrincipal()) {
owner = loadInfo->TriggeringPrincipal();
triggeringPrincipal = loadInfo->TriggeringPrincipal();
}
}
}
}
// Title is set in nsDocShell::SetTitle()
entry->Create(aURI, // uri
EmptyString(), // Title
inputStream, // Post data stream
nullptr, // LayoutHistory state
cacheKey, // CacheKey
mContentTypeHint, // Content-type
owner, // Channel or provided owner
entry->Create(aURI, // uri
EmptyString(), // Title
inputStream, // Post data stream
nullptr, // LayoutHistory state
cacheKey, // CacheKey
mContentTypeHint, // Content-type
triggeringPrincipal, // Channel or provided principal
mHistoryID,
mDynamicallyCreated);
@ -12324,7 +12323,7 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
nsCOMPtr<nsIURI> referrerURI;
uint32_t referrerPolicy;
nsAutoCString contentType;
nsCOMPtr<nsISupports> owner;
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
NS_ENSURE_TRUE(aEntry, NS_ERROR_FAILURE);
@ -12340,7 +12339,8 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
NS_ENSURE_SUCCESS(aEntry->GetPostData(getter_AddRefs(postData)),
NS_ERROR_FAILURE);
NS_ENSURE_SUCCESS(aEntry->GetContentType(contentType), NS_ERROR_FAILURE);
NS_ENSURE_SUCCESS(aEntry->GetOwner(getter_AddRefs(owner)), NS_ERROR_FAILURE);
NS_ENSURE_SUCCESS(aEntry->GetTriggeringPrincipal(getter_AddRefs(triggeringPrincipal)),
NS_ERROR_FAILURE);
// Calling CreateAboutBlankContentViewer can set mOSHE to null, and if
// that's the only thing holding a ref to aEntry that will cause aEntry to
@ -12354,11 +12354,11 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
// Replace the current document with about:blank now to prevent
// anything from the current document from leaking into any JavaScript
// code in the URL.
nsCOMPtr<nsIPrincipal> prin = do_QueryInterface(owner);
// Don't cache the presentation if we're going to just reload the
// current entry. Caching would lead to trying to save the different
// content viewers in the same nsISHEntry object.
rv = CreateAboutBlankContentViewer(prin, nullptr, aEntry != mOSHE);
rv = CreateAboutBlankContentViewer(triggeringPrincipal, nullptr,
aEntry != mOSHE);
if (NS_FAILED(rv)) {
// The creation of the intermittent about:blank content
@ -12367,11 +12367,11 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
return NS_OK;
}
if (!owner) {
// Ensure that we have an owner. Otherwise javascript: URIs will
// pick it up from the about:blank page we just loaded, and we
// don't really want even that in this case.
owner = nsNullPrincipal::CreateWithInheritedAttributes(this);
if (!triggeringPrincipal) {
// Ensure that we have a triggeringPrincipal. Otherwise javascript:
// URIs will pick it up from the about:blank page we just loaded,
// and we don't really want even that in this case.
triggeringPrincipal = nsNullPrincipal::CreateWithInheritedAttributes(this);
}
}
@ -12392,7 +12392,7 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
}
}
// Do not inherit owner from document (security-critical!);
// Do not inherit principal from document (security-critical!);
uint32_t flags = INTERNAL_LOAD_FLAGS_NONE;
nsAutoString srcdoc;
@ -12416,7 +12416,7 @@ nsDocShell::LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType)
loadReplace,
referrerURI,
referrerPolicy,
owner,
triggeringPrincipal,
flags,
nullptr, // No window target
contentType.get(), // Type hint
@ -13918,7 +13918,7 @@ nsDocShell::OnLinkClickSync(nsIContent* aContent,
false, // LoadReplace
referer, // Referer URI
refererPolicy, // Referer policy
aContent->NodePrincipal(), // Owner is our node's
aContent->NodePrincipal(), // Triggering is our node's
// principal
flags,
target.get(), // Window target

View File

@ -348,9 +348,9 @@ protected:
// at the parent.
nsIPrincipal* GetInheritedPrincipal(bool aConsiderCurrentDocument);
// Actually open a channel and perform a URI load. Note: whatever owner is
// Actually open a channel and perform a URI load. Note: whatever principal is
// passed to this function will be set on the channel. Callers who wish to
// not have an owner on the channel should just pass null.
// not have an principal on the channel should just pass null.
// If aSrcdoc is not void, the load will be considered as a srcdoc load,
// and the contents of aSrcdoc will be loaded instead of aURI.
// aOriginalURI will be set as the originalURI on the channel that does the
@ -362,7 +362,7 @@ protected:
nsIURI* aReferrer,
bool aSendReferrer,
uint32_t aReferrerPolicy,
nsISupports* aOwner,
nsIPrincipal* aTriggeringPrincipal,
const char* aTypeHint,
const nsAString& aFileName,
nsIInputStream* aPostData,
@ -401,11 +401,12 @@ protected:
// In this case it is the caller's responsibility to ensure
// FireOnLocationChange is called.
// In all other cases false is returned.
// Either aChannel or aOwner must be null. If aChannel is
// Either aChannel or aTriggeringPrincipal must be null. If aChannel is
// present, the owner should be gotten from it.
// If OnNewURI calls AddToSessionHistory, it will pass its
// aCloneSHChildren argument as aCloneChildren.
bool OnNewURI(nsIURI* aURI, nsIChannel* aChannel, nsISupports* aOwner,
bool OnNewURI(nsIURI* aURI, nsIChannel* aChannel,
nsIPrincipal* aTriggeringPrincipal,
uint32_t aLoadType,
bool aFireOnLocationChange,
bool aAddToGlobalHistory,
@ -423,7 +424,7 @@ protected:
// used when we aren't actually changing the document while adding
// the new session history entry.
nsresult AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
nsISupports* aOwner,
nsIPrincipal* aTriggeringPrincipal,
bool aCloneChildren,
nsISHEntry** aNewEntry);
nsresult AddChildSHEntryToParent(nsISHEntry* aNewEntry, int32_t aChildOffset,

View File

@ -13,8 +13,8 @@
nsDocShellLoadInfo::nsDocShellLoadInfo()
: mLoadReplace(false)
, mInheritOwner(false)
, mOwnerIsExplicit(false)
, mInheritPrincipal(false)
, mPrincipalIsExplicit(false)
, mSendReferrer(true)
, mReferrerPolicy(mozilla::net::RP_Default)
, mLoadType(nsIDocShellLoadInfo::loadNormal)
@ -83,49 +83,46 @@ nsDocShellLoadInfo::SetLoadReplace(bool aLoadReplace)
}
NS_IMETHODIMP
nsDocShellLoadInfo::GetOwner(nsISupports** aOwner)
nsDocShellLoadInfo::GetTriggeringPrincipal(nsIPrincipal** aTriggeringPrincipal)
{
NS_ENSURE_ARG_POINTER(aOwner);
*aOwner = mOwner;
NS_IF_ADDREF(*aOwner);
NS_ENSURE_ARG_POINTER(aTriggeringPrincipal);
NS_IF_ADDREF(*aTriggeringPrincipal = mTriggeringPrincipal);
return NS_OK;
}
NS_IMETHODIMP
nsDocShellLoadInfo::SetOwner(nsISupports* aOwner)
nsDocShellLoadInfo::SetTriggeringPrincipal(nsIPrincipal* aTriggeringPrincipal)
{
mOwner = aOwner;
mTriggeringPrincipal = aTriggeringPrincipal;
return NS_OK;
}
NS_IMETHODIMP
nsDocShellLoadInfo::GetInheritOwner(bool* aInheritOwner)
nsDocShellLoadInfo::GetInheritPrincipal(bool* aInheritPrincipal)
{
NS_ENSURE_ARG_POINTER(aInheritOwner);
*aInheritOwner = mInheritOwner;
NS_ENSURE_ARG_POINTER(aInheritPrincipal);
*aInheritPrincipal = mInheritPrincipal;
return NS_OK;
}
NS_IMETHODIMP
nsDocShellLoadInfo::SetInheritOwner(bool aInheritOwner)
nsDocShellLoadInfo::SetInheritPrincipal(bool aInheritPrincipal)
{
mInheritOwner = aInheritOwner;
mInheritPrincipal = aInheritPrincipal;
return NS_OK;
}
NS_IMETHODIMP
nsDocShellLoadInfo::GetOwnerIsExplicit(bool* aOwnerIsExplicit)
nsDocShellLoadInfo::GetPrincipalIsExplicit(bool* aPrincipalIsExplicit)
{
*aOwnerIsExplicit = mOwnerIsExplicit;
*aPrincipalIsExplicit = mPrincipalIsExplicit;
return NS_OK;
}
NS_IMETHODIMP
nsDocShellLoadInfo::SetOwnerIsExplicit(bool aOwnerIsExplicit)
nsDocShellLoadInfo::SetPrincipalIsExplicit(bool aPrincipalIsExplicit)
{
mOwnerIsExplicit = aOwnerIsExplicit;
mPrincipalIsExplicit = aPrincipalIsExplicit;
return NS_OK;
}

View File

@ -33,10 +33,10 @@ protected:
protected:
nsCOMPtr<nsIURI> mReferrer;
nsCOMPtr<nsIURI> mOriginalURI;
nsCOMPtr<nsISupports> mOwner;
nsCOMPtr<nsIPrincipal> mTriggeringPrincipal;
bool mLoadReplace;
bool mInheritOwner;
bool mOwnerIsExplicit;
bool mInheritPrincipal;
bool mPrincipalIsExplicit;
bool mSendReferrer;
nsDocShellInfoReferrerPolicy mReferrerPolicy;
nsDocShellInfoLoadType mLoadType;

View File

@ -101,7 +101,7 @@ interface nsIDocShell : nsIDocShellTreeItem
in nsIDocShellLoadInfo aLoadInfo);
const long INTERNAL_LOAD_FLAGS_NONE = 0x0;
const long INTERNAL_LOAD_FLAGS_INHERIT_OWNER = 0x1;
const long INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL = 0x1;
const long INTERNAL_LOAD_FLAGS_DONT_SEND_REFERRER = 0x2;
const long INTERNAL_LOAD_FLAGS_ALLOW_THIRD_PARTY_FIXUP = 0x4;
@ -124,44 +124,43 @@ interface nsIDocShell : nsIDocShellTreeItem
* that its parameter list is broken out instead of being packaged inside
* of an nsIDocShellLoadInfo object...
*
* @param aURI - The URI to load.
* @param aOriginalURI - The URI to set as the originalURI on the channel
* that does the load. If null, aURI will be set as
* the originalURI.
* @param aLoadReplace - If set LOAD_REPLACE flag will be set on the
* channel. aOriginalURI is null, this argument is
* ignored.
* @param aReferrer - Referring URI
* @param aReferrerPolicy - Referrer policy
* @param aOwner - Owner (security principal)
* @param aInheritOwner - Flag indicating whether the owner of the current
* document should be inherited if aOwner is null.
* @param aStopActiveDoc - Flag indicating whether loading the current
* document should be stopped.
* @param aWindowTarget - Window target for the load.
* @param aTypeHint - A hint as to the content-type of the resulting
* data. May be null or empty if no hint.
* @param aFileName - Non-null when the link should be downloaded as
the given filename.
* @param aPostDataStream - Post data stream (if POSTing)
* @param aHeadersStream - Stream containing "extra" request headers...
* @param aLoadFlags - Flags to modify load behaviour. Flags are defined
* in nsIWebNavigation.
* @param aSHEntry - Active Session History entry (if loading from SH)
* @param aSrcdoc When INTERNAL_LOAD_FLAGS_IS_SRCDOC is set, the
* contents of this parameter will be loaded instead
* of aURI.
* @param aSourceDocShell - The source browsing context for the navigation.
* @param aBaseURI - The base URI to be used for the load. Set in
* srcdoc loads as it cannot otherwise be inferred
* in certain situations such as view-source.
* @param aURI - The URI to load.
* @param aOriginalURI - The URI to set as the originalURI on the channel
* that does the load. If null, aURI will be set as
* the originalURI.
* @param aLoadReplace - If set LOAD_REPLACE flag will be set on the
* channel. aOriginalURI is null, this argument is
* ignored.
* @param aReferrer - Referring URI
* @param aReferrerPolicy - Referrer policy
* @param aTriggeringPrincipal - Principal that initiated that load
* @param aFlags - Any of the load flags defined within above.
* @param aStopActiveDoc - Flag indicating whether loading the current
* document should be stopped.
* @param aWindowTarget - Window target for the load.
* @param aTypeHint - A hint as to the content-type of the resulting
* data. May be null or empty if no hint.
* @param aFileName - Non-null when the link should be downloaded as
the given filename.
* @param aPostDataStream - Post data stream (if POSTing)
* @param aHeadersStream - Stream containing "extra" request headers...
* @param aLoadFlags - Flags to modify load behaviour. Flags are defined
* in nsIWebNavigation.
* @param aSHEntry - Active Session History entry (if loading from SH)
* @param aSrcdoc When INTERNAL_LOAD_FLAGS_IS_SRCDOC is set, the
* contents of this parameter will be loaded instead
* of aURI.
* @param aSourceDocShell - The source browsing context for the navigation.
* @param aBaseURI - The base URI to be used for the load. Set in
* srcdoc loads as it cannot otherwise be inferred
* in certain situations such as view-source.
*/
[noscript]void internalLoad(in nsIURI aURI,
in nsIURI aOriginalURI,
in boolean aLoadReplace,
in nsIURI aReferrer,
in unsigned long aReferrerPolicy,
in nsISupports aOwner,
in nsIPrincipal aTriggeringPrincipal,
in uint32_t aFlags,
in wstring aWindowTarget,
in string aTypeHint,

View File

@ -15,6 +15,7 @@ interface nsIURI;
interface nsIInputStream;
interface nsISHEntry;
interface nsIDocShell;
interface nsIPrincipal;
typedef long nsDocShellInfoLoadType;
typedef unsigned long nsDocShellInfoReferrerPolicy;
@ -35,23 +36,24 @@ interface nsIDocShellLoadInfo : nsISupports
*/
attribute boolean loadReplace;
/** The owner of the load, that is, the entity responsible for
* causing the load to occur. This should be a nsIPrincipal typically.
/** The principal of the load, that is, the entity responsible for
* causing the load to occur. In most cases the referrer and
* the triggeringPrincipal's URI will be identical.
*/
attribute nsISupports owner;
attribute nsIPrincipal triggeringPrincipal;
/** If this attribute is true and no owner is specified, copy
* the owner from the referring document.
/** If this attribute is true and no triggeringPrincipal is specified,
* copy the principal from the referring document.
*/
attribute boolean inheritOwner;
attribute boolean inheritPrincipal;
/** If this attribute is true only ever use the owner specify by
* the owner and inheritOwner attributes.
/** If this attribute is true only ever use the principal specified
* by the triggeringPrincipal and inheritPrincipal attributes.
* If there are security reasons for why this is unsafe, such
* as trying to use a systemprincipal owner for a content docshell
* the load fails.
* as trying to use a systemprincipal as the triggeringPrincipal
* for a content docshell the load fails.
*/
attribute boolean ownerIsExplicit;
attribute boolean principalIsExplicit;
/* these are load type enums... */
const long loadNormal = 0; // Normal Load

View File

@ -181,8 +181,11 @@ interface nsIWebNavigation : nsISupports
/**
* Prevent the owner principal from being inherited for this load.
* Note: Within Gecko we use the term principal rather than owners
* but some legacy addons might still rely on the outdated term.
*/
const unsigned long LOAD_FLAGS_DISALLOW_INHERIT_OWNER = 0x40000;
const unsigned long LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL = 0x40000;
const unsigned long LOAD_FLAGS_DISALLOW_INHERIT_OWNER = 0x40000;
/**
* Overwrite the returned error code with a specific result code

View File

@ -20,9 +20,6 @@ LOCAL_INCLUDES += [
'/uriloader/prefetch',
]
if CONFIG["MOZ_WIDGET_TOOLKIT"] == "cocoa":
LOCAL_INCLUDES += ['/uriloader/exthandler/mac']
include('/ipc/chromium/chromium-config.mozbuild')
FINAL_LIBRARY = 'xul'

View File

@ -20,6 +20,7 @@ interface nsIDocShellTreeItem;
interface nsISupportsArray;
interface nsIStructuredCloneContainer;
interface nsIBFCacheEntry;
interface nsIPrincipal;
%{C++
#include "nsRect.h"
@ -190,7 +191,7 @@ interface nsISHEntry : nsISupports
in nsIInputStream inputStream,
in nsILayoutHistoryState layoutHistoryState,
in nsISupports cacheKey, in ACString contentType,
in nsISupports owner,
in nsIPrincipal triggeringPrincipal,
in unsigned long long docshellID,
in boolean dynamicCreation);
@ -205,11 +206,11 @@ interface nsISHEntry : nsISupports
nsIContentViewer getAnyContentViewer(out nsISHEntry ownerEntry);
/**
* Get the owner, if any, that was associated with the channel
* Get the principal, if any, that was associated with the channel
* that the document that was loaded to create this history entry
* came from.
*/
attribute nsISupports owner;
attribute nsIPrincipal triggeringPrincipal;
/**
* Get/set data associated with this history state via a pushState() call,

View File

@ -412,7 +412,7 @@ nsSHEntry::Create(nsIURI* aURI, const nsAString& aTitle,
nsIInputStream* aInputStream,
nsILayoutHistoryState* aLayoutHistoryState,
nsISupports* aCacheKey, const nsACString& aContentType,
nsISupports* aOwner, uint64_t aDocShellID,
nsIPrincipal* aTriggeringPrincipal, uint64_t aDocShellID,
bool aDynamicCreation)
{
mURI = aURI;
@ -424,7 +424,7 @@ nsSHEntry::Create(nsIURI* aURI, const nsAString& aTitle,
mShared->mCacheKey = aCacheKey;
mShared->mContentType = aContentType;
mShared->mOwner = aOwner;
mShared->mTriggeringPrincipal = aTriggeringPrincipal;
mShared->mDocShellID = aDocShellID;
mShared->mDynamicallyCreated = aDynamicCreation;
@ -504,16 +504,16 @@ nsSHEntry::GetViewerBounds(nsIntRect& aBounds)
}
NS_IMETHODIMP
nsSHEntry::GetOwner(nsISupports** aOwner)
nsSHEntry::GetTriggeringPrincipal(nsIPrincipal** aTriggeringPrincipal)
{
NS_IF_ADDREF(*aOwner = mShared->mOwner);
NS_IF_ADDREF(*aTriggeringPrincipal = mShared->mTriggeringPrincipal);
return NS_OK;
}
NS_IMETHODIMP
nsSHEntry::SetOwner(nsISupports* aOwner)
nsSHEntry::SetTriggeringPrincipal(nsIPrincipal* aTriggeringPrincipal)
{
mShared->mOwner = aOwner;
mShared->mTriggeringPrincipal = aTriggeringPrincipal;
return NS_OK;
}

View File

@ -115,7 +115,7 @@ nsSHEntryShared::Duplicate(nsSHEntryShared* aEntry)
newEntry->mDocShellID = aEntry->mDocShellID;
newEntry->mChildShells.AppendObjects(aEntry->mChildShells);
newEntry->mOwner = aEntry->mOwner;
newEntry->mTriggeringPrincipal = aEntry->mTriggeringPrincipal;
newEntry->mContentType.Assign(aEntry->mContentType);
newEntry->mIsFrameNavigation = aEntry->mIsFrameNavigation;
newEntry->mSaveLayoutState = aEntry->mSaveLayoutState;

View File

@ -70,7 +70,7 @@ private:
// member here, be sure to update the Duplicate() implementation.
uint64_t mDocShellID;
nsCOMArray<nsIDocShellTreeItem> mChildShells;
nsCOMPtr<nsISupports> mOwner;
nsCOMPtr<nsIPrincipal> mTriggeringPrincipal;
nsCString mContentType;
bool mIsFrameNavigation;
bool mSaveLayoutState;

View File

@ -33,7 +33,7 @@ function test() {
// Now load the URL and disallow inheriting the principal
let webNav = Components.interfaces.nsIWebNavigation;
loadURL(url, webNav.LOAD_FLAGS_DISALLOW_INHERIT_OWNER, function () {
loadURL(url, webNav.LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL, function () {
let newPrincipal = browser.contentPrincipal;
ok(newPrincipal, "got inner principal");
ok(!newPrincipal.equals(pagePrincipal),

View File

@ -0,0 +1,28 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* 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/. */
#include "mozilla/dom/BorrowedAttrInfo.h"
namespace mozilla {
namespace dom {
BorrowedAttrInfo::BorrowedAttrInfo(const nsAttrName* aName,
const nsAttrValue* aValue)
: mName(aName)
, mValue(aValue)
{
MOZ_ASSERT_IF(mName, mValue);
}
BorrowedAttrInfo::BorrowedAttrInfo(const BorrowedAttrInfo& aOther)
: mName(aOther.mName)
, mValue(aOther.mValue)
{
MOZ_ASSERT_IF(mName, mValue);
}
} // namespace dom
} // namespace mozilla

View File

@ -0,0 +1,46 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* 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 BorrowedAttrInfo_h__
#define BorrowedAttrInfo_h__
#include "mozilla/Assertions.h"
class nsAttrName;
class nsAttrValue;
namespace mozilla {
namespace dom {
/**
* Struct that stores info on an attribute. The name and value must either both
* be null or both be non-null.
*
* Note that, just as the pointers returned by GetAttrNameAt, the pointers that
* this struct hold are only valid until the element or its attributes are
* mutated (directly or via script).
*/
struct BorrowedAttrInfo
{
BorrowedAttrInfo()
: mName(nullptr)
, mValue(nullptr)
{
}
BorrowedAttrInfo(const nsAttrName* aName, const nsAttrValue* aValue);
BorrowedAttrInfo(const BorrowedAttrInfo& aOther);
const nsAttrName* mName;
const nsAttrValue* mValue;
explicit operator bool() const { return mName != nullptr; }
};
} // namespace dom
} // namespace mozilla
#endif

View File

@ -8,6 +8,7 @@
#define mozilla_dom_DocumentFragment_h__
#include "mozilla/Attributes.h"
#include "mozilla/dom/BorrowedAttrInfo.h"
#include "mozilla/dom/FragmentOrElement.h"
#include "nsIDOMDocumentFragment.h"
@ -79,7 +80,7 @@ public:
{
return NS_OK;
}
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttribute,
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttribute,
bool aNotify) override
{
return NS_OK;
@ -88,6 +89,10 @@ public:
{
return nullptr;
}
virtual BorrowedAttrInfo GetAttrInfoAt(uint32_t aIndex) const override
{
return BorrowedAttrInfo(nullptr, nullptr);
}
virtual uint32_t GetAttrCount() const override
{
return 0;

View File

@ -1787,6 +1787,12 @@ Element::UnbindFromTree(bool aDeep, bool aNullParent)
ClearInDocument();
#ifdef MOZ_STYLO
// Drop any servo node data, since it will generally need to be recomputed on
// re-insertion anyway.
ServoData().reset();
#endif
// Editable descendant count only counts descendants that
// are in the uncomposed document.
ResetEditableDescendantCount();
@ -2205,7 +2211,7 @@ Element::MaybeCheckSameAttrVal(int32_t aNamespaceID,
// listeners and don't plan to notify. The check for aNotify here is an
// optimization, the check for *aHasListeners is a correctness issue.
if (*aHasListeners || aNotify) {
nsAttrInfo info(GetAttrInfo(aNamespaceID, aName));
BorrowedAttrInfo info(GetAttrInfo(aNamespaceID, aName));
if (info.mValue) {
// Check whether the old value is the same as the new one. Note that we
// only need to actually _get_ the old value if we have listeners or
@ -2536,7 +2542,7 @@ Element::GetEventListenerManagerForAttr(nsIAtom* aAttrName,
return GetOrCreateListenerManager();
}
Element::nsAttrInfo
BorrowedAttrInfo
Element::GetAttrInfo(int32_t aNamespaceID, nsIAtom* aName) const
{
NS_ASSERTION(nullptr != aName, "must have attribute name");
@ -2544,14 +2550,22 @@ Element::GetAttrInfo(int32_t aNamespaceID, nsIAtom* aName) const
"must have a real namespace ID!");
int32_t index = mAttrsAndChildren.IndexOfAttr(aName, aNamespaceID);
if (index >= 0) {
return nsAttrInfo(mAttrsAndChildren.AttrNameAt(index),
mAttrsAndChildren.AttrAt(index));
if (index < 0) {
return BorrowedAttrInfo(nullptr, nullptr);
}
return nsAttrInfo(nullptr, nullptr);
return mAttrsAndChildren.AttrInfoAt(index);
}
BorrowedAttrInfo
Element::GetAttrInfoAt(uint32_t aIndex) const
{
if (aIndex >= mAttrsAndChildren.AttrCount()) {
return BorrowedAttrInfo(nullptr, nullptr);
}
return mAttrsAndChildren.AttrInfoAt(aIndex);
}
bool
Element::GetAttr(int32_t aNameSpaceID, nsIAtom* aName,
@ -3284,7 +3298,7 @@ Element::RequestFullscreen(JSContext* aCx, JS::Handle<JS::Value> aOptions,
}
void
Element::MozRequestPointerLock()
Element::RequestPointerLock()
{
OwnerDoc()->RequestPointerLock(this);
}

View File

@ -509,6 +509,7 @@ public:
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttribute,
bool aNotify) override;
virtual const nsAttrName* GetAttrNameAt(uint32_t aIndex) const override;
virtual BorrowedAttrInfo GetAttrInfoAt(uint32_t aIndex) const override;
virtual uint32_t GetAttrCount() const override;
virtual bool IsNodeOfType(uint32_t aFlags) const override;
@ -750,7 +751,7 @@ public:
// aCx == nullptr is allowed only if aOptions.isNullOrUndefined()
void RequestFullscreen(JSContext* aCx, JS::Handle<JS::Value> aOptions,
ErrorResult& aError);
void MozRequestPointerLock();
void RequestPointerLock();
Attr* GetAttributeNode(const nsAString& aName);
already_AddRefed<Attr> SetAttributeNode(Attr& aNewAttr,
ErrorResult& aError);
@ -938,20 +939,6 @@ public:
// Work around silly C++ name hiding stuff
nsIFrame* GetPrimaryFrame() const { return nsIContent::GetPrimaryFrame(); }
/**
* Struct that stores info on an attribute. The name and value must
* either both be null or both be non-null.
*/
struct nsAttrInfo {
nsAttrInfo(const nsAttrName* aName, const nsAttrValue* aValue) :
mName(aName), mValue(aValue) {}
nsAttrInfo(const nsAttrInfo& aOther) :
mName(aOther.mName), mValue(aOther.mValue) {}
const nsAttrName* mName;
const nsAttrValue* mValue;
};
const nsAttrValue* GetParsedAttr(nsIAtom* aAttr) const
{
return mAttrsAndChildren.GetAttr(aAttr);
@ -986,7 +973,7 @@ public:
* is, this should only be called from methods that only care about attrs
* that effectively live in mAttrsAndChildren.
*/
virtual nsAttrInfo GetAttrInfo(int32_t aNamespaceID, nsIAtom* aName) const;
virtual BorrowedAttrInfo GetAttrInfo(int32_t aNamespaceID, nsIAtom* aName) const;
virtual void NodeInfoChanged()
{
@ -1861,7 +1848,7 @@ NS_IMETHOD MozRequestFullScreen(void) final override \
} \
NS_IMETHOD MozRequestPointerLock(void) final override \
{ \
Element::MozRequestPointerLock(); \
Element::RequestPointerLock(); \
return NS_OK; \
} \
using nsINode::QuerySelector; \

View File

@ -138,8 +138,8 @@ void NodeIterator::NodePointer::MoveBackward(nsINode *aParent, nsINode *aNode)
NodeIterator::NodeIterator(nsINode *aRoot,
uint32_t aWhatToShow,
const NodeFilterHolder &aFilter) :
nsTraversal(aRoot, aWhatToShow, aFilter),
NodeFilterHolder aFilter) :
nsTraversal(aRoot, aWhatToShow, Move(aFilter)),
mPointer(mRoot, true)
{
aRoot->AddMutationObserver(this);

View File

@ -32,7 +32,7 @@ public:
NodeIterator(nsINode *aRoot,
uint32_t aWhatToShow,
const NodeFilterHolder &aFilter);
NodeFilterHolder aFilter);
NS_DECL_NSIMUTATIONOBSERVER_CONTENTREMOVED

View File

@ -357,6 +357,9 @@ AutoJSAPI::InitInternal(nsIGlobalObject* aGlobalObject, JSObject* aGlobal,
// too.
mAutoRequest.emplace(mCx);
}
if (aGlobal) {
JS::ExposeObjectToActiveJS(aGlobal);
}
mAutoNullableCompartment.emplace(mCx, aGlobal);
ScriptSettingsStack::Push(this);

View File

@ -26,8 +26,8 @@ namespace dom {
TreeWalker::TreeWalker(nsINode *aRoot,
uint32_t aWhatToShow,
const NodeFilterHolder &aFilter) :
nsTraversal(aRoot, aWhatToShow, aFilter),
NodeFilterHolder aFilter) :
nsTraversal(aRoot, aWhatToShow, Move(aFilter)),
mCurrentNode(aRoot)
{
}

View File

@ -33,7 +33,7 @@ public:
TreeWalker(nsINode *aRoot,
uint32_t aWhatToShow,
const NodeFilterHolder &aFilter);
NodeFilterHolder aFilter);
NS_DECL_CYCLE_COLLECTION_CLASS(TreeWalker)

View File

@ -152,6 +152,7 @@ EXPORTS.mozilla.dom += [
'BarProps.h',
'BlobSet.h',
'BodyUtil.h',
'BorrowedAttrInfo.h',
'ChildIterator.h',
'ChromeNodeList.h',
'ChromeUtils.h',
@ -212,6 +213,7 @@ UNIFIED_SOURCES += [
'BarProps.cpp',
'BlobSet.cpp',
'BodyUtil.cpp',
'BorrowedAttrInfo.cpp',
'ChildIterator.cpp',
'ChromeNodeList.cpp',
'ChromeUtils.cpp',

View File

@ -79,15 +79,15 @@ GetIndexFromCache(const nsAttrAndChildArray* aArray)
/**
* Due to a compiler bug in VisualAge C++ for AIX, we need to return the
* address of the first index into mBuffer here, instead of simply returning
* Due to a compiler bug in VisualAge C++ for AIX, we need to return the
* address of the first index into mBuffer here, instead of simply returning
* mBuffer itself.
*
* See Bug 231104 for more information.
*/
#define ATTRS(_impl) \
reinterpret_cast<InternalAttr*>(&((_impl)->mBuffer[0]))
#define NS_IMPL_EXTRA_SIZE \
((sizeof(Impl) - sizeof(mImpl->mBuffer)) / sizeof(void*))
@ -114,7 +114,7 @@ nsAttrAndChildArray::GetSafeChildAt(uint32_t aPos) const
if (aPos < ChildCount()) {
return ChildAt(aPos);
}
return nullptr;
}
@ -122,11 +122,11 @@ nsIContent * const *
nsAttrAndChildArray::GetChildArray(uint32_t* aChildCount) const
{
*aChildCount = ChildCount();
if (!*aChildCount) {
return nullptr;
}
return reinterpret_cast<nsIContent**>(mImpl->mBuffer + AttrSlotsSize());
}
@ -184,7 +184,7 @@ nsAttrAndChildArray::InsertChildAt(nsIContent* aChild, uint32_t aPos)
SetChildAtPos(pos, aChild, aPos, childCount);
SetChildCount(childCount + 1);
return NS_OK;
}
@ -484,6 +484,21 @@ nsAttrAndChildArray::RemoveAttrAt(uint32_t aPos, nsAttrValue& aValue)
return MakeMappedUnique(mapped);
}
BorrowedAttrInfo
nsAttrAndChildArray::AttrInfoAt(uint32_t aPos) const
{
NS_ASSERTION(aPos < AttrCount(),
"out-of-bounds access in nsAttrAndChildArray");
uint32_t nonmapped = NonMappedAttrCount();
if (aPos < nonmapped) {
return BorrowedAttrInfo(&ATTRS(mImpl)[aPos].mName, &ATTRS(mImpl)[aPos].mValue);
}
return BorrowedAttrInfo(mImpl->mMappedAttrs->NameAt(aPos - nonmapped),
mImpl->mMappedAttrs->AttrAt(aPos - nonmapped));
}
const nsAttrName*
nsAttrAndChildArray::AttrNameAt(uint32_t aPos) const
{

View File

@ -14,6 +14,7 @@
#include "mozilla/Attributes.h"
#include "mozilla/MemoryReporting.h"
#include "mozilla/dom/BorrowedAttrInfo.h"
#include "nscore.h"
#include "nsAttrName.h"
@ -46,6 +47,7 @@ class nsMappedAttributeElement;
class nsAttrAndChildArray
{
typedef mozilla::dom::BorrowedAttrInfo BorrowedAttrInfo;
public:
nsAttrAndChildArray();
~nsAttrAndChildArray();
@ -99,6 +101,9 @@ public:
// Returns attribute name at given position, *not* out-of-bounds safe
const nsAttrName* AttrNameAt(uint32_t aPos) const;
// Returns the attribute info at a given position, *not* out-of-bounds safe
BorrowedAttrInfo AttrInfoAt(uint32_t aPos) const;
// Returns attribute name at given position or null if aPos is out-of-bounds
const nsAttrName* GetSafeAttrNameAt(uint32_t aPos) const;
@ -164,7 +169,7 @@ private:
void SetChildCount(uint32_t aCount)
{
mImpl->mAttrAndChildCount =
mImpl->mAttrAndChildCount =
(mImpl->mAttrAndChildCount & ATTRCHILD_ARRAY_ATTR_SLOTS_COUNT_MASK) |
(aCount << ATTRCHILD_ARRAY_ATTR_SLOTS_BITS);
}

View File

@ -443,7 +443,7 @@ private:
// Given an enum table and a particular entry in that table, return
// the actual integer value we should store.
int32_t EnumTableEntryToValue(const EnumTable* aEnumTable,
const EnumTable* aTableEntry);
const EnumTable* aTableEntry);
static nsTArray<const EnumTable*>* sEnumTableArray;

View File

@ -3627,11 +3627,11 @@ nsContentUtils::IsChildOfSameType(nsIDocument* aDoc)
return sameTypeParent != nullptr;
}
bool
bool
nsContentUtils::IsScriptType(const nsACString& aContentType)
{
// NOTE: if you add a type here, add it to the CONTENTDLF_CATEGORIES
// define in nsContentDLF.h as well.
// define in nsContentDLF.h as well.
return aContentType.EqualsLiteral(APPLICATION_JAVASCRIPT) ||
aContentType.EqualsLiteral(APPLICATION_XJAVASCRIPT) ||
aContentType.EqualsLiteral(TEXT_ECMASCRIPT) ||
@ -4445,9 +4445,10 @@ nsContentUtils::CreateContextualFragment(nsINode* aContextNode,
uint32_t index;
for (index = 0; index < count; index++) {
const nsAttrName* name = content->GetAttrNameAt(index);
const BorrowedAttrInfo info = content->GetAttrInfoAt(index);
const nsAttrName* name = info.mName;
if (name->NamespaceEquals(kNameSpaceID_XMLNS)) {
content->GetAttr(kNameSpaceID_XMLNS, name->LocalName(), uriStr);
info.mValue->ToString(uriStr);
// really want something like nsXMLContentSerializer::SerializeAttr
tagName.AppendLiteral(" xmlns"); // space important

View File

@ -646,7 +646,7 @@ public:
/**
* Method that gets the primary presContext for the node.
*
*
* @param aContent The content node.
* @return the presContext, or nullptr if the content is not in a document
* (if GetCurrentDoc returns nullptr)

View File

@ -174,7 +174,6 @@
#include "nsSMILAnimationController.h"
#include "imgIContainer.h"
#include "nsSVGUtils.h"
#include "SVGElementFactory.h"
#include "nsRefreshDriver.h"
@ -192,7 +191,6 @@
#include "nsTextNode.h"
#include "mozilla/dom/Link.h"
#include "mozilla/dom/HTMLElementBinding.h"
#include "mozilla/dom/SVGElementBinding.h"
#include "nsXULAppAPI.h"
#include "mozilla/dom/Touch.h"
#include "mozilla/dom/TouchEvent.h"
@ -6257,7 +6255,6 @@ nsDocument::RegisterElement(JSContext* aCx, const nsAString& aType,
JS::Rooted<JSObject*> protoObject(aCx);
{
JS::Rooted<JSObject*> htmlProto(aCx);
JS::Rooted<JSObject*> svgProto(aCx);
{
JSAutoCompartment ac(aCx, global);
@ -6266,12 +6263,6 @@ nsDocument::RegisterElement(JSContext* aCx, const nsAString& aType,
rv.Throw(NS_ERROR_OUT_OF_MEMORY);
return;
}
svgProto = SVGElementBinding::GetProtoObjectHandle(aCx);
if (!svgProto) {
rv.Throw(NS_ERROR_OUT_OF_MEMORY);
return;
}
}
if (!aOptions.mPrototype) {
@ -6323,23 +6314,16 @@ nsDocument::RegisterElement(JSContext* aCx, const nsAString& aType,
JS::Rooted<JSObject*> protoProto(aCx, protoObject);
if (!JS_WrapObject(aCx, &htmlProto) || !JS_WrapObject(aCx, &svgProto)) {
if (!JS_WrapObject(aCx, &htmlProto)) {
rv.Throw(NS_ERROR_DOM_NOT_SUPPORTED_ERR);
return;
}
// If PROTOTYPE's interface inherits from SVGElement, set NAMESPACE to SVG
// Namespace.
while (protoProto) {
if (protoProto == htmlProto) {
break;
}
if (protoProto == svgProto) {
namespaceID = kNameSpaceID_SVG;
break;
}
if (!JS_GetPrototype(aCx, protoProto, &protoProto)) {
rv.Throw(NS_ERROR_UNEXPECTED);
return;
@ -6350,21 +6334,16 @@ nsDocument::RegisterElement(JSContext* aCx, const nsAString& aType,
// If name was provided and not null...
if (!lcName.IsEmpty()) {
// Let BASE be the element interface for NAME and NAMESPACE.
bool known = false;
nameAtom = NS_Atomize(lcName);
if (namespaceID == kNameSpaceID_XHTML) {
nsIParserService* ps = nsContentUtils::GetParserService();
if (!ps) {
rv.Throw(NS_ERROR_UNEXPECTED);
return;
}
known =
ps->HTMLCaseSensitiveAtomTagToId(nameAtom) != eHTMLTag_userdefined;
} else {
known = SVGElementFactory::Exists(nameAtom);
nsIParserService* ps = nsContentUtils::GetParserService();
if (!ps) {
rv.Throw(NS_ERROR_UNEXPECTED);
return;
}
bool known =
ps->HTMLCaseSensitiveAtomTagToId(nameAtom) != eHTMLTag_userdefined;
// If BASE does not exist or is an interface for a custom element, set ERROR
// to InvalidName and stop.
// If BASE exists, then it cannot be an interface for a custom element.
@ -6373,12 +6352,6 @@ nsDocument::RegisterElement(JSContext* aCx, const nsAString& aType,
return;
}
} else {
// If NAMESPACE is SVG Namespace, set ERROR to InvalidName and stop.
if (namespaceID == kNameSpaceID_SVG) {
rv.Throw(NS_ERROR_UNEXPECTED);
return;
}
nameAtom = typeAtom;
}
} // Leaving the document's compartment for the LifecycleCallbacks init
@ -7032,8 +7005,8 @@ nsDocument::CreateNodeIterator(nsIDOMNode *aRoot,
NS_ENSURE_TRUE(root, NS_ERROR_UNEXPECTED);
ErrorResult rv;
NodeFilterHolder holder(aFilter);
*_retval = nsIDocument::CreateNodeIterator(*root, aWhatToShow, holder,
*_retval = nsIDocument::CreateNodeIterator(*root, aWhatToShow,
NodeFilterHolder(aFilter),
rv).take();
return rv.StealNSResult();
}
@ -7043,18 +7016,17 @@ nsIDocument::CreateNodeIterator(nsINode& aRoot, uint32_t aWhatToShow,
NodeFilter* aFilter,
ErrorResult& rv) const
{
NodeFilterHolder holder(aFilter);
return CreateNodeIterator(aRoot, aWhatToShow, holder, rv);
return CreateNodeIterator(aRoot, aWhatToShow, NodeFilterHolder(aFilter), rv);
}
already_AddRefed<NodeIterator>
nsIDocument::CreateNodeIterator(nsINode& aRoot, uint32_t aWhatToShow,
const NodeFilterHolder& aFilter,
NodeFilterHolder aFilter,
ErrorResult& rv) const
{
nsINode* root = &aRoot;
RefPtr<NodeIterator> iterator = new NodeIterator(root, aWhatToShow,
aFilter);
Move(aFilter));
return iterator.forget();
}
@ -7075,8 +7047,8 @@ nsDocument::CreateTreeWalker(nsIDOMNode *aRoot,
NS_ENSURE_TRUE(root, NS_ERROR_DOM_NOT_SUPPORTED_ERR);
ErrorResult rv;
NodeFilterHolder holder(aFilter);
*_retval = nsIDocument::CreateTreeWalker(*root, aWhatToShow, holder,
*_retval = nsIDocument::CreateTreeWalker(*root, aWhatToShow,
NodeFilterHolder(aFilter),
rv).take();
return rv.StealNSResult();
}
@ -7086,17 +7058,15 @@ nsIDocument::CreateTreeWalker(nsINode& aRoot, uint32_t aWhatToShow,
NodeFilter* aFilter,
ErrorResult& rv) const
{
NodeFilterHolder holder(aFilter);
return CreateTreeWalker(aRoot, aWhatToShow, holder, rv);
return CreateTreeWalker(aRoot, aWhatToShow, NodeFilterHolder(aFilter), rv);
}
already_AddRefed<TreeWalker>
nsIDocument::CreateTreeWalker(nsINode& aRoot, uint32_t aWhatToShow,
const NodeFilterHolder& aFilter,
ErrorResult& rv) const
NodeFilterHolder aFilter, ErrorResult& rv) const
{
nsINode* root = &aRoot;
RefPtr<TreeWalker> walker = new TreeWalker(root, aWhatToShow, aFilter);
RefPtr<TreeWalker> walker = new TreeWalker(root, aWhatToShow, Move(aFilter));
return walker.forget();
}
@ -9413,7 +9383,7 @@ nsDocument::OnPageHide(bool aPersisted,
SetImagesNeedAnimating(false);
}
MozExitPointerLock();
ExitPointerLock();
// Now send out a PageHide event.
nsCOMPtr<EventTarget> target = aDispatchStartTarget;
@ -12250,7 +12220,7 @@ DispatchPointerLockChange(nsIDocument* aTarget)
RefPtr<AsyncEventDispatcher> asyncDispatcher =
new AsyncEventDispatcher(aTarget,
NS_LITERAL_STRING("mozpointerlockchange"),
NS_LITERAL_STRING("pointerlockchange"),
true,
false);
asyncDispatcher->PostDOMEvent();
@ -12265,7 +12235,7 @@ DispatchPointerLockError(nsIDocument* aTarget, const char* aMessage)
RefPtr<AsyncEventDispatcher> asyncDispatcher =
new AsyncEventDispatcher(aTarget,
NS_LITERAL_STRING("mozpointerlockerror"),
NS_LITERAL_STRING("pointerlockerror"),
true,
false);
asyncDispatcher->PostDOMEvent();
@ -12531,21 +12501,21 @@ nsIDocument::UnlockPointer(nsIDocument* aDoc)
NS_IMETHODIMP
nsDocument::MozExitPointerLock()
{
nsIDocument::MozExitPointerLock();
nsIDocument::ExitPointerLock();
return NS_OK;
}
NS_IMETHODIMP
nsDocument::GetMozPointerLockElement(nsIDOMElement** aPointerLockedElement)
{
Element* el = nsIDocument::GetMozPointerLockElement();
Element* el = nsIDocument::GetPointerLockElement();
nsCOMPtr<nsIDOMElement> retval = do_QueryInterface(el);
retval.forget(aPointerLockedElement);
return NS_OK;
}
Element*
nsIDocument::GetMozPointerLockElement()
nsIDocument::GetPointerLockElement()
{
nsCOMPtr<Element> pointerLockedElement =
do_QueryReferent(EventStateManager::sPointerLockedElement);

View File

@ -426,7 +426,7 @@ nsFrameLoader::ReallyStartLoadingInternal()
// We'll use our principal, not that of the document loaded inside us. This
// is very important; needed to prevent XSS attacks on documents loaded in
// subframes!
loadInfo->SetOwner(mOwnerContent->NodePrincipal());
loadInfo->SetTriggeringPrincipal(mOwnerContent->NodePrincipal());
nsCOMPtr<nsIURI> referrer;
@ -481,7 +481,7 @@ nsFrameLoader::ReallyStartLoadingInternal()
// Flags for browser frame:
if (OwnerIsMozBrowserFrame()) {
flags = nsIWebNavigation::LOAD_FLAGS_ALLOW_THIRD_PARTY_FIXUP |
nsIWebNavigation::LOAD_FLAGS_DISALLOW_INHERIT_OWNER;
nsIWebNavigation::LOAD_FLAGS_DISALLOW_INHERIT_PRINCIPAL;
}
// Kick off the load...

View File

@ -590,6 +590,12 @@ nsGenericDOMDataNode::UnbindFromTree(bool aDeep, bool aNullParent)
}
ClearInDocument();
#ifdef MOZ_STYLO
// Drop any servo node data, since it will generally need to be recomputed on
// re-insertion anyway.
ServoData().reset();
#endif
if (aNullParent || !mParent->IsInShadowTree()) {
UnsetFlags(NODE_IS_IN_SHADOW_TREE);
@ -647,6 +653,12 @@ nsGenericDOMDataNode::GetAttrNameAt(uint32_t aIndex) const
return nullptr;
}
BorrowedAttrInfo
nsGenericDOMDataNode::GetAttrInfoAt(uint32_t aIndex) const
{
return BorrowedAttrInfo(nullptr, nullptr);
}
uint32_t
nsGenericDOMDataNode::GetAttrCount() const
{

View File

@ -123,6 +123,7 @@ public:
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttribute,
bool aNotify) override;
virtual const nsAttrName* GetAttrNameAt(uint32_t aIndex) const override;
virtual mozilla::dom::BorrowedAttrInfo GetAttrInfoAt(uint32_t aIndex) const override;
virtual uint32_t GetAttrCount() const override;
virtual const nsTextFragment *GetText() override;
virtual uint32_t TextLength() const override;
@ -325,7 +326,7 @@ public:
{
mRefCnt.RemovePurple();
}
private:
already_AddRefed<nsIAtom> GetCurrentValueAtom();
};

View File

@ -877,6 +877,8 @@ GK_ATOM(onpaste, "onpaste")
GK_ATOM(onpendingchange, "onpendingchange")
GK_ATOM(onpichange, "onpichange")
GK_ATOM(onpicture, "onpicture")
GK_ATOM(onpointerlockchange, "onpointerlockchange")
GK_ATOM(onpointerlockerror, "onpointerlockerror")
GK_ATOM(onpopuphidden, "onpopuphidden")
GK_ATOM(onpopuphiding, "onpopuphiding")
GK_ATOM(onpopupshowing, "onpopupshowing")
@ -996,6 +998,8 @@ GK_ATOM(placeholder, "placeholder")
GK_ATOM(plaintext, "plaintext")
GK_ATOM(playbackrate, "playbackrate")
GK_ATOM(pointSize, "point-size")
GK_ATOM(pointerlockchange, "pointerlockchange")
GK_ATOM(pointerlockerror, "pointerlockerror")
GK_ATOM(poly, "poly")
GK_ATOM(polygon, "polygon")
GK_ATOM(popup, "popup")

View File

@ -7,6 +7,7 @@
#define nsIContent_h___
#include "mozilla/Attributes.h"
#include "mozilla/dom/BorrowedAttrInfo.h"
#include "nsCaseTreatment.h" // for enum, cannot be forward-declared
#include "nsINode.h"
@ -35,7 +36,7 @@ struct IMEState;
enum nsLinkState {
eLinkState_Unvisited = 1,
eLinkState_Visited = 2,
eLinkState_NotLink = 3
eLinkState_NotLink = 3
};
// IID for the nsIContent interface
@ -102,7 +103,7 @@ public:
* and binding parent to null. In the typical case of a node being removed
* from a parent, this will be called after it has been removed from the
* parent's child list and after the nsIDocumentObserver notifications for
* the removal have been dispatched.
* the removal have been dispatched.
* @param aDeep Whether to recursively unbind the entire subtree rooted at
* this node. The only time false should be passed is when the
* parent node of the content is being destroyed.
@ -393,7 +394,7 @@ public:
nsIAtom* aName,
const nsAString& aValue,
nsCaseTreatment aCaseSensitive) const;
/**
* Test whether this content node's given attribute has the given value. If
* the attribute is not set at all, this will return false.
@ -408,7 +409,7 @@ public:
nsIAtom* aName,
nsIAtom* aValue,
nsCaseTreatment aCaseSensitive) const;
enum {
ATTR_MISSING = -1,
ATTR_VALUE_NO_MATCH = -2
@ -420,7 +421,7 @@ public:
* we return ATTR_MISSING. If there was an attribute but it didn't
* match, we return ATTR_VALUE_NO_MATCH. A non-negative result always
* indicates a match.
*
*
* @param aNameSpaceID The namespace ID of the attribute. Must not
* be kNameSpaceID_Unknown.
* @param aName The name atom of the attribute. Must not be null.
@ -447,13 +448,13 @@ public:
* @param aNotify specifies whether or not the document should be
* notified of the attribute change
*/
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttr,
virtual nsresult UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttr,
bool aNotify) = 0;
/**
* Get the namespace / name / prefix of a given attribute.
*
*
* @param aIndex the index of the attribute name
* @returns The name at the given index, or null if the index is
* out-of-bounds.
@ -464,6 +465,11 @@ public:
*/
virtual const nsAttrName* GetAttrNameAt(uint32_t aIndex) const = 0;
/**
* Gets the attribute info (name and value) for this content at a given index.
*/
virtual mozilla::dom::BorrowedAttrInfo GetAttrInfoAt(uint32_t aIndex) const = 0;
/**
* Get the number of all specified attributes.
*
@ -484,13 +490,13 @@ public:
*/
virtual uint32_t TextLength() const = 0;
/**
* Determines if an event attribute name (such as onclick) is valid for
* a given element type.
* @note calls nsContentUtils::IsEventAttributeName with right flag
* @note overridden by subclasses as needed
* @param aName the event name to look up
*/
/**
* Determines if an event attribute name (such as onclick) is valid for
* a given element type.
* @note calls nsContentUtils::IsEventAttributeName with right flag
* @note overridden by subclasses as needed
* @param aName the event name to look up
*/
virtual bool IsEventAttributeName(nsIAtom* aName)
{
return false;
@ -551,13 +557,13 @@ public:
/**
* Check if this content is focusable and in the current tab order.
* Note: most callers should use nsIFrame::IsFocusable() instead as it
* Note: most callers should use nsIFrame::IsFocusable() instead as it
* checks visibility and other layout factors as well.
* Tabbable is indicated by a nonnegative tabindex & is a subset of focusable.
* For example, only the selected radio button in a group is in the
* For example, only the selected radio button in a group is in the
* tab order, unless the radio group has no selection in which case
* all of the visible, non-disabled radio buttons in the group are
* in the tab order. On the other hand, all of the visible, non-disabled
* all of the visible, non-disabled radio buttons in the group are
* in the tab order. On the other hand, all of the visible, non-disabled
* radio buttons are always focusable via clicking or script.
* Also, depending on either the accessibility.tabfocus pref or
* a system setting (nowadays: Full keyboard access, mac only)
@ -778,7 +784,7 @@ public:
}
/**
* This method is called when the parser begins creating the element's
* This method is called when the parser begins creating the element's
* children, if any are present.
*
* This is only called for XTF elements currently.

View File

@ -2549,14 +2549,14 @@ public:
mozilla::ErrorResult& rv) const;
already_AddRefed<mozilla::dom::NodeIterator>
CreateNodeIterator(nsINode& aRoot, uint32_t aWhatToShow,
const mozilla::dom::NodeFilterHolder& aFilter,
mozilla::dom::NodeFilterHolder aFilter,
mozilla::ErrorResult& rv) const;
already_AddRefed<mozilla::dom::TreeWalker>
CreateTreeWalker(nsINode& aRoot, uint32_t aWhatToShow,
mozilla::dom::NodeFilter* aFilter, mozilla::ErrorResult& rv) const;
already_AddRefed<mozilla::dom::TreeWalker>
CreateTreeWalker(nsINode& aRoot, uint32_t aWhatToShow,
const mozilla::dom::NodeFilterHolder& aFilter,
mozilla::dom::NodeFilterHolder aFilter,
mozilla::ErrorResult& rv) const;
// Deprecated WebIDL bits
@ -2604,8 +2604,8 @@ public:
return !!GetFullscreenElement();
}
void ExitFullscreen();
Element* GetMozPointerLockElement();
void MozExitPointerLock()
Element* GetPointerLockElement();
void ExitPointerLock()
{
UnlockPointer(this);
}

View File

@ -53,6 +53,11 @@ public:
return mIsDying;
}
// GetGlobalJSObject may return a gray object. If this ever changes so that
// it stops doing that, please simplify the code in FindAssociatedGlobal in
// BindingUtils.h that does JS::ExposeObjectToActiveJS on the return value of
// GetGlobalJSObject. Also, in that case the JS::ExposeObjectToActiveJS in
// AutoJSAPI::InitInternal can probably be removed.
virtual JSObject* GetGlobalJSObject() = 0;
// This method is not meant to be overridden.

View File

@ -149,12 +149,6 @@ nsINode::~nsINode()
{
MOZ_ASSERT(!HasSlots(), "nsNodeUtils::LastRelease was not called?");
MOZ_ASSERT(mSubtreeRoot == this, "Didn't restore state properly?");
#ifdef MOZ_STYLO
if (mServoNodeData) {
Servo_DropNodeData(mServoNodeData);
}
#endif
}
void*

View File

@ -8,6 +8,7 @@
#define nsINode_h___
#include "mozilla/Likely.h"
#include "mozilla/UniquePtr.h"
#include "nsCOMPtr.h" // for member, local
#include "nsGkAtoms.h" // for nsGkAtoms::baseURIProperty
#include "nsIDOMNode.h"
@ -51,7 +52,22 @@ class nsIURI;
class nsNodeSupportsWeakRefTearoff;
class nsNodeWeakReference;
class nsDOMMutationObserver;
// We declare the bare minimum infrastructure here to allow us to have a
// UniquePtr<ServoNodeData> on nsINode.
struct ServoNodeData;
extern "C" void Servo_DropNodeData(ServoNodeData*);
namespace mozilla {
template<>
class DefaultDelete<ServoNodeData>
{
public:
void operator()(ServoNodeData* aPtr) const
{
Servo_DropNodeData(aPtr);
}
};
} // namespace mozilla
namespace mozilla {
class EventListenerManager;
@ -340,9 +356,6 @@ public:
, mFirstChild(nullptr)
, mSubtreeRoot(this)
, mSlots(nullptr)
#ifdef MOZ_STYLO
, mServoNodeData(nullptr)
#endif
{
}
#endif
@ -2059,7 +2072,7 @@ public:
#undef TOUCH_EVENT
#undef EVENT
ServoNodeData* GetServoNodeData() {
mozilla::UniquePtr<ServoNodeData>& ServoData() {
#ifdef MOZ_STYLO
return mServoNodeData;
#else
@ -2067,15 +2080,6 @@ public:
#endif
}
void SetServoNodeData(ServoNodeData* aData) {
#ifdef MOZ_STYLO
MOZ_ASSERT(!mServoNodeData);
mServoNodeData = aData;
#else
MOZ_CRASH("Setting servo node data in non-stylo build");
#endif
}
protected:
static bool Traverse(nsINode *tmp, nsCycleCollectionTraversalCallback &cb);
static void Unlink(nsINode *tmp);
@ -2116,7 +2120,7 @@ protected:
#ifdef MOZ_STYLO
// Layout data managed by Servo.
ServoNodeData* mServoNodeData;
mozilla::UniquePtr<ServoNodeData> mServoNodeData;
#endif
};

View File

@ -108,7 +108,7 @@ nsLocation::CheckURL(nsIURI* aURI, nsIDocShellLoadInfo** aLoadInfo)
nsCOMPtr<nsIDocShell> docShell(do_QueryReferent(mDocShell));
NS_ENSURE_TRUE(docShell, NS_ERROR_NOT_AVAILABLE);
nsCOMPtr<nsISupports> owner;
nsCOMPtr<nsIPrincipal> triggeringPrincipal;
nsCOMPtr<nsIURI> sourceURI;
net::ReferrerPolicy referrerPolicy = net::RP_Default;
@ -153,7 +153,7 @@ nsLocation::CheckURL(nsIURI* aURI, nsIDocShellLoadInfo** aLoadInfo)
rv = doc->NodePrincipal()->GetURI(getter_AddRefs(principalURI));
NS_ENSURE_SUCCESS(rv, rv);
owner = doc->NodePrincipal();
triggeringPrincipal = doc->NodePrincipal();
referrerPolicy = doc->GetReferrerPolicy();
bool urisEqual = false;
@ -183,7 +183,7 @@ nsLocation::CheckURL(nsIURI* aURI, nsIDocShellLoadInfo** aLoadInfo)
// subjectPrincipal, wich is the principal of the current JS
// compartment, or a null principal in case there is no
// compartment yet.
owner = nsContentUtils::SubjectPrincipal();
triggeringPrincipal = nsContentUtils::SubjectPrincipal();
}
}
@ -192,7 +192,7 @@ nsLocation::CheckURL(nsIURI* aURI, nsIDocShellLoadInfo** aLoadInfo)
docShell->CreateLoadInfo(getter_AddRefs(loadInfo));
NS_ENSURE_TRUE(loadInfo, NS_ERROR_FAILURE);
loadInfo->SetOwner(owner);
loadInfo->SetTriggeringPrincipal(triggeringPrincipal);
if (sourceURI) {
loadInfo->SetReferrer(sourceURI);

View File

@ -92,7 +92,7 @@ private:
};
/**
* Due to a compiler bug in VisualAge C++ for AIX, we need to return the
* Due to a compiler bug in VisualAge C++ for AIX, we need to return the
* address of the first index into mAttrs here, instead of simply
* returning mAttrs itself.
*

View File

@ -18,10 +18,10 @@ using namespace mozilla::dom;
nsTraversal::nsTraversal(nsINode *aRoot,
uint32_t aWhatToShow,
const NodeFilterHolder &aFilter) :
NodeFilterHolder aFilter) :
mRoot(aRoot),
mWhatToShow(aWhatToShow),
mFilter(aFilter),
mFilter(Move(aFilter)),
mInAcceptNode(false)
{
NS_ASSERTION(aRoot, "invalid root in call to nsTraversal constructor");

View File

@ -25,7 +25,7 @@ class nsTraversal
public:
nsTraversal(nsINode *aRoot,
uint32_t aWhatToShow,
const mozilla::dom::NodeFilterHolder &aFilter);
mozilla::dom::NodeFilterHolder aFilter);
virtual ~nsTraversal();
protected:

View File

@ -245,7 +245,7 @@ nsXHTMLContentSerializer::SerializeAttributes(nsIContent* aContent,
if (mIsCopying && kNameSpaceID_XHTML == contentNamespaceID) {
// Need to keep track of OL and LI elements in order to get ordinal number
// Need to keep track of OL and LI elements in order to get ordinal number
// for the LI.
if (aTagName == nsGkAtoms::ol) {
// We are copying and current node is an OL;
@ -306,7 +306,9 @@ nsXHTMLContentSerializer::SerializeAttributes(nsIContent* aContent,
continue;
}
const nsAttrName* name = aContent->GetAttrNameAt(index);
BorrowedAttrInfo info = aContent->GetAttrInfoAt(index);
const nsAttrName* name = info.mName;
int32_t namespaceID = name->NamespaceID();
nsIAtom* attrName = name->LocalName();
nsIAtom* attrPrefix = name->GetPrefix();
@ -331,7 +333,7 @@ nsXHTMLContentSerializer::SerializeAttributes(nsIContent* aContent,
addNSAttr = ConfirmPrefix(prefixStr, uriStr, aOriginalElement, true);
}
aContent->GetAttr(namespaceID, attrName, valueStr);
info.mValue->ToString(valueStr);
nsDependentAtomString nameStr(attrName);
bool isJS = false;
@ -354,7 +356,7 @@ nsXHTMLContentSerializer::SerializeAttributes(nsIContent* aContent,
isJS = IsJavaScript(aContent, attrName, namespaceID, valueStr);
if (namespaceID == kNameSpaceID_None &&
if (namespaceID == kNameSpaceID_None &&
((attrName == nsGkAtoms::href) ||
(attrName == nsGkAtoms::src))) {
// Make all links absolute when converting only the selection:
@ -560,7 +562,7 @@ nsXHTMLContentSerializer::IsShorthandAttr(const nsIAtom* aAttrName,
// compact
if ((aAttrName == nsGkAtoms::compact) &&
(aElementName == nsGkAtoms::dir ||
(aElementName == nsGkAtoms::dir ||
aElementName == nsGkAtoms::dl ||
aElementName == nsGkAtoms::menu ||
aElementName == nsGkAtoms::ol ||
@ -678,7 +680,7 @@ nsXHTMLContentSerializer::LineBreakBeforeOpen(int32_t aNamespaceID, nsIAtom* aNa
return mAddSpace;
}
bool
bool
nsXHTMLContentSerializer::LineBreakAfterOpen(int32_t aNamespaceID, nsIAtom* aName)
{
@ -709,7 +711,7 @@ nsXHTMLContentSerializer::LineBreakAfterOpen(int32_t aNamespaceID, nsIAtom* aNam
return false;
}
bool
bool
nsXHTMLContentSerializer::LineBreakBeforeClose(int32_t aNamespaceID, nsIAtom* aName)
{
@ -731,7 +733,7 @@ nsXHTMLContentSerializer::LineBreakBeforeClose(int32_t aNamespaceID, nsIAtom* aN
return false;
}
bool
bool
nsXHTMLContentSerializer::LineBreakAfterClose(int32_t aNamespaceID, nsIAtom* aName)
{
@ -891,7 +893,7 @@ nsXHTMLContentSerializer::SerializeLIValueAttribute(nsIContent* aElement,
// Set value attribute.
nsAutoString valueStr;
//As serializer needs to use this valueAttr we are creating here,
//As serializer needs to use this valueAttr we are creating here,
valueStr.AppendInt(startVal + offset);
NS_ENSURE_TRUE(SerializeAttr(EmptyString(), NS_LITERAL_STRING("value"),
valueStr, aStr, false), false);
@ -933,7 +935,7 @@ nsXHTMLContentSerializer::HasNoChildren(nsIContent * aContent) {
for (nsIContent* child = aContent->GetFirstChild();
child;
child = child->GetNextSibling()) {
if (!child->IsNodeOfType(nsINode::eTEXT))
return false;

View File

@ -73,7 +73,7 @@ nsXMLContentSerializer::~nsXMLContentSerializer()
NS_IMPL_ISUPPORTS(nsXMLContentSerializer, nsIContentSerializer)
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::Init(uint32_t aFlags, uint32_t aWrapColumn,
const char* aCharSet, bool aIsCopying,
bool aRewriteEncodingDeclaration)
@ -152,7 +152,7 @@ nsXMLContentSerializer::AppendTextData(nsIContent* aNode,
// error.
return NS_OK;
}
if (frag->Is2b()) {
const char16_t *strStart = frag->Get2b() + aStartOffset;
if (aTranslateEntities) {
@ -178,7 +178,7 @@ nsXMLContentSerializer::AppendTextData(nsIContent* aNode,
return NS_OK;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendText(nsIContent* aText,
int32_t aStartOffset,
int32_t aEndOffset,
@ -209,7 +209,7 @@ nsXMLContentSerializer::AppendText(nsIContent* aText,
return NS_OK;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendCDATASection(nsIContent* aCDATASection,
int32_t aStartOffset,
int32_t aEndOffset,
@ -244,7 +244,7 @@ nsXMLContentSerializer::AppendCDATASection(nsIContent* aCDATASection,
return NS_OK;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendProcessingInstruction(nsIContent* aPI,
int32_t aStartOffset,
int32_t aEndOffset,
@ -293,7 +293,7 @@ nsXMLContentSerializer::AppendProcessingInstruction(nsIContent* aPI,
return NS_OK;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendComment(nsIContent* aComment,
int32_t aStartOffset,
int32_t aEndOffset,
@ -350,7 +350,7 @@ nsXMLContentSerializer::AppendComment(nsIContent* aComment,
return NS_OK;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendDoctype(nsIContent* aDocType,
nsAString& aStr)
{
@ -411,13 +411,13 @@ nsXMLContentSerializer::AppendDoctype(nsIContent* aDocType,
NS_ENSURE_TRUE(AppendToString(systemId, aStr), NS_ERROR_OUT_OF_MEMORY);
NS_ENSURE_TRUE(AppendToString(quote, aStr), NS_ERROR_OUT_OF_MEMORY);
}
if (!internalSubset.IsEmpty()) {
NS_ENSURE_TRUE(AppendToString(NS_LITERAL_STRING(" ["), aStr), NS_ERROR_OUT_OF_MEMORY);
NS_ENSURE_TRUE(AppendToString(internalSubset, aStr), NS_ERROR_OUT_OF_MEMORY);
NS_ENSURE_TRUE(AppendToString(char16_t(']'), aStr), NS_ERROR_OUT_OF_MEMORY);
}
NS_ENSURE_TRUE(AppendToString(kGreaterThan, aStr), NS_ERROR_OUT_OF_MEMORY);
MaybeFlagNewlineForRootNode(aDocType);
@ -516,7 +516,7 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
break;
}
haveSeenOurPrefix = true;
haveSeenOurPrefix = true;
// If they don't, and either:
// 1) We have a prefix (so we'd be redeclaring this prefix to point to a
@ -544,7 +544,7 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
continue;
}
}
// If we've found a URI match, then record the first one
if (!uriMatch && aURI.Equals(decl.mURI)) {
// Need to check that decl->mPrefix is not declared anywhere closer to
@ -554,13 +554,13 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
for (index2 = count-1; index2 > index && prefixOK; --index2) {
prefixOK = (mNameSpaceStack[index2].mPrefix != decl.mPrefix);
}
if (prefixOK) {
uriMatch = true;
closestURIMatch.Assign(decl.mPrefix);
}
}
--index;
}
@ -570,7 +570,7 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
// 2) There is nothing on the namespace stack that has aPrefix as the prefix
// and a _different_ URI, except for the case aPrefix.IsEmpty (and
// possible default namespaces on ancestors)
// So if uriMatch is set it's OK to use the closestURIMatch prefix. The one
// exception is when closestURIMatch is actually empty (default namespace
// decl) and we must have a prefix.
@ -578,7 +578,7 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
aPrefix.Assign(closestURIMatch);
return false;
}
if (aPrefix.IsEmpty()) {
// At this point, aPrefix is empty (which means we never had a prefix to
// start with). If we must have a prefix, just generate a new prefix and
@ -654,7 +654,7 @@ nsXMLContentSerializer::SerializeAttr(const nsAString& aPrefix,
// See http://www.w3.org/TR/REC-html40/appendix/notes.html#h-B.3.2.2 for
// the standard on character entity references in values. We also have to
// make sure to escape any '&' characters.
bool bIncludesSingle = false;
bool bIncludesDouble = false;
nsAString::const_iterator iCurr, iEnd;
@ -686,7 +686,7 @@ nsXMLContentSerializer::SerializeAttr(const nsAString& aPrefix,
// FALSE TRUE " FALSE
// TRUE FALSE ' FALSE
// TRUE TRUE " TRUE
char16_t cDelimiter =
char16_t cDelimiter =
(bIncludesDouble && !bIncludesSingle) ? char16_t('\'') : char16_t('"');
NS_ENSURE_TRUE(attrString.Append(char16_t('='), mozilla::fallible), false);
NS_ENSURE_TRUE(attrString.Append(cDelimiter, mozilla::fallible), false);
@ -716,7 +716,7 @@ nsXMLContentSerializer::SerializeAttr(const nsAString& aPrefix,
return true;
}
uint32_t
uint32_t
nsXMLContentSerializer::ScanNamespaceDeclarations(nsIContent* aContent,
nsIContent *aOriginalElement,
const nsAString& aTagNamespaceURI)
@ -729,11 +729,13 @@ nsXMLContentSerializer::ScanNamespaceDeclarations(nsIContent* aContent,
// First scan for namespace declarations, pushing each on the stack
uint32_t skipAttr = count;
for (index = 0; index < count; index++) {
const nsAttrName* name = aContent->GetAttrNameAt(index);
const BorrowedAttrInfo info = aContent->GetAttrInfoAt(index);
const nsAttrName* name = info.mName;
int32_t namespaceID = name->NamespaceID();
nsIAtom *attrName = name->LocalName();
if (namespaceID == kNameSpaceID_XMLNS ||
// Also push on the stack attrs named "xmlns" in the null
// namespace... because once we serialize those out they'll look like
@ -742,7 +744,7 @@ nsXMLContentSerializer::ScanNamespaceDeclarations(nsIContent* aContent,
// in the xmlns namespace?
(namespaceID == kNameSpaceID_None &&
attrName == nsGkAtoms::xmlns)) {
aContent->GetAttr(namespaceID, attrName, uriStr);
info.mValue->ToString(uriStr);
if (!name->GetPrefix()) {
if (aTagNamespaceURI.IsEmpty() && !uriStr.IsEmpty()) {
@ -865,14 +867,14 @@ nsXMLContentSerializer::SerializeAttributes(nsIContent* aContent,
nsContentUtils::NameSpaceManager()->GetNameSpaceURI(namespaceID, uriStr);
addNSAttr = ConfirmPrefix(prefixStr, uriStr, aOriginalElement, true);
}
aContent->GetAttr(namespaceID, attrName, valueStr);
nsDependentAtomString nameStr(attrName);
bool isJS = IsJavaScript(aContent, attrName, namespaceID, valueStr);
NS_ENSURE_TRUE(SerializeAttr(prefixStr, nameStr, valueStr, aStr, !isJS), false);
if (addNSAttr) {
NS_ASSERTION(!prefixStr.IsEmpty(),
"Namespaced attributes must have a prefix");
@ -884,7 +886,7 @@ nsXMLContentSerializer::SerializeAttributes(nsIContent* aContent,
return true;
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendElementStart(Element* aElement,
Element* aOriginalElement,
nsAString& aStr)
@ -1026,7 +1028,7 @@ nsXMLContentSerializer::AppendEndOfElementStart(Element* aElement,
return AppendToString(NS_LITERAL_STRING("/>"), aStr);
}
NS_IMETHODIMP
NS_IMETHODIMP
nsXMLContentSerializer::AppendElementEnd(Element* aElement,
nsAString& aStr)
{
@ -1050,7 +1052,7 @@ nsXMLContentSerializer::AppendElementEnd(Element* aElement,
}
nsAutoString tagPrefix, tagLocalName, tagNamespaceURI;
aElement->NodeInfo()->GetPrefix(tagPrefix);
aElement->NodeInfo()->GetName(tagLocalName);
aElement->NodeInfo()->GetNamespaceURI(tagNamespaceURI);
@ -1121,7 +1123,7 @@ nsXMLContentSerializer::AppendDocumentStart(nsIDocument *aDocument,
NS_NAMED_LITERAL_STRING(endQuote, "\"");
aStr += NS_LITERAL_STRING("<?xml version=\"") + version + endQuote;
if (!mCharset.IsEmpty()) {
aStr += NS_LITERAL_STRING(" encoding=\"") +
NS_ConvertASCIItoUTF16(mCharset) + endQuote;
@ -1367,19 +1369,19 @@ nsXMLContentSerializer::LineBreakBeforeOpen(int32_t aNamespaceID, nsIAtom* aName
return mAddSpace;
}
bool
bool
nsXMLContentSerializer::LineBreakAfterOpen(int32_t aNamespaceID, nsIAtom* aName)
{
return false;
}
bool
bool
nsXMLContentSerializer::LineBreakBeforeClose(int32_t aNamespaceID, nsIAtom* aName)
{
return mAddSpace;
}
bool
bool
nsXMLContentSerializer::LineBreakAfterClose(int32_t aNamespaceID, nsIAtom* aName)
{
return false;
@ -1581,11 +1583,11 @@ nsXMLContentSerializer::AppendWrapped_NonWhitespaceSequence(
}
else { // we reach the max column
if (!thisSequenceStartsAtBeginningOfLine &&
(mAddSpace || (!mDoFormat && aSequenceStartAfterAWhiteSpace))) {
(mAddSpace || (!mDoFormat && aSequenceStartAfterAWhiteSpace))) {
// when !mDoFormat, mAddSpace is not used, mAddSpace is always false
// so, in the case where mDoWrap && !mDoFormat, if we want to enter in this condition...
// We can avoid to wrap. We try to add the whole block
// We can avoid to wrap. We try to add the whole block
// in an empty new line
NS_ENSURE_TRUE(AppendNewLineToString(aOutputStr), false);

View File

@ -1014,7 +1014,7 @@ NativeInterface2JSObjectAndThrowIfFailed(JSContext* aCx,
MOZ_ASSERT(NS_IsMainThread());
if (!XPCConvert::NativeInterface2JSObject(aRetval, nullptr, aHelper, aIID,
nullptr, aAllowNativeWrapper, &rv)) {
aAllowNativeWrapper, &rv)) {
// I can't tell if NativeInterface2JSObject throws JS exceptions
// or not. This is a sloppy stab at the right semantics; the
// method really ought to be fixed to behave consistently.
@ -2025,8 +2025,9 @@ ReparentWrapper(JSContext* aCx, JS::Handle<JSObject*> aObjArg)
js::GetGlobalForObjectCrossCompartment(aObj));
MOZ_ASSERT(js::GetGlobalForObjectCrossCompartment(oldParent) == oldParent);
JS::Rooted<JSObject*> newParent(aCx, domClass->mGetParent(aCx, aObj));
MOZ_ASSERT(js::GetGlobalForObjectCrossCompartment(newParent) == newParent);
JS::Rooted<JSObject*> newParent(aCx,
domClass->mGetAssociatedGlobal(aCx, aObj));
MOZ_ASSERT(JS_IsGlobalObject(newParent));
JSAutoCompartment oldAc(aCx, oldParent);

View File

@ -1524,7 +1524,7 @@ WrapObject(JSContext* cx, JSObject& p, JS::MutableHandle<JS::Value> rval)
// don't want those for our parent object.
template<typename T>
static inline JSObject*
WrapNativeISupportsParent(JSContext* cx, T* p, nsWrapperCache* cache)
WrapNativeISupports(JSContext* cx, T* p, nsWrapperCache* cache)
{
qsObjectHelper helper(ToSupports(p), cache);
JS::Rooted<JSObject*> scope(cx, JS::CurrentGlobalOrNull(cx));
@ -1537,7 +1537,7 @@ WrapNativeISupportsParent(JSContext* cx, T* p, nsWrapperCache* cache)
// Fallback for when our parent is not a WebIDL binding object.
template<typename T, bool isISupports=IsBaseOf<nsISupports, T>::value>
struct WrapNativeParentFallback
struct WrapNativeFallback
{
static inline JSObject* Wrap(JSContext* cx, T* parent, nsWrapperCache* cache)
{
@ -1548,18 +1548,18 @@ struct WrapNativeParentFallback
// Fallback for when our parent is not a WebIDL binding object but _is_ an
// nsISupports object.
template<typename T >
struct WrapNativeParentFallback<T, true >
struct WrapNativeFallback<T, true >
{
static inline JSObject* Wrap(JSContext* cx, T* parent, nsWrapperCache* cache)
{
return WrapNativeISupportsParent(cx, parent, cache);
return WrapNativeISupports(cx, parent, cache);
}
};
// Wrapping of our native parent, for cases when it's a WebIDL object (though
// possibly preffed off).
template<typename T, bool hasWrapObject=NativeHasMember<T>::WrapObject>
struct WrapNativeParentHelper
struct WrapNativeHelper
{
static inline JSObject* Wrap(JSContext* cx, T* parent, nsWrapperCache* cache)
{
@ -1567,14 +1567,20 @@ struct WrapNativeParentHelper
JSObject* obj;
if ((obj = cache->GetWrapper())) {
// GetWrapper always unmarks gray.
MOZ_ASSERT(!JS::ObjectIsMarkedGray(obj));
return obj;
}
// Inline this here while we have non-dom objects in wrapper caches.
if (!CouldBeDOMBinding(parent)) {
obj = WrapNativeParentFallback<T>::Wrap(cx, parent, cache);
// WrapNativeFallback never returns a gray thing.
obj = WrapNativeFallback<T>::Wrap(cx, parent, cache);
MOZ_ASSERT_IF(obj, !JS::ObjectIsMarkedGray(obj));
} else {
// WrapObject never returns a gray thing.
obj = parent->WrapObject(cx, nullptr);
MOZ_ASSERT_IF(obj, !JS::ObjectIsMarkedGray(obj));
}
return obj;
@ -1584,7 +1590,7 @@ struct WrapNativeParentHelper
// Wrapping of our native parent, for cases when it's not a WebIDL object. In
// this case it must be nsISupports.
template<typename T>
struct WrapNativeParentHelper<T, false>
struct WrapNativeHelper<T, false>
{
static inline JSObject* Wrap(JSContext* cx, T* parent, nsWrapperCache* cache)
{
@ -1592,81 +1598,100 @@ struct WrapNativeParentHelper<T, false>
if (cache && (obj = cache->GetWrapper())) {
#ifdef DEBUG
JS::Rooted<JSObject*> rootedObj(cx, obj);
NS_ASSERTION(WrapNativeISupportsParent(cx, parent, cache) == rootedObj,
NS_ASSERTION(WrapNativeISupports(cx, parent, cache) == rootedObj,
"Unexpected object in nsWrapperCache");
obj = rootedObj;
#endif
MOZ_ASSERT(!JS::ObjectIsMarkedGray(obj));
return obj;
}
return WrapNativeISupportsParent(cx, parent, cache);
obj = WrapNativeISupports(cx, parent, cache);
MOZ_ASSERT_IF(obj, !JS::ObjectIsMarkedGray(obj));
return obj;
}
};
// Wrapping of our native parent.
// Finding the associated global for an object.
template<typename T>
static inline JSObject*
WrapNativeParent(JSContext* cx, T* p, nsWrapperCache* cache,
bool useXBLScope = false)
FindAssociatedGlobal(JSContext* cx, T* p, nsWrapperCache* cache,
bool useXBLScope = false)
{
if (!p) {
return JS::CurrentGlobalOrNull(cx);
}
JSObject* parent = WrapNativeParentHelper<T>::Wrap(cx, p, cache);
if (!parent || !useXBLScope) {
return parent;
JSObject* obj = WrapNativeHelper<T>::Wrap(cx, p, cache);
if (!obj) {
return nullptr;
}
MOZ_ASSERT(!JS::ObjectIsMarkedGray(obj));
obj = js::GetGlobalForObjectCrossCompartment(obj);
if (!useXBLScope) {
return obj;
}
// If useXBLScope is true, it means that the canonical reflector for this
// native object should live in the content XBL scope. Note that we never put
// anonymous content inside an add-on scope.
if (xpc::IsInContentXBLScope(parent)) {
return parent;
if (xpc::IsInContentXBLScope(obj)) {
return obj;
}
JS::Rooted<JSObject*> rootedParent(cx, parent);
JS::Rooted<JSObject*> xblScope(cx, xpc::GetXBLScope(cx, rootedParent));
NS_ENSURE_TRUE(xblScope, nullptr);
JSAutoCompartment ac(cx, xblScope);
if (NS_WARN_IF(!JS_WrapObject(cx, &rootedParent))) {
return nullptr;
}
return rootedParent;
JS::Rooted<JSObject*> rootedObj(cx, obj);
JSObject* xblScope = xpc::GetXBLScope(cx, rootedObj);
MOZ_ASSERT_IF(xblScope, JS_IsGlobalObject(xblScope));
MOZ_ASSERT_IF(xblScope, !JS::ObjectIsMarkedGray(xblScope));
return xblScope;
}
// Wrapping of our native parent, when we don't want to explicitly pass in
// things like the nsWrapperCache for it.
// Finding of the associated global for an object, when we don't want to
// explicitly pass in things like the nsWrapperCache for it.
template<typename T>
static inline JSObject*
WrapNativeParent(JSContext* cx, const T& p)
FindAssociatedGlobal(JSContext* cx, const T& p)
{
return WrapNativeParent(cx, GetParentPointer(p), GetWrapperCache(p), GetUseXBLScope(p));
return FindAssociatedGlobal(cx, GetParentPointer(p), GetWrapperCache(p), GetUseXBLScope(p));
}
// Specialization for the case of nsIGlobalObject, since in that case
// we can just get the JSObject* directly.
template<>
inline JSObject*
WrapNativeParent(JSContext* cx, nsIGlobalObject* const& p)
FindAssociatedGlobal(JSContext* cx, nsIGlobalObject* const& p)
{
return p ? p->GetGlobalJSObject() : JS::CurrentGlobalOrNull(cx);
if (!p) {
return JS::CurrentGlobalOrNull(cx);
}
JSObject* global = p->GetGlobalJSObject();
if (!global) {
return nullptr;
}
MOZ_ASSERT(JS_IsGlobalObject(global));
// This object could be gray if the nsIGlobalObject is the only thing keeping
// it alive.
JS::ExposeObjectToActiveJS(global);
return global;
}
template<typename T, bool WrapperCached=NativeHasMember<T>::GetParentObject>
struct GetParentObject
template<typename T,
bool hasAssociatedGlobal=NativeHasMember<T>::GetParentObject>
struct FindAssociatedGlobalForNative
{
static JSObject* Get(JSContext* cx, JS::Handle<JSObject*> obj)
{
MOZ_ASSERT(js::IsObjectInContextCompartment(obj, cx));
T* native = UnwrapDOMObject<T>(obj);
JSObject* wrappedParent = WrapNativeParent(cx, native->GetParentObject());
return wrappedParent ? js::GetGlobalForObjectCrossCompartment(wrappedParent) : nullptr;
return FindAssociatedGlobal(cx, native->GetParentObject());
}
};
template<typename T>
struct GetParentObject<T, false>
struct FindAssociatedGlobalForNative<T, false>
{
static JSObject* Get(JSContext* cx, JS::Handle<JSObject*> obj)
{

View File

@ -373,12 +373,18 @@ public:
NS_IF_ADDREF(aCallback);
}
explicit CallbackObjectHolder(const CallbackObjectHolder& aOther)
CallbackObjectHolder(CallbackObjectHolder&& aOther)
: mPtrBits(aOther.mPtrBits)
{
NS_IF_ADDREF(GetISupports());
aOther.mPtrBits = 0;
static_assert(sizeof(CallbackObjectHolder) == sizeof(void*),
"This object is expected to be as small as a pointer, and it "
"is currently passed by value in various places. If it is "
"bloating, we may want to pass it by reference then.");
}
CallbackObjectHolder(const CallbackObjectHolder& aOther) = delete;
CallbackObjectHolder()
: mPtrBits(0)
{}
@ -402,13 +408,15 @@ public:
NS_IF_ADDREF(aCallback);
}
void operator=(const CallbackObjectHolder& aOther)
void operator=(CallbackObjectHolder&& aOther)
{
UnlinkSelf();
mPtrBits = aOther.mPtrBits;
NS_IF_ADDREF(GetISupports());
aOther.mPtrBits = 0;
}
void operator=(const CallbackObjectHolder& aOther) = delete;
nsISupports* GetISupports() const
{
return reinterpret_cast<nsISupports*>(mPtrBits & ~XPCOMCallbackFlag);
@ -420,6 +428,14 @@ public:
return GetISupports();
}
CallbackObjectHolder Clone() const
{
CallbackObjectHolder result;
result.mPtrBits = mPtrBits;
NS_IF_ADDREF(GetISupports());
return result;
}
// Even if HasWebIDLCallback returns true, GetWebIDLCallback() might still
// return null.
bool HasWebIDLCallback() const

View File

@ -390,7 +390,7 @@ def DOMClass(descriptor):
{ ${protoChain} },
IsBaseOf<nsISupports, ${nativeType} >::value,
${hooks},
GetParentObject<${nativeType}>::Get,
FindAssociatedGlobalForNative<${nativeType}>::Get,
GetProtoObjectHandle,
GetCCParticipant<${nativeType}>::Get()
""",
@ -3582,10 +3582,12 @@ class CGWrapWithCacheMethod(CGAbstractMethod):
MOZ_ASSERT(ToSupportsIsOnPrimaryInheritanceChain(aObject, aCache),
"nsISupports must be on our primary inheritance chain");
JS::Rooted<JSObject*> parent(aCx, WrapNativeParent(aCx, aObject->GetParentObject()));
if (!parent) {
JS::Rooted<JSObject*> global(aCx, FindAssociatedGlobal(aCx, aObject->GetParentObject()));
if (!global) {
return false;
}
MOZ_ASSERT(JS_IsGlobalObject(global));
MOZ_ASSERT(!JS::ObjectIsMarkedGray(global));
// That might have ended up wrapping us already, due to the wonders
// of XBL. Check for that, and bail out as needed.
@ -3597,8 +3599,7 @@ class CGWrapWithCacheMethod(CGAbstractMethod):
return true;
}
JSAutoCompartment ac(aCx, parent);
JS::Rooted<JSObject*> global(aCx, js::GetGlobalForObjectCrossCompartment(parent));
JSAutoCompartment ac(aCx, global);
$*{declareProto}
$*{createObject}
@ -8565,7 +8566,7 @@ class CGSpecializedGetter(CGAbstractStaticMethod):
CGAbstractStaticMethod.__init__(self, descriptor, name, "bool", args)
def definition_body(self):
if self.attr.maplikeOrSetlike:
if self.attr.isMaplikeOrSetlikeAttr():
# If the interface is maplike/setlike, there will be one getter
# method for the size property of the backing object. Due to having
# to unpack the backing object from the slot, this requires its own
@ -13088,6 +13089,16 @@ class ForwardDeclarationBuilder:
self.decls = set()
self.children = {}
def _ensureNonTemplateType(self, type):
if "<" in type:
# This is a templated type. We don't really know how to
# forward-declare those, and trying to do it naively is not going to
# go well (e.g. we may have :: characters inside the type we're
# templated on!). Just bail out.
raise TypeError("Attempt to use ForwardDeclarationBuilder on "
"templated type %s. We don't know how to do that "
"yet." % type)
def _listAdd(self, namespaces, name, isStruct=False):
"""
Add a forward declaration, where |namespaces| is a list of namespaces.
@ -13105,6 +13116,7 @@ class ForwardDeclarationBuilder:
Add a forward declaration to the mozilla::dom:: namespace. |name| should not
contain any other namespaces.
"""
self._ensureNonTemplateType(name);
self._listAdd(["mozilla", "dom"], name, isStruct)
def add(self, nativeType, isStruct=False):
@ -13112,6 +13124,7 @@ class ForwardDeclarationBuilder:
Add a forward declaration, where |nativeType| is a string containing
the type and its namespaces, in the usual C++ way.
"""
self._ensureNonTemplateType(nativeType);
components = nativeType.split('::')
self._listAdd(components[:-1], components[-1], isStruct)
@ -13923,6 +13936,16 @@ class CGExampleMethod(CGNativeMember):
breakAfter=breakAfter,
variadicIsSequence=True)
def declare(self, cgClass):
assert self.member.isMethod()
# We skip declaring ourselves if this is a maplike/setlike/iterable
# method, because those get implemented automatically by the binding
# machinery, so the implementor of the interface doesn't have to worry
# about it.
if self.member.isMaplikeOrSetlikeOrIterableMethod():
return ''
return CGNativeMember.declare(self, cgClass);
def define(self, cgClass):
return ''
@ -13936,6 +13959,16 @@ class CGExampleGetter(CGNativeMember):
descriptor.getExtendedAttributes(attr,
getter=True))
def declare(self, cgClass):
assert self.member.isAttr()
# We skip declaring ourselves if this is a maplike/setlike attr (in
# practice, "size"), because those get implemented automatically by the
# binding machinery, so the implementor of the interface doesn't have to
# worry about it.
if self.member.isMaplikeOrSetlikeAttr():
return ''
return CGNativeMember.declare(self, cgClass);
def define(self, cgClass):
return ''
@ -14245,14 +14278,15 @@ class CGExampleRoot(CGThing):
continue
if member.isStatic():
builder.addInMozillaDom("GlobalObject")
if member.isAttr():
if member.isAttr() and not member.isMaplikeOrSetlikeAttr():
builder.forwardDeclareForType(member.type, config)
else:
assert member.isMethod()
for sig in member.signatures():
builder.forwardDeclareForType(sig[0], config)
for arg in sig[1]:
builder.forwardDeclareForType(arg.type, config)
if not member.isMaplikeOrSetlikeOrIterableMethod():
for sig in member.signatures():
builder.forwardDeclareForType(sig[0], config)
for arg in sig[1]:
builder.forwardDeclareForType(arg.type, config)
self.root = CGList([builder.build(),
self.root], "\n")

View File

@ -711,6 +711,13 @@ def getTypesFromDescriptor(descriptor):
types.extend(a.type for a in arguments)
types.extend(a.type for a in members if a.isAttr())
if descriptor.interface.maplikeOrSetlikeOrIterable:
maplikeOrSetlikeOrIterable = descriptor.interface.maplikeOrSetlikeOrIterable
if maplikeOrSetlikeOrIterable.hasKeyType():
types.append(maplikeOrSetlikeOrIterable.keyType)
if maplikeOrSetlikeOrIterable.hasValueType():
types.append(maplikeOrSetlikeOrIterable.valueType)
return types

View File

@ -318,7 +318,8 @@ IsInterfacePrototype(DOMObjectType type)
return type == eInterfacePrototype || type == eGlobalInterfacePrototype;
}
typedef JSObject* (*ParentGetter)(JSContext* aCx, JS::Handle<JSObject*> aObj);
typedef JSObject* (*AssociatedGlobalGetter)(JSContext* aCx,
JS::Handle<JSObject*> aObj);
typedef JSObject* (*ProtoGetter)(JSContext* aCx);
@ -351,7 +352,10 @@ struct DOMJSClass
const NativePropertyHooks* mNativeHooks;
ParentGetter mGetParent;
// A callback to find the associated global for our C++ object. Note that
// this is used in cases when that global is _changing_, so it will not match
// the global of the JSObject* passed in to this function!
AssociatedGlobalGetter mGetAssociatedGlobal;
ProtoHandleGetter mGetProto;
// This stores the CC participant for the native, null if this class does not

View File

@ -109,6 +109,7 @@ if CONFIG['MOZ_DEBUG']:
EXPORTS.mozilla.dom += [
"test/TestFunctions.h",
"test/TestInterfaceIterableDouble.h",
"test/TestInterfaceIterableDoubleUnion.h",
"test/TestInterfaceIterableSingle.h",
"test/TestInterfaceMaplike.h",
"test/TestInterfaceMaplikeObject.h",
@ -118,6 +119,7 @@ if CONFIG['MOZ_DEBUG']:
UNIFIED_SOURCES += [
"test/TestFunctions.cpp",
"test/TestInterfaceIterableDouble.cpp",
"test/TestInterfaceIterableDoubleUnion.cpp",
"test/TestInterfaceIterableSingle.cpp",
"test/TestInterfaceMaplike.cpp",
"test/TestInterfaceMaplikeObject.cpp",

View File

@ -307,7 +307,11 @@ class WebIDLCodegenManager(LoggingMixin):
root = CGExampleRoot(self.config, interface)
return self._maybe_write_codegen(root, *self._example_paths(interface))
example_paths = self._example_paths(interface)
for path in example_paths:
print "Generating %s" % path
return self._maybe_write_codegen(root, *example_paths)
def _parse_webidl(self):
import WebIDL

View File

@ -0,0 +1,83 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* 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/. */
#include "mozilla/dom/TestInterfaceIterableDoubleUnion.h"
#include "mozilla/dom/TestInterfaceJSMaplikeSetlikeIterableBinding.h"
#include "nsPIDOMWindow.h"
#include "mozilla/dom/BindingUtils.h"
namespace mozilla {
namespace dom {
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(TestInterfaceIterableDoubleUnion, mParent)
NS_IMPL_CYCLE_COLLECTING_ADDREF(TestInterfaceIterableDoubleUnion)
NS_IMPL_CYCLE_COLLECTING_RELEASE(TestInterfaceIterableDoubleUnion)
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(TestInterfaceIterableDoubleUnion)
NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
NS_INTERFACE_MAP_ENTRY(nsISupports)
NS_INTERFACE_MAP_END
TestInterfaceIterableDoubleUnion::TestInterfaceIterableDoubleUnion(nsPIDOMWindowInner* aParent)
: mParent(aParent)
{
OwningStringOrLong a;
a.SetAsLong() = 1;
mValues.AppendElement(std::pair<nsString, OwningStringOrLong>(NS_LITERAL_STRING("long"),
a));
a.SetAsString() = NS_LITERAL_STRING("a");
mValues.AppendElement(std::pair<nsString, OwningStringOrLong>(NS_LITERAL_STRING("string"),
a));
}
//static
already_AddRefed<TestInterfaceIterableDoubleUnion>
TestInterfaceIterableDoubleUnion::Constructor(const GlobalObject& aGlobal,
ErrorResult& aRv)
{
nsCOMPtr<nsPIDOMWindowInner> window = do_QueryInterface(aGlobal.GetAsSupports());
if (!window) {
aRv.Throw(NS_ERROR_FAILURE);
return nullptr;
}
RefPtr<TestInterfaceIterableDoubleUnion> r = new TestInterfaceIterableDoubleUnion(window);
return r.forget();
}
JSObject*
TestInterfaceIterableDoubleUnion::WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto)
{
return TestInterfaceIterableDoubleUnionBinding::Wrap(aCx, this, aGivenProto);
}
nsPIDOMWindowInner*
TestInterfaceIterableDoubleUnion::GetParentObject() const
{
return mParent;
}
size_t
TestInterfaceIterableDoubleUnion::GetIterableLength()
{
return mValues.Length();
}
nsAString&
TestInterfaceIterableDoubleUnion::GetKeyAtIndex(uint32_t aIndex)
{
MOZ_ASSERT(aIndex < mValues.Length());
return mValues.ElementAt(aIndex).first;
}
OwningStringOrLong&
TestInterfaceIterableDoubleUnion::GetValueAtIndex(uint32_t aIndex)
{
MOZ_ASSERT(aIndex < mValues.Length());
return mValues.ElementAt(aIndex).second;
}
} // namespace dom
} // namespace mozilla

View File

@ -0,0 +1,51 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim:set ts=2 sw=2 sts=2 et cindent: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* 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_dom_TestInterfaceIterableDoubleUnion_h
#define mozilla_dom_TestInterfaceIterableDoubleUnion_h
#include "nsWrapperCache.h"
#include "nsCOMPtr.h"
class nsPIDOMWindowInner;
namespace mozilla {
class ErrorResult;
namespace dom {
class GlobalObject;
// Implementation of test binding for webidl iterable interfaces, using
// primitives for value type
class TestInterfaceIterableDoubleUnion final : public nsISupports,
public nsWrapperCache
{
public:
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(TestInterfaceIterableDoubleUnion)
explicit TestInterfaceIterableDoubleUnion(nsPIDOMWindowInner* aParent);
nsPIDOMWindowInner* GetParentObject() const;
virtual JSObject* WrapObject(JSContext* aCx,
JS::Handle<JSObject*> aGivenProto) override;
static already_AddRefed<TestInterfaceIterableDoubleUnion>
Constructor(const GlobalObject& aGlobal, ErrorResult& rv);
size_t GetIterableLength();
nsAString& GetKeyAtIndex(uint32_t aIndex);
OwningStringOrLong& GetValueAtIndex(uint32_t aIndex);
private:
virtual ~TestInterfaceIterableDoubleUnion() {}
nsCOMPtr<nsPIDOMWindowInner> mParent;
nsTArray<std::pair<nsString, OwningStringOrLong>> mValues;
};
} // namespace dom
} // namespace mozilla
#endif // mozilla_dom_TestInterfaceIterableDoubleUnion_h

View File

@ -174,6 +174,66 @@
"[object TestInterfaceIterableDoubleIteratorPrototype]",
"iterator prototype should have the right brand");
// Simple dual type iterable creation and functionality test
info("IterableDoubleUnion: Testing simple iterable creation and functionality");
itr = new TestInterfaceIterableDoubleUnion();
testExistence("IterableDoubleUnion: ", itr, base_properties);
is(itr.entries, itr[Symbol.iterator],
"IterableDoubleUnion: Should be using @@iterator for 'entries'");
var elements = [["long", 1], ["string", "a"]]
var keys = [...itr.keys()];
var values = [...itr.values()];
var entries = [...itr.entries()];
var key_itr = itr.keys();
var value_itr = itr.values();
var entries_itr = itr.entries();
for (var i = 0; i < elements.length; ++i) {
var key = key_itr.next();
var value = value_itr.next();
var entry = entries_itr.next();
is(key.value, elements[i][0], "IterableDoubleUnion: Key iterator value should be " + elements[i][0]);
is(key.value, keys[i],
"IterableDoubleUnion: Key iterator value should match destructuring " + i);
is(value.value, elements[i][1], "IterableDoubleUnion: Value iterator value should be " + elements[i][1]);
is(value.value, values[i],
"IterableDoubleUnion: Value iterator value should match destructuring " + i);
is(entry.value[0], elements[i][0], "IterableDoubleUnion: Entry iterator value 0 should be " + elements[i][0]);
is(entry.value[1], elements[i][1], "IterableDoubleUnion: Entry iterator value 1 should be " + elements[i][1]);
is(entry.value[0], entries[i][0],
"IterableDoubleUnion: Entry iterator value 0 should match destructuring " + i);
is(entry.value[1], entries[i][1],
"IterableDoubleUnion: Entry iterator value 1 should match destructuring " + i);
}
callsToForEachCallback = 0;
thisArg = {};
itr.forEach(function(value, key, obj) {
is(key, keys[callsToForEachCallback],
`IterableDoubleUnion: Should have the right key at ${callsToForEachCallback} calls to forEach callback`);
is(value, values[callsToForEachCallback],
`IterableDoubleUnion: Should have the right value at ${callsToForEachCallback} calls to forEach callback`);
is(this, thisArg,
"IterableDoubleUnion: Should have the right this value for forEach callback");
is(obj, itr,
"IterableSingle: Should have the right third arg for forEach callback");
++callsToForEachCallback;
}, thisArg);
is(callsToForEachCallback, 2,
"IterableDoubleUnion: Should have right total number of calls to forEach callback");
var key = key_itr.next();
var value = value_itr.next();
var entry = entries_itr.next()
is(key.value, undefined, "IterableDoubleUnion: Key iterator value should be undefined");
is(key.done, true, "IterableDoubleUnion: Key iterator done should be true");
is(value.value, undefined, "IterableDoubleUnion: Value iterator value should be undefined");
is(value.done, true, "IterableDoubleUnion: Value iterator done should be true");
is(entry.value, undefined, "IterableDoubleUnion: Entry iterator value should be undefined");
is(entry.done, true, "IterableDoubleUnion: Entry iterator done should be true");
is(Object.prototype.toString.call(Object.getPrototypeOf(key_itr)),
"[object TestInterfaceIterableDoubleUnionIteratorPrototype]",
"iterator prototype should have the right brand");
SimpleTest.finish();
});
</script>

View File

@ -905,7 +905,7 @@ public:
if (!context || !context->mTarget)
return;
context->ReturnTarget();
context->OnStableState();
}
static void DidTransactionCallback(void* aData)
@ -1504,6 +1504,10 @@ CanvasRenderingContext2D::ScheduleStableStateCallback()
void
CanvasRenderingContext2D::OnStableState()
{
if (!mHasPendingStableStateCallback) {
return;
}
ReturnTarget();
mHasPendingStableStateCallback = false;
@ -1529,6 +1533,8 @@ CanvasRenderingContext2D::EnsureTarget(const gfx::Rect* aCoveredRect,
return mRenderingMode;
}
ScheduleStableStateCallback();
if (mBufferProvider && mode == mRenderingMode) {
gfx::Rect rect(0, 0, mWidth, mHeight);
if (aCoveredRect && CurrentState().transform.TransformBounds(*aCoveredRect).Contains(rect)) {
@ -1537,8 +1543,6 @@ CanvasRenderingContext2D::EnsureTarget(const gfx::Rect* aCoveredRect,
mTarget = mBufferProvider->BorrowDrawTarget(IntRect(0, 0, mWidth, mHeight));
}
ScheduleStableStateCallback();
if (mTarget) {
// Restore clip and transform.
for (uint32_t i = 0; i < mStyleStack.Length(); i++) {
@ -1731,7 +1735,7 @@ CanvasRenderingContext2D::ClearTarget()
void
CanvasRenderingContext2D::ReturnTarget()
{
if (mTarget && mBufferProvider) {
if (mTarget && mBufferProvider && mTarget != sErrorTarget) {
CurrentState().transform = mTarget->GetTransform();
for (uint32_t i = 0; i < mStyleStack.Length(); i++) {
for (uint32_t c = 0; c < mStyleStack[i].clipsPushed.Length(); c++) {
@ -5693,7 +5697,7 @@ CanvasRenderingContext2D::GetBufferProvider(LayerManager* aManager)
return mBufferProvider;
}
if (aManager) {
if (aManager && !mIsSkiaGL) {
mBufferProvider = aManager->CreatePersistentBufferProvider(gfx::IntSize(mWidth, mHeight),
GetSurfaceFormat());
}

View File

@ -5899,7 +5899,7 @@ skip-if = (os == 'android' || os == 'linux' || (os == 'win' && os_version == '5.
[generated/test_2_conformance__typedarrays__data-view-crash.html]
skip-if = (os == 'android' || os == 'linux' || (os == 'win' && os_version == '5.1') || (os == 'win' && os_version == '6.2'))
[generated/test_2_conformance__typedarrays__data-view-test.html]
skip-if = (os == 'android' || os == 'linux' || (os == 'win' && os_version == '5.1') || (os == 'win' && os_version == '6.2'))
fail-if = 1
[generated/test_2_conformance__typedarrays__typed-arrays-in-workers.html]
skip-if = (os == 'android' || os == 'linux' || (os == 'win' && os_version == '5.1') || (os == 'win' && os_version == '6.2'))
[generated/test_2_conformance__uniforms__gl-uniform-arrays.html]
@ -6771,6 +6771,7 @@ skip-if = (os == 'android')
[generated/test_conformance__typedarrays__array-unit-tests.html]
[generated/test_conformance__typedarrays__data-view-crash.html]
[generated/test_conformance__typedarrays__data-view-test.html]
fail-if = 1
[generated/test_conformance__typedarrays__typed-arrays-in-workers.html]
[generated/test_conformance__uniforms__gl-uniform-arrays.html]
[generated/test_conformance__uniforms__gl-uniform-bool.html]

View File

@ -33,6 +33,13 @@ skip-if = os == 'b2g' || ((os == 'linux') && (buildapp == 'mulet'))
[generated/test_..__always-fail.html]
fail-if = 1
[generated/test_conformance__typedarrays__data-view-test.html]
# Test is out-of-date with spec.
fail-if = 1
[generated/test_2_conformance__typedarrays__data-view-test.html]
# Test is out-of-date with spec.
fail-if = 1
####################
# Tests requesting non-local network connections.

View File

@ -204,8 +204,10 @@ CryptoKey::GetAlgorithm(JSContext* cx, JS::MutableHandle<JSObject*> aRetVal,
break;
case KeyAlgorithmProxy::RSA: {
RootedDictionary<RsaHashedKeyAlgorithm> rsa(cx);
mAlgorithm.mRsa.ToKeyAlgorithm(cx, rsa);
converted = ToJSValue(cx, rsa, &val);
converted = mAlgorithm.mRsa.ToKeyAlgorithm(cx, rsa);
if (converted) {
converted = ToJSValue(cx, rsa, &val);
}
break;
}
case KeyAlgorithmProxy::EC:
@ -213,8 +215,10 @@ CryptoKey::GetAlgorithm(JSContext* cx, JS::MutableHandle<JSObject*> aRetVal,
break;
case KeyAlgorithmProxy::DH: {
RootedDictionary<DhKeyAlgorithm> dh(cx);
mAlgorithm.mDh.ToKeyAlgorithm(cx, dh);
converted = ToJSValue(cx, dh, &val);
converted = mAlgorithm.mDh.ToKeyAlgorithm(cx, dh);
if (converted) {
converted = ToJSValue(cx, dh, &val);
}
break;
}
}

View File

@ -25,14 +25,21 @@ struct RsaHashedKeyAlgorithmStorage {
uint16_t mModulusLength;
CryptoBuffer mPublicExponent;
void
bool
ToKeyAlgorithm(JSContext* aCx, RsaHashedKeyAlgorithm& aRsa) const
{
JS::Rooted<JSObject*> exponent(aCx, mPublicExponent.ToUint8Array(aCx));
if (!exponent) {
return false;
}
aRsa.mName = mName;
aRsa.mModulusLength = mModulusLength;
aRsa.mHash.mName = mHash.mName;
aRsa.mPublicExponent.Init(mPublicExponent.ToUint8Array(aCx));
aRsa.mPublicExponent.Init(exponent);
aRsa.mPublicExponent.ComputeLengthAndData();
return true;
}
};
@ -43,14 +50,26 @@ struct DhKeyAlgorithmStorage {
CryptoBuffer mPrime;
CryptoBuffer mGenerator;
void
bool
ToKeyAlgorithm(JSContext* aCx, DhKeyAlgorithm& aDh) const
{
JS::Rooted<JSObject*> prime(aCx, mPrime.ToUint8Array(aCx));
if (!prime) {
return false;
}
JS::Rooted<JSObject*> generator(aCx, mGenerator.ToUint8Array(aCx));
if (!generator) {
return false;
}
aDh.mName = mName;
aDh.mPrime.Init(mPrime.ToUint8Array(aCx));
aDh.mPrime.Init(prime);
aDh.mPrime.ComputeLengthAndData();
aDh.mGenerator.Init(mGenerator.ToUint8Array(aCx));
aDh.mGenerator.Init(generator);
aDh.mGenerator.ComputeLengthAndData();
return true;
}
};

View File

@ -37,7 +37,7 @@ namespace mozilla {
namespace dom {
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(DataTransferItem, mData,
mPrincipal, mParent)
mPrincipal, mParent, mCachedFile)
NS_IMPL_CYCLE_COLLECTING_ADDREF(DataTransferItem)
NS_IMPL_CYCLE_COLLECTING_RELEASE(DataTransferItem)

View File

@ -115,6 +115,19 @@ IsWebkitPrefixSupportEnabled()
return sIsWebkitPrefixSupportEnabled;
}
static bool
IsPrefixedPointerLockEnabled()
{
static bool sIsPrefixedPointerLockEnabled;
static bool sIsPrefCached = false;
if (!sIsPrefCached) {
sIsPrefCached = true;
Preferences::AddBoolVarCache(&sIsPrefixedPointerLockEnabled,
"pointer-lock-api.prefixed.enabled");
}
return sIsPrefixedPointerLockEnabled;
}
EventListenerManagerBase::EventListenerManagerBase()
: mNoListenerForEvent(eVoidEvent)
, mMayHavePaintEventListener(false)
@ -237,7 +250,7 @@ EventListenerManager::GetTargetAsInnerWindow() const
void
EventListenerManager::AddEventListenerInternal(
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
EventMessage aEventMessage,
nsIAtom* aTypeAtom,
const nsAString& aTypeString,
@ -278,7 +291,6 @@ EventListenerManager::AddEventListenerInternal(
listener = aAllEvents ? mListeners.InsertElementAt(0) :
mListeners.AppendElement();
listener->mListener = aListenerHolder;
listener->mEventMessage = aEventMessage;
listener->mTypeString = aTypeString;
listener->mTypeAtom = aTypeAtom;
@ -301,6 +313,7 @@ EventListenerManager::AddEventListenerInternal(
} else {
listener->mListenerType = Listener::eNativeListener;
}
listener->mListener = Move(aListenerHolder);
if (aFlags.mInSystemGroup) {
@ -348,17 +361,11 @@ EventListenerManager::AddEventListenerInternal(
#endif
#ifdef MOZ_B2G
} else if (aTypeAtom == nsGkAtoms::onmoztimechange) {
if (nsCOMPtr<nsPIDOMWindowInner> window = GetTargetAsInnerWindow()) {
window->EnableTimeChangeNotifications();
}
EnableDevice(eTimeChange);
} else if (aTypeAtom == nsGkAtoms::onmoznetworkupload) {
if (nsCOMPtr<nsPIDOMWindowInner> window = GetTargetAsInnerWindow()) {
window->EnableNetworkEvent(eNetworkUpload);
}
EnableDevice(eNetworkUpload);
} else if (aTypeAtom == nsGkAtoms::onmoznetworkdownload) {
if (nsCOMPtr<nsPIDOMWindowInner> window = GetTargetAsInnerWindow()) {
window->EnableNetworkEvent(eNetworkDownload);
}
EnableDevice(eNetworkDownload);
#endif // MOZ_B2G
} else if (aTypeAtom == nsGkAtoms::ontouchstart ||
aTypeAtom == nsGkAtoms::ontouchend ||
@ -485,6 +492,11 @@ EventListenerManager::IsDeviceType(EventMessage aEventMessage)
case eUserProximity:
#if defined(MOZ_WIDGET_ANDROID) || defined(MOZ_WIDGET_GONK)
case eOrientationChange:
#endif
#ifdef MOZ_B2G
case eTimeChange:
case eNetworkUpload:
case eNetworkDownload:
#endif
return true;
default:
@ -535,6 +547,15 @@ EventListenerManager::EnableDevice(EventMessage aEventMessage)
case eOrientationChange:
window->EnableOrientationChangeListener();
break;
#endif
#ifdef MOZ_B2G
case eTimeChange:
window->EnableTimeChangeNotifications();
break;
case eNetworkUpload:
case eNetworkDownload:
window->EnableNetworkEvent(aEventMessage);
break;
#endif
default:
NS_WARNING("Enabling an unknown device sensor.");
@ -582,15 +603,40 @@ EventListenerManager::DisableDevice(EventMessage aEventMessage)
window->DisableOrientationChangeListener();
break;
#endif
#ifdef MOZ_B2G
case eTimeChange:
window->DisableTimeChangeNotifications();
break;
case eNetworkUpload:
case eNetworkDownload:
window->DisableNetworkEvent(aEventMessage);
break;
#endif // MOZ_B2G
default:
NS_WARNING("Disabling an unknown device sensor.");
break;
}
}
void
EventListenerManager::NotifyEventListenerRemoved(nsIAtom* aUserType)
{
// If the following code is changed, other callsites of EventListenerRemoved
// and NotifyAboutMainThreadListenerChange should be changed too.
mNoListenerForEvent = eVoidEvent;
mNoListenerForEventAtom = nullptr;
if (mTarget && aUserType) {
mTarget->EventListenerRemoved(aUserType);
}
if (mIsMainThreadELM && mTarget) {
EventListenerService::NotifyAboutMainThreadListenerChange(mTarget,
aUserType);
}
}
void
EventListenerManager::RemoveEventListenerInternal(
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
EventMessage aEventMessage,
nsIAtom* aUserType,
const nsAString& aTypeString,
@ -606,11 +652,6 @@ EventListenerManager::RemoveEventListenerInternal(
uint32_t count = mListeners.Length();
uint32_t typeCount = 0;
bool deviceType = IsDeviceType(aEventMessage);
#ifdef MOZ_B2G
bool timeChangeEvent = (aEventMessage == eTimeChange);
bool networkEvent = (aEventMessage == eNetworkUpload ||
aEventMessage == eNetworkDownload);
#endif // MOZ_B2G
for (uint32_t i = 0; i < count; ++i) {
listener = &mListeners.ElementAt(i);
@ -622,21 +663,8 @@ EventListenerManager::RemoveEventListenerInternal(
RefPtr<EventListenerManager> kungFuDeathGrip(this);
mListeners.RemoveElementAt(i);
--count;
mNoListenerForEvent = eVoidEvent;
mNoListenerForEventAtom = nullptr;
if (mTarget && aUserType) {
mTarget->EventListenerRemoved(aUserType);
}
if (mIsMainThreadELM && mTarget) {
EventListenerService::NotifyAboutMainThreadListenerChange(mTarget,
aUserType);
}
if (!deviceType
#ifdef MOZ_B2G
&& !timeChangeEvent && !networkEvent
#endif // MOZ_B2G
) {
NotifyEventListenerRemoved(aUserType);
if (!deviceType) {
return;
}
--typeCount;
@ -646,16 +674,6 @@ EventListenerManager::RemoveEventListenerInternal(
if (!aAllEvents && deviceType && typeCount == 0) {
DisableDevice(aEventMessage);
#ifdef MOZ_B2G
} else if (timeChangeEvent && typeCount == 0) {
if (nsCOMPtr<nsPIDOMWindowInner> window = GetTargetAsInnerWindow()) {
window->DisableTimeChangeNotifications();
}
} else if (!aAllEvents && networkEvent && typeCount == 0) {
if (nsCOMPtr<nsPIDOMWindowInner> window = GetTargetAsInnerWindow()) {
window->DisableNetworkEvent(aEventMessage);
}
#endif // MOZ_B2G
}
}
@ -669,6 +687,10 @@ EventListenerManager::ListenerCanHandle(const Listener* aListener,
aEventMessage == GetLegacyEventMessage(aEvent->mMessage),
"aEvent and aEventMessage should agree, modulo legacyness");
// The listener has been removed, it cannot handle anything.
if (aListener->mListenerType == Listener::eNoListener) {
return false;
}
// This is slightly different from EVENT_TYPE_EQUALS in that it returns
// true even when aEvent->mMessage == eUnidentifiedEvent and
// aListener=>mEventMessage != eUnidentifiedEvent as long as the atoms are
@ -697,7 +719,7 @@ EventListenerManager::ListenerCanHandle(const Listener* aListener,
void
EventListenerManager::AddEventListenerByType(
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
const nsAString& aType,
const EventListenerFlags& aFlags)
{
@ -706,12 +728,13 @@ EventListenerManager::AddEventListenerByType(
nsContentUtils::GetEventMessageAndAtomForListener(aType,
getter_AddRefs(atom)) :
eUnidentifiedEvent;
AddEventListenerInternal(aListenerHolder, message, atom, aType, aFlags);
AddEventListenerInternal(Move(aListenerHolder),
message, atom, aType, aFlags);
}
void
EventListenerManager::RemoveEventListenerByType(
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
const nsAString& aType,
const EventListenerFlags& aFlags)
{
@ -720,7 +743,8 @@ EventListenerManager::RemoveEventListenerByType(
nsContentUtils::GetEventMessageAndAtomForListener(aType,
getter_AddRefs(atom)) :
eUnidentifiedEvent;
RemoveEventListenerInternal(aListenerHolder, message, atom, aType, aFlags);
RemoveEventListenerInternal(Move(aListenerHolder),
message, atom, aType, aFlags);
}
EventListenerManager::Listener*
@ -764,9 +788,8 @@ EventListenerManager::SetEventHandlerInternal(
nsCOMPtr<JSEventHandler> jsEventHandler;
NS_NewJSEventHandler(mTarget, aName,
aTypedHandler, getter_AddRefs(jsEventHandler));
EventListenerHolder listenerHolder(jsEventHandler);
AddEventListenerInternal(listenerHolder, eventMessage, aName, aTypeString,
flags, true);
AddEventListenerInternal(EventListenerHolder(jsEventHandler),
eventMessage, aName, aTypeString, flags, true);
listener = FindEventHandler(eventMessage, aName, aTypeString);
} else {
@ -900,14 +923,7 @@ EventListenerManager::RemoveEventHandler(nsIAtom* aName,
if (listener) {
mListeners.RemoveElementAt(uint32_t(listener - &mListeners.ElementAt(0)));
mNoListenerForEvent = eVoidEvent;
mNoListenerForEventAtom = nullptr;
if (mTarget && aName) {
mTarget->EventListenerRemoved(aName);
}
if (mIsMainThreadELM && mTarget) {
EventListenerService::NotifyAboutMainThreadListenerChange(mTarget, aName);
}
NotifyEventListenerRemoved(aName);
}
}
@ -1092,7 +1108,8 @@ EventListenerManager::HandleEventSubType(Listener* aListener,
EventTarget* aCurrentTarget)
{
nsresult result = NS_OK;
EventListenerHolder listenerHolder(aListener->mListener); // strong ref
// strong ref
EventListenerHolder listenerHolder(aListener->mListener.Clone());
// If this is a script handler and we haven't yet
// compiled the event handler itself
@ -1128,19 +1145,29 @@ EventListenerManager::GetLegacyEventMessage(EventMessage aEventMessage) const
{
// (If we're off-main-thread, we can't check the pref; so we just behave as
// if it's disabled.)
if (mIsMainThreadELM && IsWebkitPrefixSupportEnabled()) {
// webkit-prefixed legacy events:
if (aEventMessage == eTransitionEnd) {
return eWebkitTransitionEnd;
if (mIsMainThreadELM) {
if (IsWebkitPrefixSupportEnabled()) {
// webkit-prefixed legacy events:
if (aEventMessage == eTransitionEnd) {
return eWebkitTransitionEnd;
}
if (aEventMessage == eAnimationStart) {
return eWebkitAnimationStart;
}
if (aEventMessage == eAnimationEnd) {
return eWebkitAnimationEnd;
}
if (aEventMessage == eAnimationIteration) {
return eWebkitAnimationIteration;
}
}
if (aEventMessage == eAnimationStart) {
return eWebkitAnimationStart;
}
if (aEventMessage == eAnimationEnd) {
return eWebkitAnimationEnd;
}
if (aEventMessage == eAnimationIteration) {
return eWebkitAnimationIteration;
if (IsPrefixedPointerLockEnabled()) {
if (aEventMessage == ePointerLockChange) {
return eMozPointerLockChange;
}
if (aEventMessage == ePointerLockError) {
return eMozPointerLockError;
}
}
}
@ -1182,6 +1209,7 @@ EventListenerManager::HandleEventInternal(nsPresContext* aPresContext,
bool hasListener = false;
bool hasListenerForCurrentGroup = false;
bool usingLegacyMessage = false;
bool hasRemovedListener = false;
EventMessage eventMessage = aEvent->mMessage;
while (true) {
@ -1246,6 +1274,15 @@ EventListenerManager::HandleEventInternal(nsPresContext* aPresContext,
}
aEvent->mFlags.mInPassiveListener = listener->mFlags.mPassive;
Maybe<Listener> listenerHolder;
if (listener->mFlags.mOnce) {
// Move the listener to the stack before handling the event.
// The order is important, otherwise the listener could be
// called again inside the listener.
listenerHolder.emplace(Move(*listener));
listener = listenerHolder.ptr();
hasRemovedListener = true;
}
if (NS_FAILED(HandleEventSubType(listener, *aDOMEvent, aCurrentTarget))) {
aEvent->mFlags.mExceptionWasRaised = true;
}
@ -1282,6 +1319,36 @@ EventListenerManager::HandleEventInternal(nsPresContext* aPresContext,
aEvent->mCurrentTarget = nullptr;
if (hasRemovedListener) {
// If there are any once listeners replaced with a placeholder in
// the loop above, we need to clean up them here. Note that, this
// could clear once listeners handled in some outer level as well,
// but that should not affect the result.
mListeners.RemoveElementsBy([](const Listener& aListener) {
return aListener.mListenerType == Listener::eNoListener;
});
NotifyEventListenerRemoved(aEvent->mSpecifiedEventType);
if (IsDeviceType(aEvent->mMessage)) {
// This is a device-type event, we need to check whether we can
// disable device after removing the once listeners.
bool hasAnyListener = false;
nsAutoTObserverArray<Listener, 2>::ForwardIterator iter(mListeners);
while (iter.HasMore()) {
Listener* listener = &iter.GetNext();
if (EVENT_TYPE_EQUALS(listener, aEvent->mMessage,
aEvent->mSpecifiedEventType,
aEvent->mSpecifiedEventTypeString,
/* all events */ false)) {
hasAnyListener = true;
break;
}
}
if (!hasAnyListener) {
DisableDevice(aEvent->mMessage);
}
}
}
if (mIsMainThreadELM && !hasListener) {
mNoListenerForEvent = aEvent->mMessage;
mNoListenerForEventAtom = aEvent->mSpecifiedEventType;
@ -1302,20 +1369,20 @@ EventListenerManager::Disconnect()
void
EventListenerManager::AddEventListener(
const nsAString& aType,
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
bool aUseCapture,
bool aWantsUntrusted)
{
EventListenerFlags flags;
flags.mCapture = aUseCapture;
flags.mAllowUntrustedEvents = aWantsUntrusted;
return AddEventListenerByType(aListenerHolder, aType, flags);
return AddEventListenerByType(Move(aListenerHolder), aType, flags);
}
void
EventListenerManager::AddEventListener(
const nsAString& aType,
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
const dom::AddEventListenerOptionsOrBoolean& aOptions,
bool aWantsUntrusted)
{
@ -1327,26 +1394,27 @@ EventListenerManager::AddEventListener(
flags.mCapture = options.mCapture;
flags.mInSystemGroup = options.mMozSystemGroup;
flags.mPassive = options.mPassive;
flags.mOnce = options.mOnce;
}
flags.mAllowUntrustedEvents = aWantsUntrusted;
return AddEventListenerByType(aListenerHolder, aType, flags);
return AddEventListenerByType(Move(aListenerHolder), aType, flags);
}
void
EventListenerManager::RemoveEventListener(
const nsAString& aType,
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
bool aUseCapture)
{
EventListenerFlags flags;
flags.mCapture = aUseCapture;
RemoveEventListenerByType(aListenerHolder, aType, flags);
RemoveEventListenerByType(Move(aListenerHolder), aType, flags);
}
void
EventListenerManager::RemoveEventListener(
const nsAString& aType,
const EventListenerHolder& aListenerHolder,
EventListenerHolder aListenerHolder,
const dom::EventListenerOptionsOrBoolean& aOptions)
{
EventListenerFlags flags;
@ -1357,7 +1425,7 @@ EventListenerManager::RemoveEventListener(
flags.mCapture = options.mCapture;
flags.mInSystemGroup = options.mMozSystemGroup;
}
RemoveEventListenerByType(aListenerHolder, aType, flags);
RemoveEventListenerByType(Move(aListenerHolder), aType, flags);
}
void
@ -1370,9 +1438,8 @@ EventListenerManager::AddListenerForAllEvents(nsIDOMEventListener* aDOMListener,
flags.mCapture = aUseCapture;
flags.mAllowUntrustedEvents = aWantsUntrusted;
flags.mInSystemGroup = aSystemEventGroup;
EventListenerHolder listenerHolder(aDOMListener);
AddEventListenerInternal(listenerHolder, eAllEvents, nullptr, EmptyString(),
flags, false, true);
AddEventListenerInternal(EventListenerHolder(aDOMListener), eAllEvents,
nullptr, EmptyString(), flags, false, true);
}
void
@ -1384,9 +1451,8 @@ EventListenerManager::RemoveListenerForAllEvents(
EventListenerFlags flags;
flags.mCapture = aUseCapture;
flags.mInSystemGroup = aSystemEventGroup;
EventListenerHolder listenerHolder(aDOMListener);
RemoveEventListenerInternal(listenerHolder, eAllEvents, nullptr,
EmptyString(), flags, true);
RemoveEventListenerInternal(EventListenerHolder(aDOMListener), eAllEvents,
nullptr, EmptyString(), flags, true);
}
bool

View File

@ -61,11 +61,14 @@ public:
// If mPassive is true, the listener will not be calling preventDefault on the
// event. (If it does call preventDefault, we should ignore it).
bool mPassive : 1;
// If mOnce is true, the listener will be removed from the manager before it
// is invoked, so that it would only be invoked once.
bool mOnce : 1;
EventListenerFlags() :
mListenerIsJSListener(false),
mCapture(false), mInSystemGroup(false), mAllowUntrustedEvents(false),
mPassive(false)
mPassive(false), mOnce(false)
{
}
@ -75,7 +78,7 @@ public:
mInSystemGroup == aOther.mInSystemGroup &&
mListenerIsJSListener == aOther.mListenerIsJSListener &&
mAllowUntrustedEvents == aOther.mAllowUntrustedEvents);
// Don't compare mPassive
// Don't compare mPassive or mOnce
}
bool EqualsForRemoval(const EventListenerFlags& aOther) const
@ -83,7 +86,7 @@ public:
return (mCapture == aOther.mCapture &&
mInSystemGroup == aOther.mInSystemGroup &&
mListenerIsJSListener == aOther.mListenerIsJSListener);
// Don't compare mAllowUntrustedEvents or mPassive
// Don't compare mAllowUntrustedEvents, mPassive, or mOnce
}
};
@ -185,13 +188,13 @@ public:
enum ListenerType : uint8_t
{
eNativeListener = 0,
eNoListener,
eNativeListener,
eJSEventListener,
eWrappedJSListener,
eWebIDLListener,
eListenerTypeCount
};
uint8_t mListenerType;
ListenerType mListenerType;
bool mListenerIsHandler : 1;
bool mHandlerIsString : 1;
@ -208,9 +211,33 @@ public:
}
Listener()
: mEventMessage(eVoidEvent)
, mListenerType(eNoListener)
, mListenerIsHandler(false)
, mHandlerIsString(false)
, mAllEvents(false)
, mIsChrome(false)
{
MOZ_ASSERT(sizeof(mListenerType) == 1);
MOZ_ASSERT(eListenerTypeCount < 255);
}
Listener(Listener&& aOther)
: mListener(Move(aOther.mListener))
, mTypeAtom(aOther.mTypeAtom.forget())
, mTypeString(aOther.mTypeString)
, mEventMessage(aOther.mEventMessage)
, mListenerType(aOther.mListenerType)
, mListenerIsHandler(aOther.mListenerIsHandler)
, mHandlerIsString(aOther.mHandlerIsString)
, mAllEvents(aOther.mAllEvents)
, mIsChrome(aOther.mIsChrome)
{
aOther.mTypeString.Truncate();
aOther.mEventMessage = eVoidEvent;
aOther.mListenerType = eNoListener;
aOther.mListenerIsHandler = false;
aOther.mHandlerIsString = false;
aOther.mAllEvents = false;
aOther.mIsChrome = false;
}
~Listener()
@ -245,30 +272,28 @@ public:
bool aUseCapture,
bool aWantsUntrusted)
{
EventListenerHolder holder(aListener);
AddEventListener(aType, holder, aUseCapture, aWantsUntrusted);
AddEventListener(aType, EventListenerHolder(aListener),
aUseCapture, aWantsUntrusted);
}
void AddEventListener(const nsAString& aType,
dom::EventListener* aListener,
const dom::AddEventListenerOptionsOrBoolean& aOptions,
bool aWantsUntrusted)
{
EventListenerHolder holder(aListener);
AddEventListener(aType, holder, aOptions, aWantsUntrusted);
AddEventListener(aType, EventListenerHolder(aListener),
aOptions, aWantsUntrusted);
}
void RemoveEventListener(const nsAString& aType,
nsIDOMEventListener* aListener,
bool aUseCapture)
{
EventListenerHolder holder(aListener);
RemoveEventListener(aType, holder, aUseCapture);
RemoveEventListener(aType, EventListenerHolder(aListener), aUseCapture);
}
void RemoveEventListener(const nsAString& aType,
dom::EventListener* aListener,
const dom::EventListenerOptionsOrBoolean& aOptions)
{
EventListenerHolder holder(aListener);
RemoveEventListener(aType, holder, aOptions);
RemoveEventListener(aType, EventListenerHolder(aListener), aOptions);
}
void AddListenerForAllEvents(nsIDOMEventListener* aListener,
@ -287,20 +312,18 @@ public:
const nsAString& type,
const EventListenerFlags& aFlags)
{
EventListenerHolder holder(aListener);
AddEventListenerByType(holder, type, aFlags);
AddEventListenerByType(EventListenerHolder(aListener), type, aFlags);
}
void AddEventListenerByType(const EventListenerHolder& aListener,
void AddEventListenerByType(EventListenerHolder aListener,
const nsAString& type,
const EventListenerFlags& aFlags);
void RemoveEventListenerByType(nsIDOMEventListener *aListener,
const nsAString& type,
const EventListenerFlags& aFlags)
{
EventListenerHolder holder(aListener);
RemoveEventListenerByType(holder, type, aFlags);
RemoveEventListenerByType(EventListenerHolder(aListener), type, aFlags);
}
void RemoveEventListenerByType(const EventListenerHolder& aListener,
void RemoveEventListenerByType(EventListenerHolder aListener,
const nsAString& type,
const EventListenerFlags& aFlags);
@ -554,34 +577,35 @@ protected:
const nsAString& aTypeString);
void AddEventListener(const nsAString& aType,
const EventListenerHolder& aListener,
EventListenerHolder aListener,
const dom::AddEventListenerOptionsOrBoolean& aOptions,
bool aWantsUntrusted);
void AddEventListener(const nsAString& aType,
const EventListenerHolder& aListener,
EventListenerHolder aListener,
bool aUseCapture,
bool aWantsUntrusted);
void RemoveEventListener(const nsAString& aType,
const EventListenerHolder& aListener,
EventListenerHolder aListener,
const dom::EventListenerOptionsOrBoolean& aOptions);
void RemoveEventListener(const nsAString& aType,
const EventListenerHolder& aListener,
EventListenerHolder aListener,
bool aUseCapture);
void AddEventListenerInternal(const EventListenerHolder& aListener,
void AddEventListenerInternal(EventListenerHolder aListener,
EventMessage aEventMessage,
nsIAtom* aTypeAtom,
const nsAString& aTypeString,
const EventListenerFlags& aFlags,
bool aHandler = false,
bool aAllEvents = false);
void RemoveEventListenerInternal(const EventListenerHolder& aListener,
void RemoveEventListenerInternal(EventListenerHolder aListener,
EventMessage aEventMessage,
nsIAtom* aUserType,
const nsAString& aTypeString,
const EventListenerFlags& aFlags,
bool aAllEvents = false);
void RemoveAllListeners();
void NotifyEventListenerRemoved(nsIAtom* aUserType);
const EventTypeData* GetTypeDataForIID(const nsIID& aIID);
const EventTypeData* GetTypeDataForEventName(nsIAtom* aName);
nsPIDOMWindowInner* GetInnerWindowForTarget();

View File

@ -323,10 +323,18 @@ EVENT(mozfullscreenerror,
EventNameType_HTML,
eBasicEventClass)
EVENT(mozpointerlockchange,
ePointerLockChange,
eMozPointerLockChange,
EventNameType_HTML,
eBasicEventClass)
EVENT(mozpointerlockerror,
eMozPointerLockError,
EventNameType_HTML,
eBasicEventClass)
EVENT(pointerlockchange,
ePointerLockChange,
EventNameType_HTML,
eBasicEventClass)
EVENT(pointerlockerror,
ePointerLockError,
EventNameType_HTML,
eBasicEventClass)

View File

@ -109,8 +109,6 @@ function testInitializingUntrustedEvent()
is(e.buttons, 0, description + "buttons returns wrong value");
is(e.movementX, 0, description + "movementX returns wrong value");
is(e.movementY, 0, description + "movementY returns wrong value");
is(e.movementX, e.mozMovementX);
is(e.movementY, e.mozMovementY);
// getModifierState() tests
is(e.getModifierState("Shift"), kTest.shiftKey,

View File

@ -83,8 +83,8 @@ class nsGeolocationRequest final
NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsGeolocationRequest, nsIContentPermissionRequest)
nsGeolocationRequest(Geolocation* aLocator,
const GeoPositionCallback& aCallback,
const GeoPositionErrorCallback& aErrorCallback,
GeoPositionCallback aCallback,
GeoPositionErrorCallback aErrorCallback,
PositionOptions* aOptions,
uint8_t aProtocolType,
bool aWatchPositionRequest = false,
@ -347,15 +347,15 @@ PositionError::NotifyCallback(const GeoPositionErrorCallback& aCallback)
////////////////////////////////////////////////////
nsGeolocationRequest::nsGeolocationRequest(Geolocation* aLocator,
const GeoPositionCallback& aCallback,
const GeoPositionErrorCallback& aErrorCallback,
GeoPositionCallback aCallback,
GeoPositionErrorCallback aErrorCallback,
PositionOptions* aOptions,
uint8_t aProtocolType,
bool aWatchPositionRequest,
int32_t aWatchId)
: mIsWatchPositionRequest(aWatchPositionRequest),
mCallback(aCallback),
mErrorCallback(aErrorCallback),
mCallback(Move(aCallback)),
mErrorCallback(Move(aErrorCallback)),
mOptions(aOptions),
mLocator(aLocator),
mWatchId(aWatchId),
@ -1390,10 +1390,8 @@ Geolocation::GetCurrentPosition(PositionCallback& aCallback,
const PositionOptions& aOptions,
ErrorResult& aRv)
{
GeoPositionCallback successCallback(&aCallback);
GeoPositionErrorCallback errorCallback(aErrorCallback);
nsresult rv = GetCurrentPosition(successCallback, errorCallback,
nsresult rv = GetCurrentPosition(GeoPositionCallback(&aCallback),
GeoPositionErrorCallback(aErrorCallback),
CreatePositionOptionsCopy(aOptions));
if (NS_FAILED(rv)) {
@ -1410,15 +1408,13 @@ Geolocation::GetCurrentPosition(nsIDOMGeoPositionCallback* aCallback,
{
NS_ENSURE_ARG_POINTER(aCallback);
GeoPositionCallback successCallback(aCallback);
GeoPositionErrorCallback errorCallback(aErrorCallback);
return GetCurrentPosition(successCallback, errorCallback, aOptions);
return GetCurrentPosition(GeoPositionCallback(aCallback),
GeoPositionErrorCallback(aErrorCallback), aOptions);
}
nsresult
Geolocation::GetCurrentPosition(GeoPositionCallback& callback,
GeoPositionErrorCallback& errorCallback,
Geolocation::GetCurrentPosition(GeoPositionCallback callback,
GeoPositionErrorCallback errorCallback,
PositionOptions *options)
{
if (mPendingCallbacks.Length() > MAX_GEO_REQUESTS_PER_WINDOW) {
@ -1430,7 +1426,7 @@ Geolocation::GetCurrentPosition(GeoPositionCallback& callback,
static_cast<uint8_t>(mProtocolType));
RefPtr<nsGeolocationRequest> request =
new nsGeolocationRequest(this, callback, errorCallback, options,
new nsGeolocationRequest(this, Move(callback), Move(errorCallback), options,
static_cast<uint8_t>(mProtocolType), false);
if (!sGeoEnabled) {
@ -1479,10 +1475,8 @@ Geolocation::WatchPosition(PositionCallback& aCallback,
ErrorResult& aRv)
{
int32_t ret = 0;
GeoPositionCallback successCallback(&aCallback);
GeoPositionErrorCallback errorCallback(aErrorCallback);
nsresult rv = WatchPosition(successCallback, errorCallback,
nsresult rv = WatchPosition(GeoPositionCallback(&aCallback),
GeoPositionErrorCallback(aErrorCallback),
CreatePositionOptionsCopy(aOptions), &ret);
if (NS_FAILED(rv)) {
@ -1500,15 +1494,14 @@ Geolocation::WatchPosition(nsIDOMGeoPositionCallback *aCallback,
{
NS_ENSURE_ARG_POINTER(aCallback);
GeoPositionCallback successCallback(aCallback);
GeoPositionErrorCallback errorCallback(aErrorCallback);
return WatchPosition(successCallback, errorCallback, aOptions, aRv);
return WatchPosition(GeoPositionCallback(aCallback),
GeoPositionErrorCallback(aErrorCallback),
aOptions, aRv);
}
nsresult
Geolocation::WatchPosition(GeoPositionCallback& aCallback,
GeoPositionErrorCallback& aErrorCallback,
Geolocation::WatchPosition(GeoPositionCallback aCallback,
GeoPositionErrorCallback aErrorCallback,
PositionOptions* aOptions,
int32_t* aRv)
{
@ -1524,8 +1517,9 @@ Geolocation::WatchPosition(GeoPositionCallback& aCallback,
*aRv = mLastWatchId++;
RefPtr<nsGeolocationRequest> request =
new nsGeolocationRequest(this, aCallback, aErrorCallback, aOptions,
static_cast<uint8_t>(mProtocolType), true, *aRv);
new nsGeolocationRequest(this, Move(aCallback), Move(aErrorCallback),
aOptions, static_cast<uint8_t>(mProtocolType),
true, *aRv);
if (!sGeoEnabled) {
nsCOMPtr<nsIRunnable> ev = new RequestAllowEvent(false, request);

View File

@ -189,8 +189,12 @@ private:
~Geolocation();
nsresult GetCurrentPosition(GeoPositionCallback& aCallback, GeoPositionErrorCallback& aErrorCallback, PositionOptions* aOptions);
nsresult WatchPosition(GeoPositionCallback& aCallback, GeoPositionErrorCallback& aErrorCallback, PositionOptions* aOptions, int32_t* aRv);
nsresult GetCurrentPosition(GeoPositionCallback aCallback,
GeoPositionErrorCallback aErrorCallback,
PositionOptions* aOptions);
nsresult WatchPosition(GeoPositionCallback aCallback,
GeoPositionErrorCallback aErrorCallback,
PositionOptions* aOptions, int32_t* aRv);
bool RegisterRequestWithPrompt(nsGeolocationRequest* request);

View File

@ -2614,6 +2614,9 @@ HTMLMediaElement::ResetConnectionState()
ChangeNetworkState(nsIDOMHTMLMediaElement::NETWORK_EMPTY);
ChangeDelayLoadStatus(false);
ChangeReadyState(nsIDOMHTMLMediaElement::HAVE_NOTHING);
if (mDecoder) {
ShutdownDecoder();
}
}
void

View File

@ -416,7 +416,7 @@ HTMLMenuItemElement::WalkRadioGroup(Visitor* aVisitor)
return;
}
nsAttrInfo info1(GetAttrInfo(kNameSpaceID_None,
BorrowedAttrInfo info1(GetAttrInfo(kNameSpaceID_None,
nsGkAtoms::radiogroup));
bool info1Empty = !info1.mValue || info1.mValue->IsEmptyString();
@ -429,7 +429,7 @@ HTMLMenuItemElement::WalkRadioGroup(Visitor* aVisitor)
continue;
}
nsAttrInfo info2(menuitem->GetAttrInfo(kNameSpaceID_None,
BorrowedAttrInfo info2(menuitem->GetAttrInfo(kNameSpaceID_None,
nsGkAtoms::radiogroup));
bool info2Empty = !info2.mValue || info2.mValue->IsEmptyString();

View File

@ -2235,8 +2235,6 @@ nsHTMLDocument::NamedGetter(JSContext* cx, const nsAString& aName, bool& aFound,
}
JS::Rooted<JS::Value> val(cx);
// XXXbz Should we call the (slightly misnamed, really) WrapNativeParent
// here?
if (!dom::WrapObject(cx, supp, cache, nullptr, &val)) {
rv.Throw(NS_ERROR_OUT_OF_MEMORY);
return;

Some files were not shown because too many files have changed in this diff Show More