Merge inbound to m-c. a=merge

This commit is contained in:
Ryan VanderMeulen 2017-09-15 14:20:02 -04:00
commit e1d23c6fa7
50 changed files with 4851 additions and 904 deletions

View File

@ -5842,10 +5842,8 @@
this._tabFilters.set(this.mCurrentTab, filter);
this.webProgress.addProgressListener(filter, nsIWebProgress.NOTIFY_ALL);
this.style.backgroundColor =
Services.prefs.getBoolPref("browser.display.use_system_colors") ?
"-moz-default-background-color" :
Services.prefs.getCharPref("browser.display.background_color");
if (Services.prefs.getBoolPref("browser.display.use_system_colors"))
this.style.backgroundColor = "-moz-default-background-color";
let messageManager = window.getGroupMessageManager("browsers");

View File

@ -386,6 +386,8 @@ These should match what Safari and other Apple applications use on OS X Lion. --
<!ENTITY appMenuRemoteTabs.managedevices.label "Manage Devices…">
<!ENTITY appMenuRemoteTabs.sidebar.label "View Synced Tabs Sidebar">
<!ENTITY appMenuRecentHighlights.label "Recent Highlights">
<!ENTITY customizeMenu.addToToolbar.label "Add to Toolbar">
<!ENTITY customizeMenu.addToToolbar.accesskey "A">
<!ENTITY customizeMenu.addToPanel.label "Add to Menu">

View File

@ -25,6 +25,16 @@
--tab-line-color: var(--lwt-accent-color);
}
tabbrowser {
/* Value for --in-content-page-background in in-content/common.inc.css */
background-color: #f9f9fa;
}
:root[privatebrowsingmode=temporary] tabbrowser {
/* Value for --in-content-page-background in aboutPrivateBrowsing.css */
background-color: #25003e;
}
#tabbrowser-tabs,
#tabbrowser-tabs > .tabbrowser-arrowscrollbox,
.tabbrowser-tabs[positionpinnedtabs] > .tabbrowser-tab[pinned] {

View File

@ -1076,7 +1076,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
}
.project-text-search .result.focused {
background-color: var(--theme-codemirror-gutter-background);
background-color: var(--search-overlays-semitransparent);
}
.project-text-search .result .query-match {
@ -1094,6 +1094,14 @@ html[dir="rtl"] .managed-tree .tree .node > div {
.project-text-search .result .line-number {
margin-right: 1em;
width: 2em;
margin-left: 0.8em;
}
.project-text-search .no-result-msg {
color: var(--theme-body-color-inactive);
font-size: 24px;
padding: 4px;
word-break: break-all;
}
.project-text-search .file-result {
@ -1109,7 +1117,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
}
.project-text-search .file-result.focused {
background-color: var(--theme-codemirror-gutter-background);
background-color: var(--search-overlays-semitransparent);
}
.project-text-search .line-match {
@ -1191,6 +1199,14 @@ html[dir="rtl"] .managed-tree .tree .node > div {
background-color: var(--theme-body-background);
}
.theme-dark .result-list li:hover {
background: var(--grey-70);
}
.theme-dark .result-list li.selected {
background: var(--grey-70);
}
.result-list li .title {
line-height: 1.5em;
word-break: break-all;
@ -1234,7 +1250,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
flex-direction: column;
z-index: 200;
background-color: var(--theme-body-background);
overflow-y: auto;
overflow-y: hidden;
}
.searchinput-container {
@ -1314,6 +1330,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
font-weight: lighter;
white-space: nowrap;
padding-inline-end: 10px;
cursor: default;
}
.sources-list {
@ -1383,6 +1400,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
padding: 5px;
margin-bottom: 0px;
margin-top: -1px;
cursor: default;
}
.source-footer .tab:hover {
@ -1404,6 +1422,15 @@ html[dir="rtl"] .managed-tree .tree .node > div {
overflow-y: auto;
}
.outline .outline-pane-info {
width: 100%;
font-style: italic;
text-align: center;
padding: 0.5em;
user-select: none;
font-size: 12px;
}
.outline-list {
list-style-type: none;
padding-left: 0px;
@ -1416,6 +1443,7 @@ html[dir="rtl"] .managed-tree .tree .node > div {
padding-left: 1rem;
padding-right: 0.5rem;
padding-top: 0.2rem;
cursor: default;
}
.outline-list__element:hover {
@ -2392,25 +2420,6 @@ html[dir="rtl"] .editor-mount {
}
}
.welcomebox {
width: calc(100% - 1px);
/* Offsetting it by 30px for the sources-header area */
height: calc(100% - 30px);
position: absolute;
top: 30px;
left: 0;
padding: 50px 0;
text-align: center;
font-size: 1.25em;
color: var(--theme-comment-alt);
background-color: var(--theme-tab-toolbar-background);
font-weight: lighter;
z-index: 100;
-moz-user-select: none;
user-select: none;
}
.CodeMirror-guttermarker-subtle {
visibility: hidden;
}
@ -2508,6 +2517,7 @@ html .breakpoints-list .breakpoint.paused {
display: inline-block;
padding-inline-start: 2px;
padding-bottom: 4px;
cursor: default;
}
.breakpoints-list .pause-indicator {
@ -2622,23 +2632,10 @@ html .breakpoints-list .breakpoint.paused {
.expression-input {
max-width: 50%;
}
.expression-separator {
padding: 0px 5px;
}
.expression-value {
overflow-x: scroll;
color: var(--theme-content-color2);
max-width: 50% !important;
}
.expression-error {
color: var(--theme-highlight-red);
}
.frames ul .frames-group .group,
.frames ul .frames-group .group .location {
font-weight: 500;
cursor: default;
}
.frames ul .frames-group.expanded .group,
@ -2669,6 +2666,7 @@ html .breakpoints-list .breakpoint.paused {
text-align: center;
font-style: italic;
font-weight: 300;
cursor: default;
}
.theme-dark .secondary-panes .why-paused {
@ -2705,14 +2703,6 @@ html .breakpoints-list .breakpoint.paused {
user-select: none;
}
.frames ul li:nth-of-type(2n) {
background-color: var(--theme-tab-toolbar-background);
}
.theme-dark .frames ul li:nth-of-type(2n) {
background-color: var(--theme-toolbar-background-alt);
}
.frames .location {
font-weight: lighter;
display: flex;
@ -2744,7 +2734,6 @@ html .breakpoints-list .breakpoint.paused {
outline: none;
}
.theme-dark .frames ul li:hover,
.theme-dark .frames ul li:focus {
background-color: var(--theme-tab-toolbar-background);
}
@ -2764,11 +2753,6 @@ html .breakpoints-list .breakpoint.paused {
color: white;
}
:root.theme-dark .frames ul li:hover .location,
:root.theme-dark .frames ul li.selected .location {
opacity: 1;
}
.show-more {
text-align: center;
padding: 8px 0px;
@ -2865,6 +2849,7 @@ html .breakpoints-list .breakpoint.paused {
-ms-user-select: none;
-o-user-select: none;
user-select: none;
cursor: default;
}
.accordion ._header:hover {
@ -3057,6 +3042,7 @@ html .command-bar > button:disabled {
padding: 0.5em;
-moz-user-select: none;
user-select: none;
cursor: default;
}
.theme-dark .secondary-panes .accordion .arrow svg {
@ -3077,6 +3063,7 @@ html .command-bar > button:disabled {
background-color: var(--theme-toolbar-background);
font-weight: lighter;
z-index: 100;
user-select: none;
}
.theme-dark .welcomebox {
@ -3158,7 +3145,8 @@ html .welcomebox .toggle-button-end.collapsed {
overflow: hidden;
padding: 5px;
margin-inline-start: 3px;
margin-top: 4px;
margin-top: 3px;
cursor: default;
}
.source-tab:hover {

File diff suppressed because one or more lines are too long

View File

@ -28731,6 +28731,10 @@ WorkerDispatcher.prototype = {
return;
}
if (!this.worker) {
reject("Oops, The worker has shutdown!");
return;
}
this.worker.removeEventListener("message", listener);
if (result.error) {
reject(result.error);
@ -28899,6 +28903,8 @@ var _getSymbols2 = _interopRequireDefault(_getSymbols);
var _ast = __webpack_require__(1051);
var _sources = __webpack_require__(1171);
var _getOutOfScopeLocations = __webpack_require__(1072);
var _getOutOfScopeLocations2 = _interopRequireDefault(_getOutOfScopeLocations);
@ -28922,6 +28928,9 @@ self.onmessage = workerHandler({
getSymbols: _getSymbols2.default,
clearSymbols: _getSymbols.clearSymbols,
clearASTs: _ast.clearASTs,
hasSource: _sources.hasSource,
setSource: _sources.setSource,
clearSources: _sources.clearSources,
getVariablesInScope: _scopes.getVariablesInScope,
getNextStep: _steps.getNextStep,
getEmptyLines: _getEmptyLines2.default
@ -32995,6 +33004,58 @@ function isArrayLikeObject(value) {
module.exports = isArrayLikeObject;
/***/ }),
/* 1156 */,
/* 1157 */,
/* 1158 */,
/* 1159 */,
/* 1160 */,
/* 1161 */,
/* 1162 */,
/* 1163 */,
/* 1164 */,
/* 1165 */,
/* 1166 */,
/* 1167 */,
/* 1168 */,
/* 1169 */,
/* 1170 */,
/* 1171 */
/***/ (function(module, exports, __webpack_require__) {
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.hasSource = hasSource;
exports.setSource = setSource;
exports.getSource = getSource;
exports.clearSources = clearSources;
var cachedSources = new Map();
function hasSource(sourceId) {
return cachedSources.has(sourceId);
}
function setSource(source) {
cachedSources.set(source.id, source);
}
function getSource(sourceId) {
if (!cachedSources.has(sourceId)) {
throw new Error(`${sourceId} was not provided.`);
}
return cachedSources.get(sourceId);
}
function clearSources() {
cachedSources = new Map();
}
/***/ })
/******/ ]);
});

View File

@ -7435,6 +7435,10 @@ WorkerDispatcher.prototype = {
return;
}
if (!this.worker) {
reject("Oops, The worker has shutdown!");
return;
}
this.worker.removeEventListener("message", listener);
if (result.error) {
reject(result.error);

View File

@ -426,6 +426,180 @@ function findSourceMatches(source, queryText) {
/***/ }),
/***/ 1165:
/***/ (function(module, exports, __webpack_require__) {
/* 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/. */
const networkRequest = __webpack_require__(1166);
const workerUtils = __webpack_require__(1168);
module.exports = {
networkRequest,
workerUtils
};
/***/ }),
/***/ 1166:
/***/ (function(module, exports) {
/* 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/. */
function networkRequest(url, opts) {
return fetch(url, {
cache: opts.loadFromCache ? "default" : "no-cache"
}).then(res => {
if (res.status >= 200 && res.status < 300) {
return res.text().then(text => ({ content: text }));
}
return Promise.reject(`request failed with status ${res.status}`);
});
}
module.exports = networkRequest;
/***/ }),
/***/ 1168:
/***/ (function(module, exports) {
function _asyncToGenerator(fn) { return function () { var gen = fn.apply(this, arguments); return new Promise(function (resolve, reject) { function step(key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { return Promise.resolve(value).then(function (value) { step("next", value); }, function (err) { step("throw", err); }); } } return step("next"); }); }; }
function WorkerDispatcher() {
this.msgId = 1;
this.worker = null;
} /* 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/. */
WorkerDispatcher.prototype = {
start(url) {
this.worker = new Worker(url);
this.worker.onerror = () => {
console.error(`Error in worker ${url}`);
};
},
stop() {
if (!this.worker) {
return;
}
this.worker.terminate();
this.worker = null;
},
task(method) {
return (...args) => {
return new Promise((resolve, reject) => {
const id = this.msgId++;
this.worker.postMessage({ id, method, args });
const listener = ({ data: result }) => {
if (result.id !== id) {
return;
}
this.worker.removeEventListener("message", listener);
if (result.error) {
reject(result.error);
} else {
resolve(result.response);
}
};
this.worker.addEventListener("message", listener);
});
};
}
};
function workerHandler(publicInterface) {
return function (msg) {
const { id, method, args } = msg.data;
try {
const response = publicInterface[method].apply(undefined, args);
if (response instanceof Promise) {
response.then(val => self.postMessage({ id, response: val }),
// Error can't be sent via postMessage, so be sure to
// convert to string.
err => self.postMessage({ id, error: err.toString() }));
} else {
self.postMessage({ id, response });
}
} catch (error) {
// Error can't be sent via postMessage, so be sure to convert to
// string.
self.postMessage({ id, error: error.toString() });
}
};
}
function streamingWorkerHandler(publicInterface, { timeout = 100 } = {}, worker = self) {
let streamingWorker = (() => {
var _ref = _asyncToGenerator(function* (id, tasks) {
let isWorking = true;
const intervalId = setTimeout(function () {
isWorking = false;
}, timeout);
const results = [];
while (tasks.length !== 0 && isWorking) {
const { callback, context, args } = tasks.shift();
const result = yield callback.call(context, args);
results.push(result);
}
worker.postMessage({ id, status: "pending", data: results });
clearInterval(intervalId);
if (tasks.length !== 0) {
yield streamingWorker(id, tasks);
}
});
return function streamingWorker(_x, _x2) {
return _ref.apply(this, arguments);
};
})();
return (() => {
var _ref2 = _asyncToGenerator(function* (msg) {
const { id, method, args } = msg.data;
const workerMethod = publicInterface[method];
if (!workerMethod) {
console.error(`Could not find ${method} defined in worker.`);
}
worker.postMessage({ id, status: "start" });
try {
const tasks = workerMethod(args);
yield streamingWorker(id, tasks);
worker.postMessage({ id, status: "done" });
} catch (error) {
worker.postMessage({ id, status: "error", error });
}
});
return function (_x3) {
return _ref2.apply(this, arguments);
};
})();
}
module.exports = {
WorkerDispatcher,
workerHandler,
streamingWorkerHandler
};
/***/ }),
/***/ 1173:
/***/ (function(module, exports, __webpack_require__) {
@ -694,7 +868,7 @@ module.exports = isObjectLike;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.isLoaded = exports.getMode = exports.getSourceLineCount = exports.getSourcePath = exports.getFilenameFromURL = exports.getFilename = exports.getRawSourceURL = exports.getPrettySourceURL = exports.shouldPrettyPrint = exports.isPretty = exports.isJavaScript = undefined;
exports.isLoaded = exports.getMode = exports.getSourceLineCount = exports.getSourcePath = exports.getFilenameFromURL = exports.getFilename = exports.getRawSourceURL = exports.getPrettySourceURL = exports.shouldPrettyPrint = exports.isThirdParty = exports.isPretty = exports.isJavaScript = undefined;
var _devtoolsSourceMap = __webpack_require__(898);
@ -768,6 +942,14 @@ function isPretty(source) {
return source.url ? /formatted$/.test(source.url) : false;
}
function isThirdParty(source) {
if (!source || !source.url) {
return false;
}
return !!source.url.match(/(node_modules|bower_components)/);
}
/**
* @memberof utils/source
* @static
@ -917,6 +1099,7 @@ function isLoaded(source) {
exports.isJavaScript = isJavaScript;
exports.isPretty = isPretty;
exports.isThirdParty = isThirdParty;
exports.shouldPrettyPrint = shouldPrettyPrint;
exports.getPrettySourceURL = getPrettySourceURL;
exports.getRawSourceURL = getRawSourceURL;
@ -2427,7 +2610,7 @@ const {
isOriginalId
} = __webpack_require__(899);
const { workerUtils: { WorkerDispatcher } } = __webpack_require__(900);
const { workerUtils: { WorkerDispatcher } } = __webpack_require__(1165);
const dispatcher = new WorkerDispatcher();
@ -2629,6 +2812,10 @@ WorkerDispatcher.prototype = {
return;
}
if (!this.worker) {
reject("Oops, The worker has shutdown!");
return;
}
this.worker.removeEventListener("message", listener);
if (result.error) {
reject(result.error);

View File

@ -26,7 +26,7 @@ add_task(function* () {
yield sourceSeen;
let loc1 = { url: JS_URL, line: 6 };
let newLoc1 = yield service.originalPositionFor(loc1.url, loc1.line);
let newLoc1 = yield service.originalPositionFor(loc1.url, loc1.line, 4);
checkLoc1(loc1, newLoc1);
let loc2 = { url: JS_URL, line: 8, column: 3 };

View File

@ -22,7 +22,7 @@ add_task(function* () {
yield sourceSeen;
info(`checking original location for ${JS_URL}:6`);
let newLoc = yield service.originalPositionFor(JS_URL, 6);
let newLoc = yield service.originalPositionFor(JS_URL, 6, 4);
is(newLoc.sourceUrl, ORIGINAL_URL, "check mapped URL");
is(newLoc.line, 4, "check mapped line number");

View File

@ -21,9 +21,14 @@ copySource.accesskey=y
# LOCALIZATION NOTE (copySourceUrl): This is the text that appears in the
# context menu to copy the source URL of file open.
copySourceUrl=Copy Source Url
copySourceUrl=Copy Source URL
copySourceUrl.accesskey=u
# LOCALIZATION NOTE (copyFunction): This is the text that appears in the
# context menu to copy the function the user selected
copyFunction.label=Copy Function
copyFunction.accesskey=F
# LOCALIZATION NOTE (copyStackTrace): This is the text that appears in the
# context menu to copy the stack trace methods, file names and row number.
copyStackTrace=Copy Stack Trace
@ -151,6 +156,10 @@ functionSearch.key=CmdOrCtrl+Shift+O
# when searching across all of the files in a project.
projectTextSearch.placeholder=Find in files…
# LOCALIZATION NOTE (projectTextSearch.noResults): The center pane Text Search
# message when the query did not match any text of all files in a project.
projectTextSearch.noResults=No results found
# LOCALIZATION NOTE (sources.noSourcesAvailable): Text shown when the debugger
# does not have any sources.
sources.noSourcesAvailable=This page has no sources
@ -236,6 +245,10 @@ breakpointMenuItem.disableAll=Disable all breakpoints
breakpointMenuItem.disableAll.accesskey=k
breakpointMenuItem.deleteAll=Remove all breakpoints
breakpointMenuItem.deleteAll.accesskey=a
breakpointMenuItem.removeCondition.label=Remove breakpoint condition
breakpointMenuItem.removeCondition.accesskey=c
breakpointMenuItem.editCondition.label=Edit breakpoint condition
breakpointMenuItem.editCondition.accesskey=n
# LOCALIZATION NOTE (breakpoints.header): Breakpoints right sidebar pane header.
breakpoints.header=Breakpoints
@ -294,6 +307,11 @@ editor.searchResults.prevResult=Previous Result
# toggling search type buttons(function search, variable search)
editor.searchTypeToggleTitle=Search for:
# LOCALIZATION NOTE (editor.continueToHere.label): Editor gutter context
# menu item for jumping to a new paused location
editor.continueToHere.label=Continue To Here
editor.continueToHere.accesskey=H
# LOCALIZATION NOTE (editor.addBreakpoint): Editor gutter context menu item
# for adding a breakpoint on a line.
editor.addBreakpoint=Add Breakpoint
@ -328,7 +346,7 @@ editor.conditionalPanel.close=Cancel edit breakpoint and close
# LOCALIZATION NOTE (editor.jumpToMappedLocation1): Context menu item
# for navigating to a source mapped location
editor.jumpToMappedLocation1=Jump to %S location
editor.jumpToMappedLocation1=Jump to %S Location
# LOCALIZATION NOTE (framework.disableGrouping): This is the text that appears in the
# context menu to disable framework grouping.
@ -341,10 +359,10 @@ framework.enableGrouping=Enable Framework Grouping
framework.enableGrouping.accesskey=u
# LOCALIZATION NOTE (generated): Source Map term for a server source location
generated=generated
generated=Generated
# LOCALIZATION NOTE (original): Source Map term for a debugger UI source location
original=original
original=Original
# LOCALIZATION NOTE (expressions.placeholder): Placeholder text for expression
# input element
@ -352,22 +370,22 @@ expressions.placeholder=Add Watch Expression
# LOCALIZATION NOTE (sourceTabs.closeTab): Editor source tab context menu item
# for closing the selected tab below the mouse.
sourceTabs.closeTab=Close tab
sourceTabs.closeTab=Close Tab
sourceTabs.closeTab.accesskey=c
# LOCALIZATION NOTE (sourceTabs.closeOtherTabs): Editor source tab context menu item
# for closing the other tabs.
sourceTabs.closeOtherTabs=Close others
sourceTabs.closeOtherTabs=Close Other Tabs
sourceTabs.closeOtherTabs.accesskey=o
# LOCALIZATION NOTE (sourceTabs.closeTabsToEnd): Editor source tab context menu item
# for closing the tabs to the end (the right for LTR languages) of the selected tab.
sourceTabs.closeTabsToEnd=Close tabs to the right
sourceTabs.closeTabsToEnd=Close Tabs to the Right
sourceTabs.closeTabsToEnd.accesskey=e
# LOCALIZATION NOTE (sourceTabs.closeAllTabs): Editor source tab context menu item
# for closing all tabs.
sourceTabs.closeAllTabs=Close all tabs
sourceTabs.closeAllTabs=Close All Tabs
sourceTabs.closeAllTabs.accesskey=a
# LOCALIZATION NOTE (sourceTabs.revealInTree): Editor source tab context menu item
@ -432,6 +450,9 @@ sources.header=Sources
# LOCALIZATION NOTE (outline.header): Outline left sidebar header
outline.header=Outline
# LOCALIZATION NOTE (outline.noFunctions): Outline text when there are no functions to display
outline.noFunctions=No functions
# LOCALIZATION NOTE (sources.search): Sources left sidebar prompt
# e.g. Cmd+P to search. On a mac, we use the command unicode character.
# On windows, it's ctrl.

View File

@ -40,3 +40,4 @@ pref("devtools.debugger.file-search-whole-word", false);
pref("devtools.debugger.file-search-regex-match", false);
pref("devtools.debugger.features.async-stepping", true);
pref("devtools.debugger.project-text-search-enabled", true);
pref("devtools.debugger.features.wasm", true);

View File

@ -72,6 +72,7 @@ return /******/ (function(modules) { // webpackBootstrap
const getOriginalURLs = dispatcher.task("getOriginalURLs");
const getGeneratedLocation = dispatcher.task("getGeneratedLocation");
const getOriginalLocation = dispatcher.task("getOriginalLocation");
const getLocationScopes = dispatcher.task("getLocationScopes");
const getOriginalSourceText = dispatcher.task("getOriginalSourceText");
const applySourceMap = dispatcher.task("applySourceMap");
const clearSourceMaps = dispatcher.task("clearSourceMaps");
@ -86,6 +87,7 @@ return /******/ (function(modules) { // webpackBootstrap
getOriginalURLs,
getGeneratedLocation,
getOriginalLocation,
getLocationScopes,
getOriginalSourceText,
applySourceMap,
clearSourceMaps,
@ -555,6 +557,10 @@ return /******/ (function(modules) { // webpackBootstrap
return;
}
if (!this.worker) {
reject("Oops, The worker has shutdown!");
return;
}
this.worker.removeEventListener("message", listener);
if (result.error) {
reject(result.error);

File diff suppressed because it is too large Load Diff

View File

@ -13,6 +13,7 @@
SimpleTest.waitForExplicitFinish();
browserElementTestHelpers.setEnabledPref(true);
browserElementTestHelpers.addPermission();
browserElementTestHelpers.allowTopLevelDataURINavigation();
function runTest()
{

View File

@ -11,6 +11,7 @@
SimpleTest.waitForExplicitFinish();
browserElementTestHelpers.setEnabledPref(true);
browserElementTestHelpers.addPermission();
browserElementTestHelpers.allowTopLevelDataURINavigation();
function runTest() {
var iframe = document.createElement('iframe');

View File

@ -9,6 +9,7 @@
SimpleTest.waitForExplicitFinish();
browserElementTestHelpers.setEnabledPref(true);
browserElementTestHelpers.addPermission();
browserElementTestHelpers.allowTopLevelDataURINavigation();
function runTest() {
var iframe = document.createElement('iframe');

View File

@ -7,6 +7,7 @@
SimpleTest.waitForExplicitFinish();
browserElementTestHelpers.setEnabledPref(true);
browserElementTestHelpers.addPermission();
browserElementTestHelpers.allowTopLevelDataURINavigation();
function runTest() {
var iframe = document.createElement('iframe');

View File

@ -7,6 +7,7 @@
SimpleTest.waitForExplicitFinish();
browserElementTestHelpers.setEnabledPref(true);
browserElementTestHelpers.addPermission();
browserElementTestHelpers.allowTopLevelDataURINavigation();
function runTest() {
var iframe1 = document.createElement('iframe');

View File

@ -1140,7 +1140,6 @@ TabParent::SendRealMouseEvent(WidgetMouseEvent& aEvent)
}
if (!mIsReadyToHandleInputEvents) {
if (eMouseEnterIntoWidget == aEvent.mMessage) {
MOZ_ASSERT(!mIsMouseEnterIntoWidgetEventSuppressed);
mIsMouseEnterIntoWidgetEventSuppressed = true;
} else if (eMouseExitFromWidget == aEvent.mMessage) {
mIsMouseEnterIntoWidgetEventSuppressed = false;

View File

@ -82,28 +82,6 @@ add_task(async function test_loopback() {
validateHistogramEntryCount("WEBAUTHN_GET_ASSERTION_MS", 1);
}
/*{
cleanupTelemetry();
// Same as test_successful_loopback, but we will swap to using a (non-existent)
// usb token. This will cause U2FRegisterAbort to fire, but will not execute the
// Sign function, and no histogram entries will log.
Services.prefs.setBoolPref("security.webauth.webauthn", true);
Services.prefs.setBoolPref("security.webauth.webauthn_enable_softtoken", false);
Services.prefs.setBoolPref("security.webauth.webauthn_enable_usbtoken", true);
await executeTestPage(testPage);
let webauthn_used = getTelemetryForScalar("security.webauthn_used");
ok(webauthn_used, "Scalar keys are set: " + Object.keys(webauthn_used).join(", "));
is(webauthn_used["U2FRegisterFinish"], undefined, "webauthn_used U2FRegisterFinish must be unset");
is(webauthn_used["U2FSignFinish"], undefined, "webauthn_used U2FSignFinish scalar must be unset");
is(webauthn_used["U2FRegisterAbort"], 1, "webauthn_used U2FRegisterAbort scalar should be a 1");
is(webauthn_used["U2FSignAbort"], undefined, "webauthn_used U2FSignAbort scalar must be unset");
validateHistogramEntryCount("WEBAUTHN_CREATE_CREDENTIAL_MS", 0);
validateHistogramEntryCount("WEBAUTHN_GET_ASSERTION_MS", 0);
}*/
// There aren't tests for register succeeding and sign failing, as I don't see an easy way to prompt
// the soft token to fail that way _and_ trigger the Abort telemetry.
});

View File

@ -23,8 +23,8 @@ pub mod platform;
#[path = "windows/mod.rs"]
pub mod platform;
#[cfg(any(target_os = "android"))]
#[path = "android/mod.rs"]
#[cfg(not(any(target_os = "linux", target_os = "macos", target_os = "windows")))]
#[path = "stub/mod.rs"]
pub mod platform;
#[macro_use]

View File

@ -376,7 +376,6 @@ WebRenderLayerManager::EndTransactionWithoutLayer(nsDisplayList* aDisplayList,
{
MOZ_ASSERT(aDisplayList && aDisplayListBuilder);
mEndTransactionWithoutLayers = true;
DiscardImages();
WrBridge()->RemoveExpiredFontKeys();
EndTransactionInternal(nullptr,
nullptr,
@ -686,7 +685,6 @@ WebRenderLayerManager::EndTransaction(DrawPaintedLayerCallback aCallback,
EndTransactionFlags aFlags)
{
mEndTransactionWithoutLayers = false;
DiscardImages();
WrBridge()->RemoveExpiredFontKeys();
EndTransactionInternal(aCallback, aCallbackData, aFlags);
}
@ -817,6 +815,11 @@ WebRenderLayerManager::EndTransactionInternal(DrawPaintedLayerCallback aCallback
mLatestTransactionId = mTransactionIdAllocator->GetTransactionId(/*aThrottle*/ true);
TimeStamp transactionStart = mTransactionIdAllocator->GetTransactionStart();
for (const auto& key : mImageKeysToDelete) {
resourceUpdates.DeleteImage(key);
}
mImageKeysToDelete.Clear();
// Skip the synchronization for buffer since we also skip the painting during
// device-reset status.
if (!gfxPlatform::GetPlatform()->DidRenderingDeviceReset()) {

View File

@ -0,0 +1,23 @@
Bug 1387937 - Import changeset 40324.
diff --git a/intl/icu/source/i18n/zonemeta.cpp b/intl/icu/source/i18n/zonemeta.cpp
--- a/intl/icu/source/i18n/zonemeta.cpp
+++ b/intl/icu/source/i18n/zonemeta.cpp
@@ -685,17 +685,16 @@ ZoneMeta::createMetazoneMappings(const U
entry->mzid = mz_name;
entry->from = from;
entry->to = to;
if (mzMappings == NULL) {
mzMappings = new UVector(deleteOlsonToMetaMappingEntry, NULL, status);
if (U_FAILURE(status)) {
delete mzMappings;
- deleteOlsonToMetaMappingEntry(entry);
uprv_free(entry);
break;
}
}
mzMappings->addElement(entry, status);
if (U_FAILURE(status)) {
break;

View File

@ -690,7 +690,6 @@ ZoneMeta::createMetazoneMappings(const UnicodeString &tzid) {
mzMappings = new UVector(deleteOlsonToMetaMappingEntry, NULL, status);
if (U_FAILURE(status)) {
delete mzMappings;
deleteOlsonToMetaMappingEntry(entry);
uprv_free(entry);
break;
}

View File

@ -73,6 +73,7 @@ for patch in \
u_setMemoryFunctions-callconvention-anachronism-msvc.diff \
bug-1373763-convertToPosix-stack-value-out-of-scope.diff \
bug-1380083 \
bug-1387937.diff \
; do
echo "Applying local patch $patch"
patch -d ${icu_dir}/../../ -p1 --no-backup-if-mismatch < ${icu_dir}/../icu-patches/$patch

View File

@ -38,13 +38,13 @@ Message::~Message() {
Message::Message()
: Pickle(MSG_HEADER_SZ) {
MOZ_COUNT_CTOR(IPC::Message);
header()->routing = header()->type = header()->flags = 0;
header()->routing = header()->type = 0;
#if defined(OS_POSIX)
header()->num_fds = 0;
#endif
#ifdef MOZ_TASK_TRACER
if (UseTaskTracerHeader()) {
header()->flags |= TASKTRACER_BIT;
header()->flags.SetTaskTracer();
HeaderTaskTracer* _header = static_cast<HeaderTaskTracer*>(header());
GetCurTraceInfo(&_header->source_event_id,
&_header->parent_task_id,
@ -57,21 +57,14 @@ Message::Message()
Message::Message(int32_t routing_id,
msgid_t type,
uint32_t segment_capacity,
NestedLevel nestedLevel,
PriorityValue priority,
MessageCompression compression,
HeaderFlags flags,
const char* const aName,
bool recordWriteLatency)
: Pickle(MSG_HEADER_SZ, segment_capacity) {
MOZ_COUNT_CTOR(IPC::Message);
header()->routing = routing_id;
header()->type = type;
header()->flags = nestedLevel;
set_priority(priority);
if (compression == COMPRESSION_ENABLED)
header()->flags |= COMPRESS_BIT;
else if (compression == COMPRESSION_ALL)
header()->flags |= COMPRESSALL_BIT;
header()->flags = flags;
#if defined(OS_POSIX)
header()->num_fds = 0;
#endif
@ -83,7 +76,7 @@ Message::Message(int32_t routing_id,
#endif
#ifdef MOZ_TASK_TRACER
if (UseTaskTracerHeader()) {
header()->flags |= TASKTRACER_BIT;
header()->flags.SetTaskTracer();
HeaderTaskTracer* _header = static_cast<HeaderTaskTracer*>(header());
GetCurTraceInfo(&_header->source_event_id,
&_header->parent_task_id,
@ -100,7 +93,7 @@ Message::Message(int32_t routing_id,
#define MSG_HEADER_SZ_DATA sizeof(Header)
#else
#define MSG_HEADER_SZ_DATA \
(reinterpret_cast<const Header*>(data)->flags & TASKTRACER_BIT ? \
(reinterpret_cast<const Header*>(data)->flags.IsTaskTracer() ? \
sizeof(HeaderTaskTracer) : sizeof(Header))
#endif
@ -119,6 +112,37 @@ Message::Message(Message&& other) : Pickle(mozilla::Move(other)) {
#endif
}
/*static*/ Message*
Message::IPDLMessage(int32_t routing_id,
msgid_t type,
HeaderFlags flags,
const char* const name)
{
return new Message(routing_id, type, 0, flags, name, true);
}
/*static*/ Message*
Message::ForSyncDispatchError(NestedLevel level)
{
auto* m = new Message(0, 0, 0, HeaderFlags(level));
auto& flags = m->header()->flags;
flags.SetSync();
flags.SetReply();
flags.SetReplyError();
return m;
}
/*static*/ Message*
Message::ForInterruptDispatchError()
{
auto* m = new Message();
auto& flags = m->header()->flags;
flags.SetInterrupt();
flags.SetReply();
flags.SetReplyError();
return m;
}
void Message::InitLoggingVariables(const char* const aName) {
name_ = aName;
}
@ -181,7 +205,7 @@ void *MessageTask() {
void
Message::TaskTracerDispatch() {
if (header()->flags & TASKTRACER_BIT) {
if (header()->flags.IsTaskTracer()) {
HeaderTaskTracer* _header = static_cast<HeaderTaskTracer*>(header());
_header->task_id = GenNewUniqueTaskId();
uintptr_t* vtab = reinterpret_cast<uintptr_t*>(&MessageTask);
@ -199,7 +223,7 @@ Message::AutoTaskTracerRun::AutoTaskTracerRun(Message& aMsg)
: mMsg(aMsg)
, mTaskId(0)
, mSourceEventId(0) {
if (mMsg.header()->flags & TASKTRACER_BIT) {
if (mMsg.header()->flags.IsTaskTracer()) {
const HeaderTaskTracer* _header =
static_cast<HeaderTaskTracer*>(mMsg.header());
LogBegin(_header->task_id,

View File

@ -57,6 +57,130 @@ class Message : public Pickle {
COMPRESSION_ALL
};
enum Sync {
SYNC = 0,
ASYNC = 1,
};
enum Interrupt {
NOT_INTERRUPT = 0,
INTERRUPT = 1,
};
enum Constructor {
NOT_CONSTRUCTOR = 0,
CONSTRUCTOR = 1,
};
enum Reply {
NOT_REPLY = 0,
REPLY = 1,
};
class HeaderFlags {
friend class Message;
enum {
NESTED_MASK = 0x0003,
PRIO_MASK = 0x000C,
SYNC_BIT = 0x0010,
REPLY_BIT = 0x0020,
REPLY_ERROR_BIT = 0x0040,
INTERRUPT_BIT = 0x0080,
COMPRESS_BIT = 0x0100,
COMPRESSALL_BIT = 0x0200,
COMPRESS_MASK = 0x0300,
CONSTRUCTOR_BIT = 0x0400,
#ifdef MOZ_TASK_TRACER
TASKTRACER_BIT = 0x0800,
#endif
};
public:
constexpr HeaderFlags()
: mFlags(NOT_NESTED)
{
}
explicit constexpr HeaderFlags(NestedLevel level)
: mFlags(level)
{
}
constexpr HeaderFlags(NestedLevel level, PriorityValue priority,
MessageCompression compression,
Constructor constructor,
Sync sync, Interrupt interrupt, Reply reply)
: mFlags(level |
(priority << 2) |
(compression == COMPRESSION_ENABLED ? COMPRESS_BIT :
compression == COMPRESSION_ALL ? COMPRESSALL_BIT : 0) |
(constructor == CONSTRUCTOR ? CONSTRUCTOR_BIT : 0) |
(sync == SYNC ? SYNC_BIT : 0) |
(interrupt == INTERRUPT ? INTERRUPT_BIT : 0) |
(reply == REPLY ? REPLY_BIT : 0))
{
}
NestedLevel Level() const {
return static_cast<NestedLevel>(mFlags & NESTED_MASK);
}
PriorityValue Priority() const {
return static_cast<PriorityValue>((mFlags & PRIO_MASK) >> 2);
}
MessageCompression Compression() const {
return ((mFlags & COMPRESS_BIT) ? COMPRESSION_ENABLED :
(mFlags & COMPRESSALL_BIT) ? COMPRESSION_ALL : COMPRESSION_NONE);
}
bool IsConstructor() const {
return (mFlags & CONSTRUCTOR_BIT) != 0;
}
bool IsSync() const {
return (mFlags & SYNC_BIT) != 0;
}
bool IsInterrupt() const {
return (mFlags & INTERRUPT_BIT) != 0;
}
bool IsReply() const {
return (mFlags & REPLY_BIT) != 0;
}
bool IsReplyError() const {
return (mFlags & REPLY_ERROR_BIT) != 0;
}
#ifdef MOZ_TASK_TRACER
bool IsTaskTracer() const {
return (mFlags & TASKTRACER_BIT) != 0;
}
#endif
private:
void SetSync() {
mFlags |= SYNC_BIT;
}
void SetInterrupt() {
mFlags |= INTERRUPT_BIT;
}
void SetReply() {
mFlags |= REPLY_BIT;
}
void SetReplyError() {
mFlags |= REPLY_ERROR_BIT;
}
#ifdef MOZ_TASK_TRACER
void SetTaskTracer() {
mFlags |= TASKTRACER_BIT;
}
#endif
uint32_t mFlags;
};
virtual ~Message();
Message();
@ -69,9 +193,7 @@ class Message : public Pickle {
Message(int32_t routing_id,
msgid_t type,
uint32_t segmentCapacity = 0, // 0 for the default capacity.
NestedLevel nestedLevel = NOT_NESTED,
PriorityValue priority = NORMAL_PRIORITY,
MessageCompression compression = COMPRESSION_NONE,
HeaderFlags flags = HeaderFlags(),
const char* const name="???",
bool recordWriteLatency=false);
@ -82,68 +204,51 @@ class Message : public Pickle {
Message& operator=(const Message& other) = delete;
Message& operator=(Message&& other);
NestedLevel nested_level() const {
return static_cast<NestedLevel>(header()->flags & NESTED_MASK);
}
// Helper method for the common case (default segmentCapacity, recording
// the write latency of messages) of IPDL message creation. This helps
// move the malloc and some of the parameter setting out of autogenerated
// code.
static Message* IPDLMessage(int32_t routing_id,
msgid_t type,
HeaderFlags flags,
const char* const name);
void set_nested_level(NestedLevel nestedLevel) {
DCHECK((nestedLevel & ~NESTED_MASK) == 0);
header()->flags = (header()->flags & ~NESTED_MASK) | nestedLevel;
// One-off constructors for special error-handling messages.
static Message* ForSyncDispatchError(NestedLevel level);
static Message* ForInterruptDispatchError();
NestedLevel nested_level() const {
return header()->flags.Level();
}
PriorityValue priority() const {
return static_cast<PriorityValue>((header()->flags & PRIO_MASK) >> 2);
}
void set_priority(PriorityValue prio) {
DCHECK(((prio << 2) & ~PRIO_MASK) == 0);
header()->flags = (header()->flags & ~PRIO_MASK) | (prio << 2);
return header()->flags.Priority();
}
bool is_constructor() const {
return (header()->flags & CONSTRUCTOR_BIT) != 0;
}
void set_constructor() {
header()->flags |= CONSTRUCTOR_BIT;
return header()->flags.IsConstructor();
}
// True if this is a synchronous message.
bool is_sync() const {
return (header()->flags & SYNC_BIT) != 0;
return header()->flags.IsSync();
}
// True if this is a synchronous message.
bool is_interrupt() const {
return (header()->flags & INTERRUPT_BIT) != 0;
return header()->flags.IsInterrupt();
}
// True if compression is enabled for this message.
MessageCompression compress_type() const {
return (header()->flags & COMPRESS_BIT) ?
COMPRESSION_ENABLED :
(header()->flags & COMPRESSALL_BIT) ?
COMPRESSION_ALL :
COMPRESSION_NONE;
}
// Set this on a reply to a synchronous message.
void set_reply() {
header()->flags |= REPLY_BIT;
return header()->flags.Compression();
}
bool is_reply() const {
return (header()->flags & REPLY_BIT) != 0;
}
// Set this on a reply to a synchronous message to indicate that no receiver
// was found.
void set_reply_error() {
header()->flags |= REPLY_ERROR_BIT;
return header()->flags.IsReply();
}
bool is_reply_error() const {
return (header()->flags & REPLY_ERROR_BIT) != 0;
return header()->flags.IsReplyError();
}
msgid_t type() const {
@ -283,14 +388,6 @@ class Message : public Pickle {
friend class MessageReplyDeserializer;
friend class SyncMessage;
void set_sync() {
header()->flags |= SYNC_BIT;
}
void set_interrupt() {
header()->flags |= INTERRUPT_BIT;
}
#ifdef MOZ_TASK_TRACER
void TaskTracerDispatch();
class AutoTaskTracerRun
@ -308,26 +405,10 @@ class Message : public Pickle {
protected:
#endif
// flags
enum {
NESTED_MASK = 0x0003,
PRIO_MASK = 0x000C,
SYNC_BIT = 0x0010,
REPLY_BIT = 0x0020,
REPLY_ERROR_BIT = 0x0040,
INTERRUPT_BIT = 0x0080,
COMPRESS_BIT = 0x0100,
COMPRESSALL_BIT = 0x0200,
CONSTRUCTOR_BIT = 0x0400,
#ifdef MOZ_TASK_TRACER
TASKTRACER_BIT = 0x0800,
#endif
};
struct Header : Pickle::Header {
int32_t routing; // ID of the view that this message is destined for
msgid_t type; // specifies the user-defined message type
uint32_t flags; // specifies control flags for the message
HeaderFlags flags; // specifies control flags for the message
#if defined(OS_POSIX)
uint32_t num_fds; // the number of descriptors included with this message
# if defined(OS_MACOSX)

View File

@ -2091,11 +2091,7 @@ MessageChannel::DispatchSyncMessage(const Message& aMsg, Message*& aReply)
}
if (!MaybeHandleError(rv, aMsg, "DispatchSyncMessage")) {
aReply = new Message();
aReply->set_sync();
aReply->set_nested_level(aMsg.nested_level());
aReply->set_reply();
aReply->set_reply_error();
aReply = Message::ForSyncDispatchError(aMsg.nested_level());
}
aReply->set_seqno(aMsg.seqno());
aReply->set_transaction_id(aMsg.transaction_id());
@ -2152,10 +2148,7 @@ MessageChannel::DispatchInterruptMessage(Message&& aMsg, size_t stackDepth)
--mRemoteStackDepthGuess;
if (!MaybeHandleError(rv, aMsg, "DispatchInterruptMessage")) {
reply = new Message();
reply->set_interrupt();
reply->set_reply();
reply->set_reply_error();
reply = Message::ForInterruptDispatchError();
}
reply->set_seqno(aMsg.seqno());

View File

@ -77,7 +77,7 @@ public:
: IPC::Message(MSG_ROUTING_CONTROL, // these only go to top-level actors
CHANNEL_OPENED_MESSAGE_TYPE,
0,
aNestedLevel)
HeaderFlags(aNestedLevel))
{
IPC::WriteParam(this, aDescriptor);
IPC::WriteParam(this, aOtherProcess);

View File

@ -25,7 +25,8 @@ public:
id_t aIPDLId,
size_t aSize,
SharedMemory::SharedMemoryType aType) :
IPC::Message(routingId, SHMEM_CREATED_MESSAGE_TYPE, 0, NESTED_INSIDE_CPOW)
IPC::Message(routingId, SHMEM_CREATED_MESSAGE_TYPE, 0,
HeaderFlags(NESTED_INSIDE_CPOW))
{
IPC::WriteParam(this, aIPDLId);
IPC::WriteParam(this, aSize);

View File

@ -1597,24 +1597,14 @@ class _GenerateProtocolCode(ipdl.ast.Visitor):
segmentcapacity = self.segmentcapacitydict.get(name, 0)
mfDecl, mfDefn = _splitFuncDeclDefn(
_generateMessageConstructor(md.msgCtorFunc(), md.msgId(),
segmentcapacity,
md.decl.type.nested,
md.decl.type.prio,
md.prettyMsgName(p.name+'::'),
md.decl.type.compress))
_generateMessageConstructor(md, segmentcapacity, p,
forReply=False))
decls.append(mfDecl)
self.funcDefns.append(mfDefn)
if md.hasReply():
rfDecl, rfDefn = _splitFuncDeclDefn(
_generateMessageConstructor(
md.replyCtorFunc(), md.replyId(),
0,
md.decl.type.nested,
md.decl.type.prio,
md.prettyReplyName(p.name+'::'),
md.decl.type.compress))
_generateMessageConstructor(md, 0, p, forReply=True))
decls.append(rfDecl)
self.funcDefns.append(rfDefn)
@ -1711,7 +1701,22 @@ class _GenerateProtocolCode(ipdl.ast.Visitor):
##--------------------------------------------------
def _generateMessageConstructor(clsname, msgid, segmentSize, nested, prio, prettyName, compress):
def _generateMessageConstructor(md, segmentSize, protocol, forReply=False):
if forReply:
clsname = md.replyCtorFunc()
msgid = md.replyId()
prettyName = md.prettyReplyName(protocol.name+'::')
replyEnum = 'REPLY'
else:
clsname = md.msgCtorFunc()
msgid = md.msgId()
prettyName = md.prettyMsgName(protocol.name+'::')
replyEnum = 'NOT_REPLY'
nested = md.decl.type.nested
prio = md.decl.type.prio
compress = md.decl.type.compress
routingId = ExprVar('routingId')
func = FunctionDefn(FunctionDecl(
@ -1720,39 +1725,73 @@ def _generateMessageConstructor(clsname, msgid, segmentSize, nested, prio, prett
ret=Type('IPC::Message', ptr=1)))
if compress == 'compress':
compression = ExprVar('IPC::Message::COMPRESSION_ENABLED')
compression = 'COMPRESSION_ENABLED'
elif compress:
assert compress == 'compressall'
compression = ExprVar('IPC::Message::COMPRESSION_ALL')
compression = 'COMPRESSION_ALL'
else:
compression = ExprVar('IPC::Message::COMPRESSION_NONE')
compression = 'COMPRESSION_NONE'
if nested == ipdl.ast.NOT_NESTED:
nestedEnum = 'IPC::Message::NOT_NESTED'
nestedEnum = 'NOT_NESTED'
elif nested == ipdl.ast.INSIDE_SYNC_NESTED:
nestedEnum = 'IPC::Message::NESTED_INSIDE_SYNC'
nestedEnum = 'NESTED_INSIDE_SYNC'
else:
assert nested == ipdl.ast.INSIDE_CPOW_NESTED
nestedEnum = 'IPC::Message::NESTED_INSIDE_CPOW'
nestedEnum = 'NESTED_INSIDE_CPOW'
if prio == ipdl.ast.NORMAL_PRIORITY:
prioEnum = 'IPC::Message::NORMAL_PRIORITY'
prioEnum = 'NORMAL_PRIORITY'
elif prio == ipdl.ast.INPUT_PRIORITY:
prioEnum = 'IPC::Message::INPUT_PRIORITY'
prioEnum = 'INPUT_PRIORITY'
else:
prioEnum = 'IPC::Message::HIGH_PRIORITY'
prioEnum = 'HIGH_PRIORITY'
func.addstmt(
StmtReturn(ExprNew(Type('IPC::Message'),
args=[ routingId,
ExprVar(msgid),
ExprLiteral.Int(int(segmentSize)),
ExprVar(nestedEnum),
ExprVar(prioEnum),
compression,
ExprLiteral.String(prettyName),
# Pass `true` to recordWriteLatency to collect telemetry
ExprLiteral.TRUE ])))
if md.decl.type.isSync():
syncEnum = 'SYNC'
else:
syncEnum = 'ASYNC'
if md.decl.type.isInterrupt():
interruptEnum = 'INTERRUPT'
else:
interruptEnum = 'NOT_INTERRUPT'
if md.decl.type.isCtor():
ctorEnum = 'CONSTRUCTOR'
else:
ctorEnum = 'NOT_CONSTRUCTOR'
def messageEnum(valname):
return ExprVar('IPC::Message::' + valname)
flags = ExprCall(ExprVar('IPC::Message::HeaderFlags'),
args=[ messageEnum(nestedEnum),
messageEnum(prioEnum),
messageEnum(compression),
messageEnum(ctorEnum),
messageEnum(syncEnum),
messageEnum(interruptEnum),
messageEnum(replyEnum) ])
segmentSize = int(segmentSize)
if segmentSize:
func.addstmt(
StmtReturn(ExprNew(Type('IPC::Message'),
args=[ routingId,
ExprVar(msgid),
ExprLiteral.Int(int(segmentSize)),
flags,
ExprLiteral.String(prettyName),
# Pass `true` to recordWriteLatency to collect telemetry
ExprLiteral.TRUE ])))
else:
func.addstmt(
StmtReturn(ExprCall(ExprVar('IPC::Message::IPDLMessage'),
args=[ routingId,
ExprVar(msgid),
flags,
ExprLiteral.String(prettyName) ])))
return func
@ -4273,7 +4312,7 @@ class _GenerateProtocolActorCode(ipdl.ast.Visitor):
+ [ self.checkedWrite(p.ipdltype, p.var(), msgvar, sentinelKey=p.name, this=this)
for p in md.params ]
+ [ Whitespace.NL ]
+ self.setMessageFlags(md, msgvar, reply=0))
+ self.setMessageFlags(md, msgvar))
return msgvar, stmts
@ -4290,7 +4329,7 @@ class _GenerateProtocolActorCode(ipdl.ast.Visitor):
resolvertype = Type(md.resolverName())
failifsendok = StmtIf(ExprNot(sendok))
failifsendok.addifstmt(_printWarningMessage('Error sending reply'))
sendmsg = (self.setMessageFlags(md, self.replyvar, reply=1, seqno=seqno)
sendmsg = (self.setMessageFlags(md, self.replyvar, seqno=seqno)
+ [ self.logMessage(md, self.replyvar, 'Sending reply '),
StmtDecl(Decl(Type.BOOL, sendok.name),
init=ExprCall(
@ -4361,7 +4400,7 @@ class _GenerateProtocolActorCode(ipdl.ast.Visitor):
Whitespace.NL ]
+ [ self.checkedWrite(r.ipdltype, r.var(), replyvar, sentinelKey=r.name)
for r in md.returns ]
+ self.setMessageFlags(md, replyvar, reply=1)
+ self.setMessageFlags(md, replyvar)
+ [ self.logMessage(md, replyvar, 'Sending reply ') ])
def genVerifyMessage(self, verify, params, errfn, msgsrcVar):
@ -4404,24 +4443,9 @@ class _GenerateProtocolActorCode(ipdl.ast.Visitor):
return stmts
def setMessageFlags(self, md, var, reply, seqno=None):
def setMessageFlags(self, md, var, seqno=None):
stmts = [ ]
if md.decl.type.isSync():
stmts.append(StmtExpr(ExprCall(
ExprSelect(var, '->', 'set_sync'))))
elif md.decl.type.isInterrupt():
stmts.append(StmtExpr(ExprCall(
ExprSelect(var, '->', 'set_interrupt'))))
if md.decl.type.isCtor():
stmts.append(StmtExpr(ExprCall(
ExprSelect(var, '->', 'set_constructor'))))
if reply:
stmts.append(StmtExpr(ExprCall(
ExprSelect(var, '->', 'set_reply'))))
if seqno:
stmts.append(StmtExpr(ExprCall(
ExprSelect(var, '->', 'set_seqno'),

View File

@ -214,10 +214,13 @@ typedef enum JSWhyMagic
JS_WHY_MAGIC_COUNT
} JSWhyMagic;
namespace js {
static inline JS::Value PoisonedObjectValue(uintptr_t poison);
} // namespace js
namespace JS {
static inline constexpr JS::Value UndefinedValue();
static inline JS::Value PoisonedObjectValue(JSObject* obj);
namespace detail {
@ -361,7 +364,7 @@ class MOZ_NON_PARAM alignas(8) Value
}
void setObject(JSObject& obj) {
MOZ_ASSERT(uintptr_t(&obj) > 0x1000 || uintptr_t(&obj) == 0x48);
MOZ_ASSERT(uintptr_t(&obj) >= 0x1000);
#if defined(JS_PUNBOX64)
// VisualStudio cannot contain parenthesized C++ style cast and shift
// inside decltype in template parameter:
@ -377,7 +380,7 @@ class MOZ_NON_PARAM alignas(8) Value
data.asBits = bitsFromTagAndPayload(JSVAL_TAG_OBJECT, PayloadType(obj));
}
friend inline Value PoisonedObjectValue(JSObject* obj);
friend inline Value js::PoisonedObjectValue(uintptr_t poison);
public:
void setBoolean(bool b) {
@ -1081,14 +1084,6 @@ ObjectValue(JSObject& obj)
return v;
}
static inline Value
ObjectValueCrashOnTouch()
{
Value v;
v.setObject(*reinterpret_cast<JSObject*>(0x48));
return v;
}
static inline Value
MagicValue(JSWhyMagic why)
{
@ -1235,14 +1230,6 @@ PrivateGCThingValue(js::gc::Cell* cell)
return v;
}
static inline Value
PoisonedObjectValue(JSObject* obj)
{
Value v;
v.setObjectNoCheck(obj);
return v;
}
inline bool
SameType(const Value& lhs, const Value& rhs)
{
@ -1454,6 +1441,14 @@ template <class S> struct VoidDefaultAdaptor { static void defaultValue(const S&
template <class S> struct IdentityDefaultAdaptor { static S defaultValue(const S& v) {return v;} };
template <class S, bool v> struct BoolDefaultAdaptor { static bool defaultValue(const S&) { return v; } };
static inline JS::Value
PoisonedObjectValue(uintptr_t poison)
{
JS::Value v;
v.setObjectNoCheck(reinterpret_cast<JSObject*>(poison));
return v;
}
} // namespace js
#ifdef DEBUG

View File

@ -66,21 +66,21 @@ BEGIN_TEST(testGCStoreBufferRemoval)
new (relocValue) HeapPtr<Value>;
*relocValue = ObjectValue(*NurseryObject());
relocValue->~HeapPtr<Value>();
punnedValue = ObjectValueCrashOnTouch();
punnedValue = js::PoisonedObjectValue(0x48);
JS_GC(cx);
new (relocValue) HeapPtr<Value>;
*relocValue = ObjectValue(*NurseryObject());
*relocValue = ObjectValue(*tenuredObject);
relocValue->~HeapPtr<Value>();
punnedValue = ObjectValueCrashOnTouch();
punnedValue = js::PoisonedObjectValue(0x48);
JS_GC(cx);
new (relocValue) HeapPtr<Value>;
*relocValue = ObjectValue(*NurseryObject());
*relocValue = NullValue();
relocValue->~HeapPtr<Value>();
punnedValue = ObjectValueCrashOnTouch();
punnedValue = js::PoisonedObjectValue(0x48);
JS_GC(cx);
}

View File

@ -309,12 +309,12 @@ Poison(void* ptr, uint8_t value, size_t num)
// Unfortunately, this adds about 2% more overhead, so we can only enable
// it in debug.
#if defined(DEBUG)
uintptr_t obj;
memset(&obj, value, sizeof(obj));
uintptr_t poison;
memset(&poison, value, sizeof(poison));
# if defined(JS_PUNBOX64)
obj = obj & ((uintptr_t(1) << JSVAL_TAG_SHIFT) - 1);
poison = poison & ((uintptr_t(1) << JSVAL_TAG_SHIFT) - 1);
# endif
JS::Value v = JS::PoisonedObjectValue(reinterpret_cast<JSObject*>(obj));
JS::Value v = js::PoisonedObjectValue(poison);
size_t value_count = num / sizeof(v);
size_t byte_count = num % sizeof(v);

View File

@ -41,7 +41,7 @@ Debug_SetValueRangeToCrashOnTouch(Value* beg, Value* end)
{
#ifdef DEBUG
for (Value* v = beg; v != end; ++v)
v->setObject(*reinterpret_cast<JSObject*>(0x48));
*v = js::PoisonedObjectValue(0x48);
#endif
}

View File

@ -116,7 +116,7 @@ class RegExpShared : public gc::TenuredCell
};
/* Source to the RegExp, for lazy compilation. */
HeapPtr<JSAtom*> source;
GCPtr<JSAtom*> source;
RegExpFlag flags;
bool canStringMatch;

View File

@ -475,10 +475,10 @@ public:
*/
void Accumulate(ContainerState* aState,
nsDisplayItem* aItem,
const nsIntRegion& aClippedOpaqueRegion,
const nsIntRect& aVisibleRect,
const DisplayItemClip& aClip,
LayerState aLayerState);
LayerState aLayerState,
nsDisplayList *aList);
AnimatedGeometryRoot* GetAnimatedGeometryRoot() { return mAnimatedGeometryRoot; }
/**
@ -3431,10 +3431,10 @@ IsItemAreaInWindowOpaqueRegion(nsDisplayListBuilder* aBuilder,
void
PaintedLayerData::Accumulate(ContainerState* aState,
nsDisplayItem* aItem,
const nsIntRegion& aClippedOpaqueRegion,
const nsIntRect& aVisibleRect,
const DisplayItemClip& aClip,
LayerState aLayerState)
LayerState aLayerState,
nsDisplayList* aList)
{
FLB_LOG_PAINTED_LAYER_DECISION(this, "Accumulating dp=%s(%p), f=%p against pld=%p\n", aItem->Name(), aItem, aItem->Frame(), this);
@ -3470,11 +3470,16 @@ PaintedLayerData::Accumulate(ContainerState* aState,
return;
}
nsIntRegion opaquePixels = aState->ComputeOpaqueRect(aItem,
mAnimatedGeometryRoot, mASR, aClip, aList,
&mHideAllLayersBelow, &mOpaqueForAnimatedGeometryRootParent);
opaquePixels.AndWith(aVisibleRect);
/* Mark as available for conversion to image layer if this is a nsDisplayImage and
* it's the only thing visible in this layer.
*/
if (nsIntRegion(aVisibleRect).Contains(mVisibleRegion) &&
aClippedOpaqueRegion.Contains(mVisibleRegion) &&
opaquePixels.Contains(mVisibleRegion) &&
aItem->SupportsOptimizingToImage()) {
mImage = static_cast<nsDisplayImageContainer*>(aItem);
FLB_LOG_PAINTED_LAYER_DECISION(this, " Tracking image: nsDisplayImageContainer covers the layer\n");
@ -3525,8 +3530,8 @@ PaintedLayerData::Accumulate(ContainerState* aState,
mVisibleRegion.SimplifyOutward(4);
}
if (!aClippedOpaqueRegion.IsEmpty()) {
for (auto iter = aClippedOpaqueRegion.RectIter(); !iter.Done(); iter.Next()) {
if (!opaquePixels.IsEmpty()) {
for (auto iter = opaquePixels.RectIter(); !iter.Done(); iter.Next()) {
// We don't use SimplifyInward here since it's not defined exactly
// what it will discard. For our purposes the most important case
// is a large opaque background at the bottom of z-order (e.g.,
@ -4486,14 +4491,7 @@ ContainerState::ProcessDisplayItems(nsDisplayList* aList,
if (mManager->IsWidgetLayerManager()) {
paintedLayerData->UpdateCommonClipCount(itemClip);
}
nsIntRegion opaquePixels = ComputeOpaqueRect(item,
animatedGeometryRoot, itemASR, itemClip, aList,
&paintedLayerData->mHideAllLayersBelow,
&paintedLayerData->mOpaqueForAnimatedGeometryRootParent);
MOZ_ASSERT(nsIntRegion(itemDrawRect).Contains(opaquePixels));
opaquePixels.AndWith(itemVisibleRect);
paintedLayerData->Accumulate(this, item, opaquePixels,
itemVisibleRect, itemClip, layerState);
paintedLayerData->Accumulate(this, item, itemVisibleRect, itemClip, layerState, aList);
if (!paintedLayerData->mLayer) {
// Try to recycle the old layer of this display item.

View File

@ -18,11 +18,9 @@
enum class DisplayItemType {
TYPE_ZERO = 0, /** Spacer so that the first item starts at 1 */
#define DECLARE_DISPLAY_ITEM_TYPE(name) TYPE_##name,
#define DECLARE_DISPLAY_ITEM_TYPE_FLAGS(name,flags) TYPE_##name,
#define DECLARE_DISPLAY_ITEM_TYPE(name,flags) TYPE_##name,
#include "nsDisplayItemTypesList.h"
#undef DECLARE_DISPLAY_ITEM_TYPE
#undef DECLARE_DISPLAY_ITEM_TYPE_FLAGS
TYPE_MAX
};
@ -39,11 +37,9 @@ enum DisplayItemFlags {
inline const char* DisplayItemTypeName(DisplayItemType aType)
{
switch (aType) {
#define DECLARE_DISPLAY_ITEM_TYPE(name) case DisplayItemType::TYPE_##name: return #name;
#define DECLARE_DISPLAY_ITEM_TYPE_FLAGS(name,flags) case DisplayItemType::TYPE_##name: return #name;
#define DECLARE_DISPLAY_ITEM_TYPE(name,flags) case DisplayItemType::TYPE_##name: return #name;
#include "nsDisplayItemTypesList.h"
#undef DECLARE_DISPLAY_ITEM_TYPE
#undef DECLARE_DISPLAY_ITEM_TYPE_FLAGS
default: return "TYPE_UNKNOWN";
}
@ -53,11 +49,9 @@ inline uint8_t GetDisplayItemFlagsForType(DisplayItemType aType)
{
static const uint8_t flags[static_cast<uint32_t>(DisplayItemType::TYPE_MAX)] = {
0
#define DECLARE_DISPLAY_ITEM_TYPE(name) ,0
#define DECLARE_DISPLAY_ITEM_TYPE_FLAGS(name,flags) ,flags
#define DECLARE_DISPLAY_ITEM_TYPE(name,flags) ,flags
#include "nsDisplayItemTypesList.h"
#undef DECLARE_DISPLAY_ITEM_TYPE
#undef DECLARE_DISPLAY_ITEM_TYPE_FLAGS
};
return flags[static_cast<uint32_t>(aType)];

View File

@ -1,99 +1,101 @@
// IWYU pragma: private, include "nsDisplayList.h"
DECLARE_DISPLAY_ITEM_TYPE(ALT_FEEDBACK)
DECLARE_DISPLAY_ITEM_TYPE(BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(THEMED_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE_FLAGS(BACKGROUND_COLOR,TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BLEND_CONTAINER)
DECLARE_DISPLAY_ITEM_TYPE(BLEND_MODE)
DECLARE_DISPLAY_ITEM_TYPE(BORDER)
DECLARE_DISPLAY_ITEM_TYPE(BOX_SHADOW_OUTER)
DECLARE_DISPLAY_ITEM_TYPE(BOX_SHADOW_INNER)
DECLARE_DISPLAY_ITEM_TYPE(BULLET)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_BORDER_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_BOX_SHADOW_OUTER)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_FOREGROUND)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_BACKGROUND_COLOR)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_THEMED_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_BACKGROUND_IMAGE)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_FOCUS)
DECLARE_DISPLAY_ITEM_TYPE(CARET)
DECLARE_DISPLAY_ITEM_TYPE(CHECKED_CHECKBOX)
DECLARE_DISPLAY_ITEM_TYPE(CHECKED_RADIOBUTTON)
DECLARE_DISPLAY_ITEM_TYPE(CLEAR_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(COLUMN_RULE)
DECLARE_DISPLAY_ITEM_TYPE(COMBOBOX_FOCUS)
DECLARE_DISPLAY_ITEM_TYPE(EVENT_RECEIVER)
DECLARE_DISPLAY_ITEM_TYPE(LAYER_EVENT_REGIONS)
DECLARE_DISPLAY_ITEM_TYPE(FIELDSET_BORDER_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(FIXED_POSITION)
DECLARE_DISPLAY_ITEM_TYPE(STICKY_POSITION)
DECLARE_DISPLAY_ITEM_TYPE(FRAMESET_BORDER)
DECLARE_DISPLAY_ITEM_TYPE(FRAMESET_BLANK)
DECLARE_DISPLAY_ITEM_TYPE(HEADER_FOOTER)
DECLARE_DISPLAY_ITEM_TYPE(IMAGE)
DECLARE_DISPLAY_ITEM_TYPE(LIST_FOCUS)
DECLARE_DISPLAY_ITEM_TYPE(OPACITY)
DECLARE_DISPLAY_ITEM_TYPE(OPTION_EVENT_GRABBER)
DECLARE_DISPLAY_ITEM_TYPE(OUTLINE)
DECLARE_DISPLAY_ITEM_TYPE(OWN_LAYER)
DECLARE_DISPLAY_ITEM_TYPE(PLUGIN)
DECLARE_DISPLAY_ITEM_TYPE(PLUGIN_READBACK)
DECLARE_DISPLAY_ITEM_TYPE(PLUGIN_VIDEO)
DECLARE_DISPLAY_ITEM_TYPE(PRINT_PLUGIN)
DECLARE_DISPLAY_ITEM_TYPE(RANGE_FOCUS_RING)
DECLARE_DISPLAY_ITEM_TYPE(REMOTE)
DECLARE_DISPLAY_ITEM_TYPE(RESOLUTION)
DECLARE_DISPLAY_ITEM_TYPE(SCROLL_INFO_LAYER)
DECLARE_DISPLAY_ITEM_TYPE(SELECTION_OVERLAY)
DECLARE_DISPLAY_ITEM_TYPE(SOLID_COLOR)
DECLARE_DISPLAY_ITEM_TYPE(SOLID_COLOR_REGION)
DECLARE_DISPLAY_ITEM_TYPE(SUBDOCUMENT)
DECLARE_DISPLAY_ITEM_TYPE(MASK)
DECLARE_DISPLAY_ITEM_TYPE(FILTER)
DECLARE_DISPLAY_ITEM_TYPE(SVG_OUTER_SVG)
DECLARE_DISPLAY_ITEM_TYPE(SVG_GEOMETRY)
DECLARE_DISPLAY_ITEM_TYPE(SVG_TEXT)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_CELL_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_CELL_SELECTION)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_BORDER_COLLAPSE)
DECLARE_DISPLAY_ITEM_TYPE(TEXT)
DECLARE_DISPLAY_ITEM_TYPE(TEXT_OVERFLOW)
DECLARE_DISPLAY_ITEM_TYPE_FLAGS(TRANSFORM,TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE_FLAGS(PERSPECTIVE,TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(VIDEO)
DECLARE_DISPLAY_ITEM_TYPE(WRAP_LIST)
DECLARE_DISPLAY_ITEM_TYPE(ZOOM)
DECLARE_DISPLAY_ITEM_TYPE(GENERIC)
DECLARE_DISPLAY_ITEM_TYPE(ALT_FEEDBACK, 0)
DECLARE_DISPLAY_ITEM_TYPE(BACKGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(THEMED_BACKGROUND, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BACKGROUND_COLOR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BLEND_CONTAINER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BLEND_MODE, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BORDER, 0)
DECLARE_DISPLAY_ITEM_TYPE(BOX_SHADOW_OUTER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BOX_SHADOW_INNER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BULLET, 0)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_BORDER_BACKGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_BOX_SHADOW_OUTER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(BUTTON_FOREGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_BACKGROUND_COLOR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_THEMED_BACKGROUND, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_BACKGROUND_IMAGE, 0)
DECLARE_DISPLAY_ITEM_TYPE(CANVAS_FOCUS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CARET, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CHECKED_CHECKBOX, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CHECKED_RADIOBUTTON, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(CLEAR_BACKGROUND, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(COLUMN_RULE, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(COMBOBOX_FOCUS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(EVENT_RECEIVER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(LAYER_EVENT_REGIONS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(FIELDSET_BORDER_BACKGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(FIXED_POSITION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(STICKY_POSITION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(FRAMESET_BORDER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(FRAMESET_BLANK, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(HEADER_FOOTER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(IMAGE, 0)
DECLARE_DISPLAY_ITEM_TYPE(LIST_FOCUS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(OPACITY, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(OPTION_EVENT_GRABBER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(OUTLINE, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(OWN_LAYER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(PLUGIN, 0)
DECLARE_DISPLAY_ITEM_TYPE(PLUGIN_READBACK, 0)
DECLARE_DISPLAY_ITEM_TYPE(PRINT_PLUGIN, 0)
DECLARE_DISPLAY_ITEM_TYPE(RANGE_FOCUS_RING, 0)
DECLARE_DISPLAY_ITEM_TYPE(REMOTE, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(RESOLUTION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SCROLL_INFO_LAYER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SELECTION_OVERLAY, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SOLID_COLOR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SOLID_COLOR_REGION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SUBDOCUMENT, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MASK, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(FILTER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SVG_OUTER_SVG, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(SVG_GEOMETRY, 0)
DECLARE_DISPLAY_ITEM_TYPE(SVG_TEXT, 0)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_CELL_BACKGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_CELL_SELECTION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_BORDER_COLLAPSE, 0)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_BACKGROUND_COLOR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_BACKGROUND_IMAGE, 0)
DECLARE_DISPLAY_ITEM_TYPE(TABLE_FIXED_POSITION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(TEXT, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(TEXT_OVERFLOW, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(TRANSFORM,TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(PERSPECTIVE,TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(VIDEO, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(WRAP_LIST, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(ZOOM, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(GENERIC, TYPE_RENDERS_NO_IMAGES)
#if defined(MOZ_REFLOW_PERF_DSP) && defined(MOZ_REFLOW_PERF)
DECLARE_DISPLAY_ITEM_TYPE(REFLOW_COUNT)
DECLARE_DISPLAY_ITEM_TYPE(REFLOW_COUNT, TYPE_RENDERS_NO_IMAGES)
#endif
#ifdef MOZ_XUL
DECLARE_DISPLAY_ITEM_TYPE(XUL_EVENT_REDIRECTOR)
DECLARE_DISPLAY_ITEM_TYPE(XUL_GROUP_BACKGROUND)
DECLARE_DISPLAY_ITEM_TYPE(XUL_IMAGE)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TEXT_BOX)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TREE_BODY)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TREE_COL_SPLITTER_TARGET)
DECLARE_DISPLAY_ITEM_TYPE(XUL_EVENT_REDIRECTOR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(XUL_GROUP_BACKGROUND, 0)
DECLARE_DISPLAY_ITEM_TYPE(XUL_IMAGE, 0)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TEXT_BOX, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TREE_BODY, 0)
DECLARE_DISPLAY_ITEM_TYPE(XUL_TREE_COL_SPLITTER_TARGET, TYPE_RENDERS_NO_IMAGES)
#ifdef DEBUG_LAYOUT
DECLARE_DISPLAY_ITEM_TYPE(XUL_DEBUG)
DECLARE_DISPLAY_ITEM_TYPE(XUL_DEBUG, TYPE_RENDERS_NO_IMAGES)
#endif
#endif
DECLARE_DISPLAY_ITEM_TYPE(MATHML_BAR)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_CHAR_FOREGROUND)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_ERROR)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_MENCLOSE_NOTATION)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_SELECTION_RECT)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_SLASH)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_BAR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_CHAR_FOREGROUND, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_ERROR, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_MENCLOSE_NOTATION, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_SELECTION_RECT, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_SLASH, TYPE_RENDERS_NO_IMAGES)
#ifdef DEBUG
DECLARE_DISPLAY_ITEM_TYPE(MATHML_BOUNDING_METRICS)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_CHAR_DEBUG)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_BOUNDING_METRICS, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(MATHML_CHAR_DEBUG, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_BORDER)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_IMAGE_MAP)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_PLACEHOLDER)
DECLARE_DISPLAY_ITEM_TYPE(EVENT_TARGET_BORDER)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_BORDER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_IMAGE_MAP, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(DEBUG_PLACEHOLDER, TYPE_RENDERS_NO_IMAGES)
DECLARE_DISPLAY_ITEM_TYPE(EVENT_TARGET_BORDER, TYPE_RENDERS_NO_IMAGES)
#endif

View File

@ -2,7 +2,7 @@ default-preferences pref(layout.css.box-decoration-break.enabled,true)
== box-decoration-break-1.html box-decoration-break-1-ref.html
fuzzy(1,20) fuzzy-if(skiaContent,1,700) fuzzy-if(webrender,4-4,36-36) == box-decoration-break-with-inset-box-shadow-1.html box-decoration-break-with-inset-box-shadow-1-ref.html
fuzzy(16,460) fuzzy-if(skiaContent,57,374) fuzzy-if(Android,57,1330) fuzzy-if(styloVsGecko,2,1410) == box-decoration-break-with-outset-box-shadow-1.html box-decoration-break-with-outset-box-shadow-1-ref.html # Bug 1386543
fuzzy(45,460) fuzzy-if(skiaContent,57,374) fuzzy-if(Android,57,1330) fuzzy-if(styloVsGecko,2,1410) == box-decoration-break-with-outset-box-shadow-1.html box-decoration-break-with-outset-box-shadow-1-ref.html # Bug 1386543
random-if(!gtkWidget) HTTP(..) == box-decoration-break-border-image.html box-decoration-break-border-image-ref.html
== box-decoration-break-block-border-padding.html box-decoration-break-block-border-padding-ref.html
== box-decoration-break-block-margin.html box-decoration-break-block-margin-ref.html

View File

@ -208,13 +208,13 @@ public class ActionBarPresenter {
mIconView.setVisibility(View.INVISIBLE);
} else {
SecurityModeUtil.IconType icon;
if ("unknown".equals(security.securityMode)) {
if (SecurityInformation.SECURITY_MODE_UNKNOWN == security.securityMode) {
icon = SecurityModeUtil.IconType.UNKNOWN;
} else {
icon = SecurityModeUtil.IconType.LOCK_SECURE;
}
if ("loaded".equals(security.mixedModePassive)) {
if (SecurityInformation.CONTENT_LOADED == security.mixedModePassive) {
icon = SecurityModeUtil.IconType.WARNING;
}

View File

@ -105,8 +105,8 @@ public class CustomTabsSecurityPopup extends AnchoredPopup {
init();
}
final boolean isIdentityKnown = ("identified".equals(security.securityMode) ||
"verified".equals(security.securityMode));
final boolean isIdentityKnown = (SecurityInformation.SECURITY_MODE_IDENTIFIED == security.securityMode ||
SecurityInformation.SECURITY_MODE_VERIFIED == security.securityMode);
updateConnectionState(security);
toggleIdentityKnownContainerVisibility(isIdentityKnown);
@ -132,18 +132,18 @@ public class CustomTabsSecurityPopup extends AnchoredPopup {
*/
private void updateConnectionState(final SecurityInformation security) {
if (!security.isSecure) {
if ("loaded".equals(security.mixedModeActive)) {
if (SecurityInformation.CONTENT_LOADED == security.mixedModeActive) {
// Active Mixed Content loaded because user has disabled blocking.
mIcon.setImageResource(R.drawable.ic_lock_disabled);
clearSecurityStateIcon();
mMixedContentActivity.setVisibility(View.VISIBLE);
mMixedContentActivity.setText(R.string.mixed_content_protection_disabled);
} else if ("loaded".equals(security.mixedModePassive)) {
} else if (SecurityInformation.CONTENT_LOADED == security.mixedModePassive) {
// Passive Mixed Content loaded.
mIcon.setImageResource(R.drawable.ic_lock_inactive);
setSecurityStateIcon(R.drawable.ic_warning_major, 1);
mMixedContentActivity.setVisibility(View.VISIBLE);
if ("blocked".equals(security.mixedModeActive)) {
if (SecurityInformation.CONTENT_BLOCKED == security.mixedModeActive) {
mMixedContentActivity.setText(R.string.mixed_content_blocked_some);
} else {
mMixedContentActivity.setText(R.string.mixed_content_display_loaded);
@ -160,7 +160,6 @@ public class CustomTabsSecurityPopup extends AnchoredPopup {
mSecurityState.setTextColor(ContextCompat.getColor(mContext, R.color.placeholder_active_grey));
} else if (security.isException) {
mIcon.setImageResource(R.drawable.ic_lock_inactive);
setSecurityStateIcon(R.drawable.ic_warning_major, 1);
mSecurityState.setText(R.string.identity_connection_insecure);
@ -175,8 +174,8 @@ public class CustomTabsSecurityPopup extends AnchoredPopup {
mSecurityState.setText(R.string.identity_connection_secure);
// Mixed content has been blocked, if present.
if ("blocked".equals(security.mixedModeActive) ||
"blocked".equals(security.mixedModePassive)) {
if (SecurityInformation.CONTENT_BLOCKED == security.mixedModeActive ||
SecurityInformation.CONTENT_BLOCKED == security.mixedModePassive) {
mMixedContentActivity.setVisibility(View.VISIBLE);
mMixedContentActivity.setText(R.string.mixed_content_blocked_all);
} else {

View File

@ -1235,6 +1235,13 @@ public class GeckoView extends LayerView {
* Class representing security information for a site.
*/
public class SecurityInformation {
public static final int SECURITY_MODE_UNKNOWN = 0;
public static final int SECURITY_MODE_IDENTIFIED = 1;
public static final int SECURITY_MODE_VERIFIED = 2;
public static final int CONTENT_UNKNOWN = 0;
public static final int CONTENT_BLOCKED = 1;
public static final int CONTENT_LOADED = 2;
/**
* Indicates whether or not the site is secure.
*/
@ -1268,35 +1275,35 @@ public class GeckoView extends LayerView {
*/
public final String issuerOrganization;
/**
* Indicates the security level of the site; possible values are "unknown",
* "identified", and "verified". "identified" indicates domain validation only,
* while "verified" indicates extended validation.
* Indicates the security level of the site; possible values are SECURITY_MODE_UNKNOWN,
* SECURITY_MODE_IDENTIFIED, and SECURITY_MODE_VERIFIED. SECURITY_MODE_IDENTIFIED
* indicates domain validation only, while SECURITY_MODE_VERIFIED indicates extended validation.
*/
public final String securityMode;
public final int securityMode;
/**
* Indicates the presence of passive mixed content; possible values are
* "unknown", "blocked", and "loaded".
* CONTENT_UNKNOWN, CONTENT_BLOCKED, and CONTENT_LOADED.
*/
public final String mixedModePassive;
public final int mixedModePassive;
/**
* Indicates the presence of active mixed content; possible values are
* "unknown", "blocked", and "loaded".
* CONTENT_UNKNOWN, CONTENT_BLOCKED, and CONTENT_LOADED.
*/
public final String mixedModeActive;
public final int mixedModeActive;
/**
* Indicates the status of tracking protection; possible values are
* "unknown", "blocked", and "loaded".
* CONTENT_UNKNOWN, CONTENT_BLOCKED, and CONTENT_LOADED.
*/
public final String trackingMode;
public final int trackingMode;
/* package */ SecurityInformation(GeckoBundle identityData) {
final GeckoBundle mode = identityData.getBundle("mode");
mixedModePassive = mode.getString("mixed_display");
mixedModeActive = mode.getString("mixed_active");
trackingMode = mode.getString("tracking");
mixedModePassive = mode.getInt("mixed_display");
mixedModeActive = mode.getInt("mixed_active");
trackingMode = mode.getInt("tracking");
securityMode = mode.getString("identity");
securityMode = mode.getInt("identity");
isSecure = identityData.getBoolean("secure");
isException = identityData.getBoolean("securityException");

View File

@ -24,38 +24,39 @@ function debug(aMsg) {
}
var IdentityHandler = {
// The definitions below should be kept in sync with those in GeckoView.ProgressListener.SecurityInformation
// No trusted identity information. No site identity icon is shown.
IDENTITY_MODE_UNKNOWN: "unknown",
IDENTITY_MODE_UNKNOWN: 0,
// Domain-Validation SSL CA-signed domain verification (DV).
IDENTITY_MODE_IDENTIFIED: "identified",
IDENTITY_MODE_IDENTIFIED: 1,
// Extended-Validation SSL CA-signed identity information (EV). A more rigorous validation process.
IDENTITY_MODE_VERIFIED: "verified",
IDENTITY_MODE_VERIFIED: 2,
// The following mixed content modes are only used if "security.mixed_content.block_active_content"
// is enabled. Our Java frontend coalesces them into one indicator.
// No mixed content information. No mixed content icon is shown.
MIXED_MODE_UNKNOWN: "unknown",
MIXED_MODE_UNKNOWN: 0,
// Blocked active mixed content.
MIXED_MODE_CONTENT_BLOCKED: "blocked",
MIXED_MODE_CONTENT_BLOCKED: 1,
// Loaded active mixed content.
MIXED_MODE_CONTENT_LOADED: "loaded",
MIXED_MODE_CONTENT_LOADED: 2,
// The following tracking content modes are only used if tracking protection
// is enabled. Our Java frontend coalesces them into one indicator.
// No tracking content information. No tracking content icon is shown.
TRACKING_MODE_UNKNOWN: "unknown",
TRACKING_MODE_UNKNOWN: 0,
// Blocked active tracking content. Shield icon is shown, with a popup option to load content.
TRACKING_MODE_CONTENT_BLOCKED: "blocked",
TRACKING_MODE_CONTENT_BLOCKED: 1,
// Loaded active tracking content. Yellow triangle icon is shown.
TRACKING_MODE_CONTENT_LOADED: "loaded",
TRACKING_MODE_CONTENT_LOADED: 2,
_useTrackingProtection: false,
_usePrivateMode: false,

View File

@ -212,7 +212,7 @@ Tester.prototype = {
return this.tests[this.currentTestIndex];
},
get done() {
return this.currentTestIndex == this.tests.length - 1;
return (this.currentTestIndex == this.tests.length - 1) && (this.repeat <= 0);
},
start: function Tester_start() {
@ -336,40 +336,34 @@ Tester.prototype = {
// Include failures from window state checking prior to running the first test
failCount += this.failuresFromInitialWindowState;
if (this.repeat > 0) {
--this.repeat;
this.currentTestIndex = -1;
this.nextTest();
TabDestroyObserver.destroy();
Services.console.unregisterListener(this);
// It's important to terminate the module to avoid crashes on shutdown.
this.PromiseTestUtils.uninit();
// In the main process, we print the ShutdownLeaksCollector message here.
let pid = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime).processID;
dump("Completed ShutdownLeaks collections in process " + pid + "\n");
this.structuredLogger.info("TEST-START | Shutdown");
if (this.tests.length) {
let e10sMode = gMultiProcessBrowser ? "e10s" : "non-e10s";
this.structuredLogger.info("Browser Chrome Test Summary");
this.structuredLogger.info("Passed: " + passCount);
this.structuredLogger.info("Failed: " + failCount);
this.structuredLogger.info("Todo: " + todoCount);
this.structuredLogger.info("Mode: " + e10sMode);
} else {
TabDestroyObserver.destroy();
Services.console.unregisterListener(this);
// It's important to terminate the module to avoid crashes on shutdown.
this.PromiseTestUtils.uninit();
// In the main process, we print the ShutdownLeaksCollector message here.
let pid = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime).processID;
dump("Completed ShutdownLeaks collections in process " + pid + "\n");
this.structuredLogger.info("TEST-START | Shutdown");
if (this.tests.length) {
let e10sMode = gMultiProcessBrowser ? "e10s" : "non-e10s";
this.structuredLogger.info("Browser Chrome Test Summary");
this.structuredLogger.info("Passed: " + passCount);
this.structuredLogger.info("Failed: " + failCount);
this.structuredLogger.info("Todo: " + todoCount);
this.structuredLogger.info("Mode: " + e10sMode);
} else {
this.structuredLogger.error("browser-test.js | No tests to run. Did you pass invalid test_paths?");
}
this.structuredLogger.info("*** End BrowserChrome Test Results ***");
// Tests complete, notify the callback and return
this.callback(this.tests);
this.callback = null;
this.tests = null;
this.structuredLogger.error("browser-test.js | No tests to run. Did you pass invalid test_paths?");
}
this.structuredLogger.info("*** End BrowserChrome Test Results ***");
// Tests complete, notify the callback and return
this.callback(this.tests);
this.callback = null;
this.tests = null;
},
haltTests: function Tester_haltTests() {
@ -690,8 +684,18 @@ Tester.prototype = {
return;
}
this.currentTestIndex++;
this.execTest();
if (this.repeat > 0) {
--this.repeat;
if (this.currentTestIndex < 0) {
this.currentTestIndex = 0;
}
this.execTest();
} else {
this.currentTestIndex++;
if (gConfig.repeat)
this.repeat = gConfig.repeat;
this.execTest();
}
});
}),

View File

@ -10,9 +10,16 @@ Cu.import("resource://gre/modules/AppConstants.jsm", this);
Cu.import("resource://gre/modules/AsyncShutdown.jsm", this);
Cu.import("resource://gre/modules/KeyValueParser.jsm");
Cu.import("resource://gre/modules/osfile.jsm", this);
Cu.import("resource://gre/modules/PromiseUtils.jsm", this);
Cu.import("resource://gre/modules/Services.jsm", this);
Cu.import("resource://gre/modules/XPCOMUtils.jsm", this);
// Set to true if the application is quitting
var gQuitting = false;
// Tracks all the running instances of the minidump-analyzer
var gRunningProcesses = new Set();
/**
* Run the minidump analyzer tool to gather stack traces from the minidump. The
* stack traces will be stored in the .extra file under the StackTraces= entry.
@ -31,9 +38,9 @@ function runMinidumpAnalyzer(minidumpPath) {
let exe = Services.dirsvc.get("GreBinD", Ci.nsIFile);
if (AppConstants.platform === "macosx") {
exe.append("crashreporter.app");
exe.append("Contents");
exe.append("MacOS");
exe.append("crashreporter.app");
exe.append("Contents");
exe.append("MacOS");
}
exe.append(exeName);
@ -46,6 +53,7 @@ function runMinidumpAnalyzer(minidumpPath) {
process.runAsync(args, args.length, (subject, topic, data) => {
switch (topic) {
case "process-finished":
gRunningProcesses.delete(process);
resolve();
break;
default:
@ -53,6 +61,8 @@ function runMinidumpAnalyzer(minidumpPath) {
break;
}
});
gRunningProcesses.add(process);
} catch (e) {
Cu.reportError(e);
}
@ -120,7 +130,9 @@ function processExtraFile(extraPath) {
*
* It is a service because some background activity will eventually occur.
*/
this.CrashService = function() {};
this.CrashService = function() {
Services.obs.addObserver(this, "quit-application");
};
CrashService.prototype = Object.freeze({
classID: Components.ID("{92668367-1b17-4190-86b2-1061b2179744}"),
@ -168,7 +180,12 @@ CrashService.prototype = Object.freeze({
let metadata = {};
let hash = null;
await runMinidumpAnalyzer(minidumpPath);
if (!gQuitting) {
// Minidump analysis can take a long time, don't start it if the browser
// is already quitting.
await runMinidumpAnalyzer(minidumpPath);
}
metadata = await processExtraFile(extraPath);
hash = await computeMinidumpHash(minidumpPath);
@ -194,6 +211,13 @@ CrashService.prototype = Object.freeze({
// Side-effect is the singleton is instantiated.
Services.crashmanager;
break;
case "quit-application":
gQuitting = true;
gRunningProcesses.forEach((process) => {
process.kill();
Services.obs.notifyObservers(null, "test-minidump-analyzer-killed");
});
break;
}
},
});

View File

@ -7,6 +7,7 @@ var {classes: Cc, interfaces: Ci, utils: Cu} = Components;
Cu.import("resource://gre/modules/osfile.jsm", this);
Cu.import("resource://gre/modules/Services.jsm", this);
Cu.import("resource://gre/modules/Timer.jsm");
Cu.import("resource://testing-common/AppData.jsm", this);
Cu.import("resource://testing-common/CrashManagerTest.jsm", this);
var bsp = Cu.import("resource://gre/modules/CrashManager.jsm", {});
@ -28,23 +29,40 @@ add_task(async function test_instantiation() {
"The objects are the same.");
});
add_task(async function test_addCrash() {
const crashId = "56cd87bc-bb26-339b-3a8e-f00c0f11380e";
var gMinidumpDir = do_get_tempdir();
var gCrashReporter = Cc["@mozilla.org/toolkit/crash-reporter;1"]
.getService(Ci.nsICrashReporter);
// Ensure that the nsICrashReporter methods can find the dump
gCrashReporter.minidumpPath = gMinidumpDir;
var gDumpFile;
var gExtraFile;
// Sets up a fake crash dump and sets up the crashreporter so that it will be
// able to find it.
async function setup(crashId) {
let cwd = await OS.File.getCurrentDirectory();
let minidump = OS.Path.join(cwd, "crash.dmp");
let extra = OS.Path.join(cwd, "crash.extra");
let dir = do_get_tempdir();
// Make a copy of the files because the .extra file will be modified
await OS.File.copy(minidump, OS.Path.join(dir.path, crashId + ".dmp"));
await OS.File.copy(extra, OS.Path.join(dir.path, crashId + ".extra"));
gDumpFile = OS.Path.join(gMinidumpDir.path, crashId + ".dmp");
await OS.File.copy(minidump, gDumpFile);
gExtraFile = OS.Path.join(gMinidumpDir.path, crashId + ".extra");
await OS.File.copy(extra, gExtraFile);
// Ensure that the nsICrashReporter methods can find the dump
let crashReporter =
Components.classes["@mozilla.org/toolkit/crash-reporter;1"]
.getService(Components.interfaces.nsICrashReporter);
crashReporter.minidumpPath = dir;
}
// Cleans up the fake crash dump and resets the minidump path
async function teardown() {
await OS.File.remove(gDumpFile);
await OS.File.remove(gExtraFile);
}
add_task(async function test_addCrash() {
const crashId = "56cd87bc-bb26-339b-3a8e-f00c0f11380e";
await setup(crashId);
let cs = Cc["@mozilla.org/crashservice;1"].getService(Ci.nsICrashService);
await cs.addCrash(Ci.nsICrashService.PROCESS_TYPE_CONTENT,
@ -72,6 +90,57 @@ add_task(async function test_addCrash() {
Assert.ok(false, "StackTraces does not contain valid JSON.");
}
// Remove the minidumps to prevent the test harness from thinking we crashed
await OS.File.removeDir(dir.path);
await teardown();
});
add_task(async function test_addCrash_quitting() {
const firstCrashId = "0e578a74-a887-48cb-b270-d4775d01e715";
const secondCrashId = "208379e5-1979-430d-a066-f6e57a8130ce";
await setup(firstCrashId);
let minidumpAnalyzerKilledPromise = new Promise((resolve, reject) => {
Services.obs.addObserver((subject, topic, data) => {
if (topic === "test-minidump-analyzer-killed") {
resolve();
}
reject();
}, "test-minidump-analyzer-killed");
});
let cs = Cc["@mozilla.org/crashservice;1"].getService(Ci.nsICrashService);
let addCrashPromise =
cs.addCrash(Ci.nsICrashService.PROCESS_TYPE_CONTENT,
Ci.nsICrashService.CRASH_TYPE_CRASH, firstCrashId);
// Spin the event loop so that the minidump analyzer is launched
await new Promise((resolve) => { do_execute_soon(resolve); });
// Pretend we're quitting
let obs = cs.QueryInterface(Ci.nsIObserver);
obs.observe(null, "quit-application", null);
// Wait for the minidump analyzer to be killed
await minidumpAnalyzerKilledPromise;
// Now wait for the crash to be recorded
await addCrashPromise;
let crashes = await Services.crashmanager.getCrashes();
let crash = crashes.find(c => { return c.id === firstCrashId; });
Assert.ok(crash, "Crash " + firstCrashId + " has been stored successfully.");
// Cleanup the fake crash and generate a new one
await teardown();
await setup(secondCrashId);
await cs.addCrash(Ci.nsICrashService.PROCESS_TYPE_CONTENT,
Ci.nsICrashService.CRASH_TYPE_CRASH, secondCrashId);
crashes = await Services.crashmanager.getCrashes();
crash = crashes.find(c => { return c.id === secondCrashId; });
Assert.ok(crash, "Crash " + secondCrashId + " has been stored successfully.");
Assert.ok(crash.metadata.StackTraces === undefined,
"The StackTraces field is not present because the minidump " +
"analyzer did not start.\n");
await teardown();
});

View File

@ -472,6 +472,9 @@ nsresult nsCocoaWindow::CreateNativeWindow(const NSRect &aRect,
mWindow = [[windowClass alloc] initWithContentRect:contentRect styleMask:features
backing:NSBackingStoreBuffered defer:YES];
// By default, hide window titles.
[mWindow setTitleVisibility:NSWindowTitleHidden];
// setup our notification delegate. Note that setDelegate: does NOT retain.
mDelegate = [[WindowDelegate alloc] initWithGeckoWindow:this];
[mWindow setDelegate:mDelegate];
@ -1840,9 +1843,11 @@ nsCocoaWindow::SetTitle(const nsAString& aTitle)
if ([mWindow drawsContentsIntoWindowFrame] && ![mWindow wantsTitleDrawn]) {
// Don't cause invalidations.
[mWindow disableSetNeedsDisplay];
[mWindow setTitleVisibility:NSWindowTitleHidden];
[mWindow setTitle:title];
[mWindow enableSetNeedsDisplay];
} else {
[mWindow setTitleVisibility:NSWindowTitleVisible];
[mWindow setTitle:title];
}