Merge fx-team to elm

This commit is contained in:
Nick Alexander 2013-10-18 11:39:01 -07:00
commit bcdd987f34
971 changed files with 8503 additions and 4284 deletions

View File

@ -360,6 +360,7 @@ pref("browser.dom.window.dump.enabled", false);
// Default Content Security Policy to apply to privileged and certified apps
pref("security.apps.privileged.CSP.default", "default-src *; script-src 'self'; object-src 'none'; style-src 'self' 'unsafe-inline'");
// If you change this CSP, make sure to update the fast path in nsCSPService.cpp
pref("security.apps.certified.CSP.default", "default-src *; script-src 'self'; object-src 'none'; style-src 'self'");
// Temporarily force-enable GL compositing. This is default-disabled
@ -388,9 +389,6 @@ pref("dom.ipc.browser_frames.oop_by_default", false);
// SMS/MMS
pref("dom.sms.enabled", true);
pref("dom.sms.strict7BitEncoding", false); // Disabled by default.
pref("dom.sms.requestStatusReport", true); // Enabled by default.
pref("dom.mms.requestStatusReport", true); // Enabled by default.
//The waiting time in network manager.
pref("network.gonk.ms-release-mms-connection", 30000);
@ -434,7 +432,6 @@ pref("services.push.udp.wakeupEnabled", true);
// NetworkStats
#ifdef MOZ_B2G_RIL
pref("dom.mozNetworkStats.enabled", true);
pref("ril.cellbroadcast.disabled", false);
pref("dom.webapps.firstRunWithSIM", true);
#endif
@ -730,10 +727,6 @@ pref("font.size.inflation.disabledInMasterProcess", true);
// consumption when applications are sent to the background.
pref("memory.free_dirty_pages", true);
// UAProfile settings
pref("wap.UAProf.url", "");
pref("wap.UAProf.tagname", "x-wap-profile");
pref("layout.imagevisibility.enabled", false);
pref("layout.imagevisibility.numscrollportwidths", 1);
pref("layout.imagevisibility.numscrollportheights", 1);
@ -824,6 +817,19 @@ pref("gfx.canvas.azure.accelerated", true);
// Enable Telephony API
pref("dom.telephony.enabled", true);
// Cell Broadcast API
pref("dom.cellbroadcast.enabled", true);
pref("ril.cellbroadcast.disabled", false);
// ICC API
pref("dom.icc.enabled", true);
// Mobile Connection API
pref("dom.mobileconnection.enabled", true);
// Voice Mail API
pref("dom.voicemail.enabled", true);
// The url of the page used to display network error details.
pref("b2g.neterror.url", "app://system.gaiamobile.org/net_error.html");

View File

@ -1,4 +1,4 @@
{
"revision": "563d1aa93586165246ab2ab9d40566a598f56387",
"revision": "154bb18c48ff06e41fb7ba24d8f72d520919646f",
"repo_path": "/integration/gaia-central"
}

View File

@ -20,8 +20,7 @@
],
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1"
"MOZILLA_OFFICIAL": "1"
},
"b2g_manifest": "hamachi.xml",
"b2g_manifest_branch": "master",

View File

@ -20,7 +20,6 @@
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1",
"ANDROIDFS_DIR": "{workdir}/helix-ics"
},
"b2g_manifest": "helix.xml",

View File

@ -20,8 +20,7 @@
],
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1"
"MOZILLA_OFFICIAL": "1"
},
"b2g_manifest": "inari.xml",
"b2g_manifest_branch": "master",

View File

@ -20,8 +20,7 @@
],
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1"
"MOZILLA_OFFICIAL": "1"
},
"b2g_manifest": "leo.xml",
"b2g_manifest_branch": "master",

View File

@ -20,8 +20,7 @@
],
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1"
"MOZILLA_OFFICIAL": "1"
},
"b2g_manifest": "nexus-4.xml",
"b2g_manifest_branch": "master",

View File

@ -22,8 +22,7 @@
],
"env": {
"VARIANT": "user",
"MOZILLA_OFFICIAL": "1",
"B2GUPDATER": "1"
"MOZILLA_OFFICIAL": "1"
},
"gecko_l10n_root": "http://hg.mozilla.org/l10n-central",
"gaia": {

View File

@ -129,8 +129,9 @@ pref("app.update.cert.maxErrors", 5);
// the |app.update.url.override| preference should ONLY be used for testing.
// IMPORTANT! metro.js should also be updated for updates to certs.X.issuerName
// Nightly builds have switched over to aus4.mozilla.org, but we don't want anything else to yet.
#ifdef NIGHTLY_BUILD
// Non-release builds (Nightly, Aurora, etc.) have been switched over to aus4.mozilla.org.
// This condition protects us against accidentally using it for release builds.
#ifndef RELEASE_BUILD
pref("app.update.certs.1.issuerName", "CN=DigiCert Secure Server CA,O=DigiCert Inc,C=US");
pref("app.update.certs.1.commonName", "aus4.mozilla.org");
@ -172,7 +173,7 @@ pref("app.update.silent", false);
pref("app.update.staging.enabled", true);
// Update service URL:
#ifdef NIGHTLY_BUILD
#ifndef RELEASE_BUILD
pref("app.update.url", "https://aus4.mozilla.org/update/3/%PRODUCT%/%VERSION%/%BUILD_ID%/%BUILD_TARGET%/%LOCALE%/%CHANNEL%/%OS_VERSION%/%DISTRIBUTION%/%DISTRIBUTION_VERSION%/update.xml");
#else
pref("app.update.url", "https://aus3.mozilla.org/update/3/%PRODUCT%/%VERSION%/%BUILD_ID%/%BUILD_TARGET%/%LOCALE%/%CHANNEL%/%OS_VERSION%/%DISTRIBUTION%/%DISTRIBUTION_VERSION%/update.xml");
@ -232,6 +233,12 @@ pref("xpinstall.whitelist.add.180", "marketplace.firefox.com");
pref("lightweightThemes.update.enabled", true);
// UI tour experience.
pref("browser.uitour.enabled", true);
pref("browser.uitour.themeOrigin", "https://addons.mozilla.org/%LOCALE%/firefox/themes/");
pref("browser.uitour.pinnedTabUrl", "https://support.mozilla.org/%LOCALE%/kb/pinned-tabs-keep-favorite-websites-open");
pref("browser.uitour.whitelist.add.260", "www.mozilla.org,support.mozilla.org");
pref("keyword.enabled", true);
pref("general.useragent.locale", "@AB_CD@");
@ -659,6 +666,8 @@ pref("plugins.update.notifyUser", false);
pref("plugins.click_to_play", true);
pref("plugins.clickToActivateInfo.url", "https://support.mozilla.org/1/firefox/%VERSION%/%OS%/%LOCALE%/clicktoplay");
// let all plugins except Flash default to click-to-play
pref("plugin.default.state", 1);
pref("plugin.state.flash", 2);

View File

@ -704,6 +704,9 @@ var gPluginHandler = {
else if (pluginInfo.blocklistState != Ci.nsIBlocklistService.STATE_NOT_BLOCKED) {
url = Services.blocklist.getPluginBlocklistURL(pluginInfo.pluginTag);
}
else {
url = Services.urlFormatter.formatURLPref("plugins.clickToActivateInfo.url");
}
pluginInfo.detailsLink = url;
centerActions.push(pluginInfo);

View File

@ -778,27 +778,6 @@ var gBrowserInit = {
window.QueryInterface(Ci.nsIDOMChromeWindow).browserDOMWindow =
new nsBrowserAccess();
// Manually hook up session and global history for the first browser
// so that we don't have to load global history before bringing up a
// window.
// Wire up session and global history before any possible
// progress notifications for back/forward button updating
gBrowser.webNavigation.sessionHistory = Cc["@mozilla.org/browser/shistory;1"].
createInstance(Ci.nsISHistory);
Services.obs.addObserver(gBrowser.browsers[0], "browser:purge-session-history", false);
// remove the disablehistory attribute so the browser cleans up, as
// though it had done this work itself
gBrowser.browsers[0].removeAttribute("disablehistory");
// enable global history
try {
if (!gMultiProcessBrowser)
gBrowser.docShell.useGlobalHistory = true;
} catch(ex) {
Cu.reportError("Places database may be locked: " + ex);
}
// hook up UI through progress listener
gBrowser.addProgressListener(window.XULBrowserWindow);
gBrowser.addTabsProgressListener(window.TabsProgressListener);

View File

@ -22,6 +22,7 @@
<window id="main-window"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns:html="http://www.w3.org/1999/xhtml"
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
onload="gBrowserInit.onLoad()" onunload="gBrowserInit.onUnload()" onclose="return WindowIsClosing();"
title="&mainWindow.title;@PRE_RELEASE_SUFFIX@"
@ -183,6 +184,22 @@
</hbox>
</panel>
<!-- UI tour experience -->
<panel id="UITourTooltip"
type="arrow"
hidden="true"
consumeoutsideclicks="false"
noautofocus="true"
align="start"
orient="vertical"
role="alert">
<label id="UITourTooltipTitle" flex="1"/>
<description id="UITourTooltipDescription" flex="1"/>
</panel>
<html:div id="UITourHighlightContainer" style="position:relative">
<html:div id="UITourHighlight"></html:div>
</html:div>
<panel id="socialActivatedNotification"
type="arrow"
hidden="true"
@ -1028,7 +1045,7 @@
<splitter id="sidebar-splitter" class="chromeclass-extrachrome sidebar-splitter" hidden="true"/>
<vbox id="appcontent" flex="1">
<tabbrowser id="content" disablehistory="true"
<tabbrowser id="content"
flex="1" contenttooltip="aHTMLTooltip"
tabcontainer="tabbrowser-tabs"
contentcontextmenu="contentAreaContextMenu"

View File

@ -15,6 +15,8 @@ XPCOMUtils.defineLazyModuleGetter(this,
"InsecurePasswordUtils", "resource://gre/modules/InsecurePasswordUtils.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "PrivateBrowsingUtils",
"resource://gre/modules/PrivateBrowsingUtils.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "UITour",
"resource:///modules/UITour.jsm");
// Creates a new nsIURI object.
function makeURI(uri, originCharset, baseURI) {
@ -49,6 +51,15 @@ if (Services.prefs.getBoolPref("browser.tabs.remote")) {
addEventListener("blur", function(event) {
LoginManagerContent.onUsernameInput(event);
});
addEventListener("mozUITour", function(event) {
if (!Services.prefs.getBoolPref("browser.uitour.enabled"))
return;
let handled = UITour.onPageEvent(event);
if (handled)
addEventListener("pagehide", UITour);
}, false, true);
}
let AboutHomeListener = {

View File

@ -34,7 +34,7 @@
<xul:hbox flex="1" class="browserSidebarContainer">
<xul:vbox flex="1" class="browserContainer">
<xul:stack flex="1" class="browserStack" anonid="browserStack">
<xul:browser anonid="initialBrowser" type="content-primary" message="true" disablehistory="true"
<xul:browser anonid="initialBrowser" type="content-primary" message="true"
xbl:inherits="tooltip=contenttooltip,contextmenu=contentcontextmenu,autocompletepopup,selectpopup"/>
</xul:stack>
</xul:vbox>

View File

@ -4,4 +4,6 @@
# 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/.
TEST_DIRS += ['test']
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini',
]

View File

@ -4,8 +4,6 @@
# 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/.
TEST_DIRS += ['tests']
MODULE = 'browserdir'
EXPORTS.mozilla.browser += [
@ -18,3 +16,6 @@ CPP_SOURCES += [
LIBRARY_NAME = 'browserdir_s'
XPCSHELL_TESTS_MANIFESTS += [
'tests/unit/xpcshell.ini',
]

View File

@ -1,9 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
MODULE = 'test_browserdir'
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']

View File

@ -5,4 +5,11 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['src']
TEST_DIRS += ['test']
XPCSHELL_TESTS_MANIFESTS += [
'test/unit/xpcshell.ini',
]
BROWSER_CHROME_MANIFESTS += [
'test/browser/browser.ini',
]

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -1,9 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
DIRS += ['browser']
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']

View File

@ -5,4 +5,15 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['public', 'src']
TEST_DIRS += ['test']
XPCSHELL_TESTS_MANIFESTS += [
'test/unit/xpcshell.ini',
]
MOCHITEST_CHROME_MANIFESTS += [
'test/chrome/chrome.ini',
]
MOCHITEST_MANIFESTS += [
'test/mochitest.ini'
]

View File

@ -1,10 +0,0 @@
#
# 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/.
# sample_feed.atom was copied from toolkit/components/places/tests/chrome
MOCHITEST_FILES = \
sample_feed.atom \
$(NULL)

View File

@ -1,4 +1,5 @@
[DEFAULT]
support-files = sample_feed.atom
[test_423060.xul]
[test_bug368464.html]

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
MOCHITEST_CHROME_MANIFESTS += ['chrome.ini']

View File

@ -1,14 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
DIRS += ['chrome']
MODULE = 'test_browser_feeds'
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']
MOCHITEST_MANIFESTS += ['mochitest.ini']

View File

@ -5,4 +5,7 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['public', 'src']
TEST_DIRS += ['tests']
XPCSHELL_TESTS_MANIFESTS += [
'tests/unit/xpcshell.ini',
]

View File

@ -1,7 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']

View File

@ -21,10 +21,6 @@ PARALLEL_DIRS += [
'migration',
]
if CONFIG['MOZ_SAFE_BROWSING']:
PARALLEL_DIRS += ['safebrowsing']
TEST_DIRS += ['test']
DIRS += ['build']
XPIDL_SOURCES += [
@ -48,3 +44,10 @@ EXTRA_JS_MODULES += [
'distribution.js',
]
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini'
]
if CONFIG['MOZ_SAFE_BROWSING']:
BROWSER_CHROME_MANIFESTS += ['safebrowsing/content/test/browser.ini']

View File

@ -472,6 +472,7 @@ BrowserGlue.prototype = {
ShumwayUtils.init();
webrtcUI.init();
AboutHome.init();
SessionStore.init();
if (Services.prefs.getBoolPref("browser.tabs.remote"))
ContentClick.init();
@ -612,7 +613,6 @@ BrowserGlue.prototype = {
}
#endif
SessionStore.init(aWindow);
this._trackSlowStartup();
// Offer to reset a user's profile if it hasn't been used for 60 days.

View File

@ -5,5 +5,15 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['src']
TEST_DIRS += ['tests']
XPCSHELL_TESTS_MANIFESTS += [
'tests/unit/xpcshell.ini',
]
MOCHITEST_CHROME_MANIFESTS += [
'tests/chrome/chrome.ini'
]
BROWSER_CHROME_MANIFESTS += [
'tests/browser/browser.ini',
]

View File

@ -1,38 +0,0 @@
# 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/.
MOCHITEST_BROWSER_FILES = \
head.js \
browser_0_library_left_pane_migration.js \
browser_library_left_pane_fixnames.js \
browser_425884.js \
browser_475045.js \
browser_423515.js \
browser_410196_paste_into_tags.js \
browser_sort_in_library.js \
browser_library_open_leak.js \
browser_library_panel_leak.js \
browser_library_search.js \
browser_history_sidebar_search.js \
browser_bookmarksProperties.js \
$(filter disabled-for-very-frequent-oranges--bug-551540, browser_forgetthissite_single.js) \
browser_library_left_pane_commands.js \
browser_drag_bookmarks_on_toolbar.js \
browser_library_middleclick.js \
browser_library_views_liveupdate.js \
browser_views_liveupdate.js \
$(filter temporarily-disabled-for-breaking-the-treeview--bug-658744, browser_sidebarpanels_click.js) \
sidebarpanels_click_test_page.html \
browser_library_infoBox.js \
browser_markPageAsFollowedLink.js \
framedPage.html \
frameLeft.html \
frameRight.html \
browser_toolbar_migration.js \
browser_library_batch_delete.js \
browser_555547.js \
browser_416459_cut.js \
browser_library_downloads.js \
browser_library_left_pane_select_hierarchy.js \
$(NULL)

View File

@ -0,0 +1,47 @@
# 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/.
[DEFAULT]
support-files =
head.js
framedPage.html
frameLeft.html
frameRight.html
sidebarpanels_click_test_page.html
[browser_0_library_left_pane_migration.js]
[browser_library_left_pane_fixnames.js]
[browser_425884.js]
[browser_475045.js]
[browser_423515.js]
[browser_410196_paste_into_tags.js]
[browser_sort_in_library.js]
[browser_library_open_leak.js]
[browser_library_panel_leak.js]
[browser_library_search.js]
[browser_history_sidebar_search.js]
[browser_bookmarksProperties.js]
[browser_forgetthissite_single.js]
# disabled for very frequent oranges - bug 551540
skip-if = true
[browser_library_left_pane_commands.js]
[browser_drag_bookmarks_on_toolbar.js]
[browser_library_middleclick.js]
[browser_library_views_liveupdate.js]
[browser_views_liveupdate.js]
[browser_sidebarpanels_click.js]
# temporarily disabled for breaking the treeview - bug 658744
skip-if = true
[browser_library_infoBox.js]
[browser_markPageAsFollowedLink.js]
[browser_toolbar_migration.js]
[browser_library_batch_delete.js]
[browser_555547.js]
[browser_416459_cut.js]
[browser_library_downloads.js]
[browser_library_left_pane_select_hierarchy.js]

View File

@ -1,6 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
MOCHITEST_CHROME_MANIFESTS += ['chrome.ini']

View File

@ -1,11 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
DIRS += ['browser', 'chrome']
MODULE = 'test_browser_places'
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']

View File

@ -4,4 +4,3 @@
# 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/.
TEST_DIRS += ['tests']

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -5,4 +5,8 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
PARALLEL_DIRS += ['in-content']
TEST_DIRS += ['tests']
BROWSER_CHROME_MANIFESTS += [
'in-content/tests/browser.ini',
'tests/browser.ini',
]

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -4,7 +4,6 @@
# 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/.
TEST_DIRS += ['test']
MODULE = 'privatebrowsing'
BROWSER_CHROME_MANIFESTS += [
'test/browser/browser.ini',
]

View File

@ -1,10 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
MODULE = 'test_privatebrowsing'
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -1,10 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
DIRS += ['browser']
MODULE = 'test_privatebrowsing'

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
TEST_DIRS += ['content/test']

View File

@ -4,4 +4,6 @@
# 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/.
TEST_DIRS += ['test']
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini',
]

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -5,7 +5,6 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['src']
TEST_DIRS += ['test']
XPIDL_SOURCES += [
'nsISessionStartup.idl',
@ -14,3 +13,10 @@ XPIDL_SOURCES += [
MODULE = 'sessionstore'
XPCSHELL_TESTS_MANIFESTS += [
'test/unit/xpcshell.ini',
]
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini',
]

View File

@ -156,8 +156,8 @@ this.SessionStore = {
SessionStoreInternal.canRestoreLastSession = val;
},
init: function ss_init(aWindow) {
SessionStoreInternal.init(aWindow);
init: function ss_init() {
SessionStoreInternal.init();
},
getBrowserState: function ss_getBrowserState() {
@ -368,15 +368,11 @@ let SessionStoreInternal = {
/**
* Initialize the sessionstore service.
*/
init: function (aWindow) {
init: function () {
if (this._initialized) {
throw new Error("SessionStore.init() must only be called once!");
}
if (!aWindow) {
throw new Error("SessionStore.init() must be called with a valid window.");
}
this._disabledForMultiProcess = Services.prefs.getBoolPref("browser.tabs.remote");
if (this._disabledForMultiProcess) {
this._deferredInitialized.resolve();
@ -390,20 +386,6 @@ let SessionStoreInternal = {
this._initPrefs();
this._initialized = true;
// Wait until nsISessionStartup has finished reading the session data.
gSessionStartup.onceInitialized.then(() => {
// Parse session data and start restoring.
let initialState = this.initSession();
// Start tracking the given (initial) browser window.
if (!aWindow.closed) {
this.onLoad(aWindow, initialState);
}
// Let everyone know we're done.
this._deferredInitialized.resolve();
}, Cu.reportError);
},
initSession: function ssi_initSession() {
@ -489,7 +471,6 @@ let SessionStoreInternal = {
this._prefBranch.setBoolPref("sessionstore.resume_session_once", false);
this._performUpgradeBackup();
this._sessionInitialized = true;
return state;
},
@ -876,7 +857,34 @@ let SessionStoreInternal = {
onOpen: function ssi_onOpen(aWindow) {
let onload = () => {
aWindow.removeEventListener("load", onload);
this.onLoad(aWindow);
if (this._sessionInitialized) {
this.onLoad(aWindow);
return;
}
// We can't call this.onLoad since initialization
// hasn't completed, so we'll wait until it is done.
// Even if additional windows are opened and wait
// for initialization as well, the first opened
// window should execute first, and this.onLoad
// will be called with the initialState.
gSessionStartup.onceInitialized.then(() => {
if (aWindow.closed) {
return;
}
if (this._sessionInitialized) {
this.onLoad(aWindow);
} else {
let initialState = this.initSession();
this._sessionInitialized = true;
this.onLoad(aWindow, initialState);
// Let everyone know we're done.
this._deferredInitialized.resolve();
}
}, Cu.reportError);
};
aWindow.addEventListener("load", onload);
@ -1471,7 +1479,7 @@ let SessionStoreInternal = {
TabStateCache.delete(aTab);
this._setWindowStateBusy(window);
this.restoreHistoryPrecursor(window, [aTab], [tabState], 0, 0, 0);
this.restoreHistoryPrecursor(window, [aTab], [tabState], 0);
},
duplicateTab: function ssi_duplicateTab(aWindow, aTab, aDelta = 0) {
@ -1491,7 +1499,7 @@ let SessionStoreInternal = {
aWindow.gBrowser.addTab(null, {relatedToCurrent: true, ownerTab: aTab}) :
aWindow.gBrowser.addTab();
this.restoreHistoryPrecursor(aWindow, [newTab], [tabState], 0, 0, 0,
this.restoreHistoryPrecursor(aWindow, [newTab], [tabState], 0,
true /* Load this tab right away. */);
return newTab;
@ -1571,7 +1579,7 @@ let SessionStoreInternal = {
let tab = tabbrowser.addTab();
// restore tab content
this.restoreHistoryPrecursor(aWindow, [tab], [closedTabState], 1, 0, 0);
this.restoreHistoryPrecursor(aWindow, [tab], [closedTabState], 1);
// restore the tab's position
tabbrowser.moveTabTo(tab, closedTab.pos);
@ -2344,7 +2352,7 @@ let SessionStoreInternal = {
}
this.restoreHistoryPrecursor(aWindow, tabs, winData.tabs,
(overwriteTabs ? (parseInt(winData.selected) || 1) : 0), 0, 0);
(overwriteTabs ? (parseInt(winData.selected) || 1) : 0));
if (aState.scratchpads) {
ScratchpadManager.restoreSession(aState.scratchpads);
@ -2448,40 +2456,17 @@ let SessionStoreInternal = {
* Array of tab data
* @param aSelectTab
* Index of selected tab
* @param aIx
* Index of the next tab to check readyness for
* @param aCount
* Counter for number of times delaying b/c browser or history aren't ready
* @param aRestoreImmediately
* Flag to indicate whether the given set of tabs aTabs should be
* restored/loaded immediately even if restore_on_demand = true
*/
restoreHistoryPrecursor:
function ssi_restoreHistoryPrecursor(aWindow, aTabs, aTabData, aSelectTab,
aIx, aCount, aRestoreImmediately = false) {
aRestoreImmediately = false)
{
var tabbrowser = aWindow.gBrowser;
// make sure that all browsers and their histories are available
// - if one's not, resume this check in 100ms (repeat at most 10 times)
for (var t = aIx; t < aTabs.length; t++) {
try {
if (!tabbrowser.getBrowserForTab(aTabs[t]).webNavigation.sessionHistory) {
throw new Error();
}
}
catch (ex) { // in case browser or history aren't ready yet
if (aCount < 10) {
var restoreHistoryFunc = function(self) {
self.restoreHistoryPrecursor(aWindow, aTabs, aTabData, aSelectTab,
aIx, aCount + 1, aRestoreImmediately);
};
aWindow.setTimeout(restoreHistoryFunc, 100, this);
return;
}
}
}
if (!this._isWindowLoaded(aWindow)) {
// from now on, the data will come from the actual window
delete this._statesToRestore[aWindow.__SS_restoreID];
@ -2507,7 +2492,7 @@ let SessionStoreInternal = {
return;
}
// Sets the tabs restoring order.
// Sets the tabs restoring order.
[aTabs, aTabData] =
this._setTabsRestoringOrder(tabbrowser, aTabs, aTabData, aSelectTab);
@ -2515,7 +2500,7 @@ let SessionStoreInternal = {
// and show/hide tabs as necessary. We'll also set the labels, user typed
// value, and attach a copy of the tab's data in case we close it before
// it's been restored.
for (t = 0; t < aTabs.length; t++) {
for (let t = 0; t < aTabs.length; t++) {
let tab = aTabs[t];
let browser = tabbrowser.getBrowserForTab(tab);
let tabData = aTabData[t];
@ -2587,14 +2572,14 @@ let SessionStoreInternal = {
// helper hashes for ensuring unique frame IDs and unique document
// identifiers.
var idMap = { used: {} };
var docIdentMap = {};
let idMap = { used: {} };
let docIdentMap = {};
this.restoreHistory(aWindow, aTabs, aTabData, idMap, docIdentMap,
aRestoreImmediately);
},
/**
* Restore history for a window
* Restore history for a list of tabs.
* @param aWindow
* Window reference
* @param aTabs

View File

@ -227,6 +227,14 @@ let SessionFileInternal = {
return Promise.reject(new Error("_SessionFile is closed"));
}
let refObj = {};
let isFinalWrite = false;
if (Services.startup.shuttingDown) {
// If shutdown has started, we will want to stop receiving
// write instructions.
isFinalWrite = this._isClosed = true;
}
return this._latestWrite = TaskUtils.spawn(function task() {
TelemetryStopwatch.start("FX_SESSION_RESTORE_WRITE_FILE_LONGEST_OP_MS", refObj);
@ -243,15 +251,10 @@ let SessionFileInternal = {
Cu.reportError("Could not write session state file " + this.path
+ ": " + ex);
}
// At this stage, we are done writing. If shutdown has started,
// we will want to stop receiving write instructions.
if (Services.startup.shuttingDown) {
this._isClosed = true;
if (isFinalWrite) {
Services.obs.notifyObservers(null, "sessionstore-final-state-write-complete", "");
}
// In rare cases, we may already have other writes pending,
// which we need to flush before shutdown proceeds. AsyncShutdown
// uses _latestWrite to determine what needs to be flushed during
// shutdown.
}.bind(this));
},

View File

@ -1,165 +0,0 @@
# 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/.
# browser_506482.js is disabled because of frequent failures (bug 538672)
# browser_526613.js is disabled because of frequent failures (bug 534489)
# browser_589246.js is disabled for leaking browser windows (bug 752467)
# browser_580512.js is disabled for leaking browser windows (bug 752467)
MOCHITEST_BROWSER_FILES = \
head.js \
browser_attributes.js \
browser_capabilities.js \
browser_dying_cache.js \
browser_form_restore_events.js \
browser_form_restore_events_sample.html \
browser_formdata_format.js \
browser_formdata_format_sample.html \
browser_input.js \
browser_input_sample.html \
browser_pageshow.js \
browser_sessionStorage.js \
browser_tabStateCache.js \
browser_upgrade_backup.js \
browser_windowRestore_perwindowpb.js \
browser_248970_b_perwindowpb.js \
browser_248970_b_sample.html \
browser_339445.js \
browser_339445_sample.html \
browser_345898.js \
browser_346337.js \
browser_346337_sample.html \
browser_350525.js \
browser_354894_perwindowpb.js \
browser_367052.js \
browser_393716.js \
browser_394759_basic.js \
browser_394759_behavior.js \
browser_394759_perwindowpb.js \
browser_394759_purge.js \
browser_408470.js \
browser_408470_sample.html \
browser_423132.js \
browser_423132_sample.html \
browser_447951.js \
browser_447951_sample.html \
browser_448741.js \
browser_454908.js \
browser_454908_sample.html \
browser_456342.js \
browser_456342_sample.xhtml \
browser_461634.js \
browser_463205.js \
browser_463205_helper.html \
browser_463205_sample.html \
browser_463206.js \
browser_463206_sample.html \
browser_464199.js \
browser_465215.js \
browser_465223.js \
browser_466937.js \
browser_466937_sample.html \
browser_467409-backslashplosion.js \
browser_477657.js \
browser_480148.js \
browser_480893.js \
browser_483330.js \
browser_485482.js \
browser_485482_sample.html \
browser_485563.js \
browser_490040.js \
browser_491168.js \
browser_491577.js \
browser_495495.js \
browser_500328.js \
browser_514751.js \
browser_522375.js \
browser_522545.js \
browser_524745.js \
browser_528776.js \
browser_579868.js \
browser_579879.js \
browser_581593.js \
browser_581937.js \
browser_586147.js \
browser_586068-apptabs.js \
browser_586068-apptabs_ondemand.js \
browser_586068-browser_state_interrupted.js \
browser_586068-cascade.js \
browser_586068-multi_window.js \
browser_586068-reload.js \
browser_586068-select.js \
browser_586068-window_state.js \
browser_586068-window_state_override.js \
browser_588426.js \
browser_590268.js \
browser_590563.js \
browser_595601-restore_hidden.js \
browser_597315.js \
browser_597315_index.html \
browser_597315_a.html \
browser_597315_b.html \
browser_597315_c.html \
browser_597315_c1.html \
browser_597315_c2.html \
browser_599909.js \
browser_600545.js \
browser_601955.js \
browser_607016.js \
browser_615394-SSWindowState_events.js \
browser_618151.js \
browser_623779.js \
browser_624727.js \
browser_625257.js \
browser_628270.js \
browser_635418.js \
browser_636279.js \
browser_637020.js \
browser_637020_slow.sjs \
browser_644409-scratchpads.js \
browser_645428.js \
browser_659591.js \
browser_662743.js \
browser_662743_sample.html \
browser_662812.js \
browser_665702-state_session.js \
browser_682507.js \
browser_687710.js \
browser_687710_2.js \
browser_694378.js \
browser_701377.js \
browser_705597.js \
browser_707862.js \
browser_739531.js \
browser_739531_sample.html \
browser_739805.js \
browser_819510_perwindowpb.js \
browser_833286_atomic_backup.js \
browser_916390_form_data_loss.js \
browser_916390_sample.html \
$(filter disabled-for-intermittent-failures--bug-766044, browser_459906_empty.html) \
$(filter disabled-for-intermittent-failures--bug-766044, browser_459906_sample.html) \
$(filter disabled-for-intermittent-failures--bug-765389, browser_461743_sample.html) \
$(NULL)
# Disabled on Windows for frequent intermittent failures
ifneq ($(OS_ARCH), WINNT)
MOCHITEST_FILES += \
browser_464620_a.js \
browser_464620_a.html \
browser_464620_b.js \
browser_464620_b.html \
browser_464620_xd.html \
$(NULL)
else
$(filter disabled-for-intermittent-failures-on-windows--bug-552424, browser_464620_a.js)
$(filter disabled-for-intermittent-failures-on-windows--bug-552424, browser_464620_b.js)
endif
ifneq ($(OS_ARCH),Darwin)
MOCHITEST_BROWSER_FILES += \
browser_597071.js \
browser_625016.js \
$(NULL)
endif

View File

@ -0,0 +1,164 @@
# 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/.
# browser_506482.js is disabled because of frequent failures (bug 538672)
# browser_526613.js is disabled because of frequent failures (bug 534489)
# browser_589246.js is disabled for leaking browser windows (bug 752467)
# browser_580512.js is disabled for leaking browser windows (bug 752467)
[DEFAULT]
support-files =
head.js
browser_form_restore_events_sample.html
browser_formdata_format_sample.html
browser_input_sample.html
browser_248970_b_sample.html
browser_339445_sample.html
browser_346337_sample.html
browser_408470_sample.html
browser_423132_sample.html
browser_447951_sample.html
browser_454908_sample.html
browser_456342_sample.xhtml
browser_463205_helper.html
browser_463205_sample.html
browser_463206_sample.html
browser_466937_sample.html
browser_485482_sample.html
browser_597315_index.html
browser_597315_a.html
browser_597315_b.html
browser_597315_c.html
browser_597315_c1.html
browser_597315_c2.html
browser_662743_sample.html
browser_739531_sample.html
browser_916390_sample.html
#NB: the following are disabled on Windows:
browser_464620_a.html
browser_464620_b.html
browser_464620_xd.html
#disabled-for-intermittent-failures--bug-766044, browser_459906_empty.html
#disabled-for-intermittent-failures--bug-766044, browser_459906_sample.html
#disabled-for-intermittent-failures--bug-765389, browser_461743_sample.html
[browser_attributes.js]
[browser_capabilities.js]
[browser_dying_cache.js]
[browser_form_restore_events.js]
[browser_formdata_format.js]
[browser_input.js]
[browser_pageshow.js]
[browser_sessionStorage.js]
[browser_tabStateCache.js]
[browser_upgrade_backup.js]
[browser_windowRestore_perwindowpb.js]
[browser_248970_b_perwindowpb.js]
[browser_339445.js]
[browser_345898.js]
[browser_346337.js]
[browser_350525.js]
[browser_354894_perwindowpb.js]
[browser_367052.js]
[browser_393716.js]
[browser_394759_basic.js]
[browser_394759_behavior.js]
[browser_394759_perwindowpb.js]
[browser_394759_purge.js]
[browser_408470.js]
[browser_423132.js]
[browser_447951.js]
[browser_448741.js]
[browser_454908.js]
[browser_456342.js]
[browser_461634.js]
[browser_463205.js]
[browser_463206.js]
[browser_464199.js]
[browser_465215.js]
[browser_465223.js]
[browser_466937.js]
[browser_467409-backslashplosion.js]
[browser_477657.js]
[browser_480148.js]
[browser_480893.js]
[browser_483330.js]
[browser_485482.js]
[browser_485563.js]
[browser_490040.js]
[browser_491168.js]
[browser_491577.js]
[browser_495495.js]
[browser_500328.js]
[browser_514751.js]
[browser_522375.js]
[browser_522545.js]
[browser_524745.js]
[browser_528776.js]
[browser_579868.js]
[browser_579879.js]
[browser_581593.js]
[browser_581937.js]
[browser_586147.js]
[browser_586068-apptabs.js]
[browser_586068-apptabs_ondemand.js]
[browser_586068-browser_state_interrupted.js]
[browser_586068-cascade.js]
[browser_586068-multi_window.js]
[browser_586068-reload.js]
[browser_586068-select.js]
[browser_586068-window_state.js]
[browser_586068-window_state_override.js]
[browser_588426.js]
[browser_590268.js]
[browser_590563.js]
[browser_595601-restore_hidden.js]
[browser_597315.js]
[browser_599909.js]
[browser_600545.js]
[browser_601955.js]
[browser_607016.js]
[browser_615394-SSWindowState_events.js]
[browser_618151.js]
[browser_623779.js]
[browser_624727.js]
[browser_625257.js]
[browser_628270.js]
[browser_635418.js]
[browser_636279.js]
[browser_637020.js]
[browser_637020_slow.sjs]
[browser_644409-scratchpads.js]
[browser_645428.js]
[browser_659591.js]
[browser_662743.js]
[browser_662812.js]
[browser_665702-state_session.js]
[browser_682507.js]
[browser_687710.js]
[browser_687710_2.js]
[browser_694378.js]
[browser_701377.js]
[browser_705597.js]
[browser_707862.js]
[browser_739531.js]
[browser_739805.js]
[browser_819510_perwindowpb.js]
[browser_833286_atomic_backup.js]
[browser_916390_form_data_loss.js]
# Disabled on Windows for frequent intermittent failures
[browser_464620_a.js]
skip-if = os == "win"
[browser_464620_b.js]
skip-if = os == "win"
# Disabled on OS X:
[browser_597071.js]
skip-if = os == "mac"
[browser_625016.js]
skip-if = os == "mac"

View File

@ -1,7 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']

View File

@ -5,4 +5,11 @@
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
DIRS += ['public', 'src']
TEST_DIRS += ['test']
XPCSHELL_TESTS_MANIFESTS += [
'test/unit/xpcshell.ini'
]
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini',
]

View File

@ -1,12 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
MODULE = 'test_browser_shell'
XPCSHELL_TESTS_MANIFESTS += ['unit/xpcshell.ini']
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -1,9 +0,0 @@
#
# 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 $(topsrcdir)/config/rules.mk
libs::
$(NSINSTALL) $(srcdir)/modules/* $(FINAL_TARGET)/modules/tabview

View File

@ -4,4 +4,9 @@
# 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/.
TEST_DIRS += ['test']
EXTRA_JS_MODULES = ['modules/utils.jsm']
JS_MODULES_PATH = 'modules/tabview'
BROWSER_CHROME_MANIFESTS += [
'test/browser.ini',
]

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -1,8 +0,0 @@
# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
# vim: set filetype=python:
# 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/.
BROWSER_CHROME_MANIFESTS += ['browser.ini']

View File

@ -258,6 +258,10 @@ WebappsStore.prototype = {
proxifiedApp.iconURL = res.url;
}
});
// This app may have been running while being installed, so check the list
// of running apps again to get the right answer.
this._getRunningApps();
});
},

View File

@ -45,6 +45,6 @@
<section id="connecting">
<p><img src="chrome://browser/skin/tabbrowser/loading.png"></img> &connecting;</p>
</section>
<footer>&help2;</footer>
<footer>&remoteHelp;<a target='_' href='https://developer.mozilla.org/docs/Tools/Remote_Debugging'>&remoteDocumentation;</a>&remoteHelpSuffix;</footer>
</body>
</html>

View File

@ -1537,6 +1537,7 @@ NetworkDetailsView.prototype = {
}));
this._json = new VariablesView($("#response-content-json"),
Heritage.extend(GENERIC_VARIABLES_VIEW_SETTINGS, {
onlyEnumVisible: true,
searchPlaceholder: L10N.getStr("jsonFilterText")
}));
VariablesViewController.attach(this._json);
@ -1874,7 +1875,7 @@ NetworkDetailsView.prototype = {
let sanitizedJSON = aString.replace(jsonpRegex, "");
let callbackPadding = aString.match(jsonpRegex);
// Make sure this is an valid JSON object first. If so, nicely display
// Make sure this is a valid JSON object first. If so, nicely display
// the parsing results in a variables view. Otherwise, simply show
// the contents as plain text.
try {

View File

@ -610,66 +610,23 @@ var Scratchpad = {
deferred.resolve(aError);
}
else {
let reject = aReason => deferred.reject(aReason);
let objectClient = new ObjectClient(this.debuggerClient, aError);
// Because properties on Error objects are lazily added, this roundabout
// way of getting all the properties is required, rather than simply
// using getPrototypeAndProperties. See bug 724768.
let names = ["message", "stack", "fileName", "lineNumber"];
let promises = names.map(aName => {
let deferred = promise.defer();
objectClient.getProperty(aName, aResponse => {
if (aResponse.error) {
deferred.reject(aResponse);
}
else {
deferred.resolve({
name: aName,
descriptor: aResponse.descriptor
});
}
});
return deferred.promise;
});
{
// We also need to use getPrototypeAndProperties to retrieve any
// safeGetterValues in case this is a DOM error.
let deferred = promise.defer();
objectClient.getPrototypeAndProperties(aResponse => {
if (aResponse.error) {
deferred.reject(aResponse);
}
else {
deferred.resolve(aResponse);
}
});
promises.push(deferred.promise);
}
promise.all(promises).then(aProperties => {
let error = {};
let safeGetters;
// Combine all the property descriptor/getter values into one object.
for (let property of aProperties) {
if (property.descriptor) {
error[property.name] = property.descriptor.value;
}
else if (property.safeGetterValues) {
safeGetters = property.safeGetterValues;
}
objectClient.getPrototypeAndProperties(aResponse => {
if (aResponse.error) {
deferred.reject(aResponse);
return;
}
if (safeGetters) {
for (let key of Object.keys(safeGetters)) {
if (!error.hasOwnProperty(key)) {
error[key] = safeGetters[key].getterValue;
}
}
let { ownProperties, safeGetterValues } = aResponse;
let error = Object.create(null);
// Combine all the property descriptor/getter values into one object.
for (let key of Object.keys(safeGetterValues)) {
error[key] = safeGetterValues[key].getterValue;
}
for (let key of Object.keys(ownProperties)) {
error[key] = ownProperties[key].value;
}
// Assemble the best possible stack we can given the properties we have.
@ -693,23 +650,23 @@ var Scratchpad = {
deferred.resolve(error.message + stack);
}
else {
objectClient.getDisplayString(aResult => {
if (aResult.error) {
deferred.reject(aResult);
objectClient.getDisplayString(aResponse => {
if (aResponse.error) {
deferred.reject(aResponse);
}
else if (aResult.displayString.type == "null") {
deferred.resolve(stack);
else if (typeof aResponse.displayString == "string") {
deferred.resolve(aResponse.displayString + stack);
}
else {
deferred.resolve(aResult.displayString + stack);
deferred.resolve(stack);
}
}, reject);
});
}
}, reject);
});
}
return deferred.promise.then(aMessage => {
console.log(aMessage);
console.error(aMessage);
this.writeAsComment("Exception: " + aMessage);
});
},

View File

@ -43,6 +43,7 @@ function testColorUtils() {
let color = new colorUtils.CssColor(authored);
// Check all values.
info("Checking values for " + authored);
is(color.name, name, "color.name === name");
is(color.hex, hex, "color.hex === hex");
is(color.hsl, hsl, "color.hsl === hsl");
@ -291,14 +292,18 @@ function getTestData() {
{authored: "whitesmoke", name: "whitesmoke", hex: "#F5F5F5", hsl: "hsl(0, 0%, 96%)", rgb: "rgb(245, 245, 245)"},
{authored: "yellow", name: "yellow", hex: "#FF0", hsl: "hsl(60, 100%, 50%)", rgb: "rgb(255, 255, 0)"},
{authored: "yellowgreen", name: "yellowgreen", hex: "#9ACD32", hsl: "hsl(79.742, 61%, 50%)", rgb: "rgb(154, 205, 50)"},
{authored: "transparent", name: "transparent", hex: "transparent", hsl: "transparent", rgb: "transparent"},
{authored: "rgba(0, 0, 0, 0)", name: "transparent", hex: "transparent", hsl: "transparent", rgb: "transparent"},
{authored: "hsla(0, 0%, 0%, 0)", name: "transparent", hex: "transparent", hsl: "transparent", rgb: "transparent"},
{authored: "rgba(0, 0, 0, 0)", name: "rgba(0, 0, 0, 0)", hex: "rgba(0, 0, 0, 0)", hsl: "hsla(0, 0%, 0%, 0)", rgb: "rgba(0, 0, 0, 0)"},
{authored: "hsla(0, 0%, 0%, 0)", name: "rgba(0, 0, 0, 0)", hex: "rgba(0, 0, 0, 0)", hsl: "hsla(0, 0%, 0%, 0)", rgb: "rgba(0, 0, 0, 0)"},
{authored: "rgba(50, 60, 70, 0.5)", name: "rgba(50, 60, 70, 0.5)", hex: "rgba(50, 60, 70, 0.5)", hsl: "hsla(210, 17%, 24%, 0.5)", rgb: "rgba(50, 60, 70, 0.5)"},
{authored: "rgba(0, 0, 0, 0.3)", name: "rgba(0, 0, 0, 0.3)", hex: "rgba(0, 0, 0, 0.3)", hsl: "hsla(0, 0%, 0%, 0.3)", rgb: "rgba(0, 0, 0, 0.3)"},
{authored: "rgba(255, 255, 255, 0.6)", name: "rgba(255, 255, 255, 0.6)", hex: "rgba(255, 255, 255, 0.6)", hsl: "hsla(0, 0%, 100%, 0.6)", rgb: "rgba(255, 255, 255, 0.6)"},
{authored: "rgba(127, 89, 45, 1)", name: "#7F592D", hex: "#7F592D", hsl: "hsl(32.195, 48%, 34%)", rgb: "rgb(127, 89, 45)"},
{authored: "hsla(19.304, 56%, 40%, 1)", name: "#9F512C", hex: "#9F512C", hsl: "hsl(19.304, 57%, 40%)", rgb: "rgb(159, 81, 44)"},
{authored: "invalidColor", name: "", hex: "", hsl: "", rgb: ""}
{authored: "currentcolor", name: "currentcolor", hex: "currentcolor", hsl: "currentcolor", rgb: "currentcolor"},
{authored: "inherit", name: "inherit", hex: "inherit", hsl: "inherit", rgb: "inherit"},
{authored: "initial", name: "initial", hex: "initial", hsl: "initial", rgb: "initial"},
{authored: "invalidColor", name: "", hex: "", hsl: "", rgb: ""},
{authored: "transparent", name: "transparent", hex: "transparent", hsl: "transparent", rgb: "transparent"},
{authored: "unset", name: "unset", hex: "unset", hsl: "unset", rgb: "unset"}
];
}

View File

@ -136,12 +136,11 @@ BreadcrumbsWidget.prototype = {
// Repeated calls to ensureElementIsVisible would interfere with each other
// and may sometimes result in incorrect scroll positions.
this.window.clearTimeout(this._ensureVisibleTimeout);
this._ensureVisibleTimeout = this.window.setTimeout(() => {
setNamedTimeout("breadcrumb-select", ENSURE_SELECTION_VISIBLE_DELAY, () => {
if (this._selectedItem) {
this._list.ensureElementIsVisible(this._selectedItem);
}
}, ENSURE_SELECTION_VISIBLE_DELAY);
});
},
/**
@ -172,8 +171,7 @@ BreadcrumbsWidget.prototype = {
document: null,
_parent: null,
_list: null,
_selectedItem: null,
_ensureVisibleTimeout: null
_selectedItem: null
};
/**

View File

@ -461,7 +461,7 @@ VariablesViewController.prototype = {
scope.expanded = true;
scope.locked = true;
let variable = scope.addItem();
let variable = scope.addItem("", { enumerable: true });
let expanded;
if (aOptions.objectActor) {

View File

@ -19,4 +19,11 @@
<!ENTITY errorTimeout "Error: connection timeout.">
<!ENTITY errorRefused "Error: connection refused.">
<!ENTITY errorUnexpected "Unexpected error.">
<!ENTITY help2 "Firefox Developer Tools can debug remote devices (Firefox for Android and Firefox OS, for example). Make sure that you have turned on the 'Remote debugging' option in the remote device. See the <a target='_' href='https://developer.mozilla.org/docs/Tools/Remote_Debugging'>documentation</a> for more.">
<!-- LOCALIZATION NOTE (remoteHelp, remoteDocumentation, remoteHelpSuffix):
these strings will be concatenated in a single label, remoteDocumentation will
be used as text for a link to MDN. -->
<!ENTITY remoteHelp "Firefox Developer Tools can debug remote devices (Firefox for Android and Firefox OS, for example). Make sure that you have turned on the 'Remote debugging' option in the remote device. For more, see the">
<!ENTITY remoteDocumentation "documentation">
<!ENTITY remoteHelpSuffix ".">

View File

@ -167,9 +167,12 @@ TopSitesView.prototype = Util.extend(Object.create(View.prototype), {
let filepath = PageThumbsStorage.getFilePathForURL(aSite.url);
if (yield OS.File.exists(filepath)) {
aSite.backgroundImage = 'url("'+PageThumbs.getThumbnailURL(aSite.url)+'")';
if ('backgroundImage' in aTileNode) {
// use the setter when available to update the backgroundImage value
if ('backgroundImage' in aTileNode &&
aTileNode.backgroundImage != aSite.backgroundImage) {
aTileNode.backgroundImage = aSite.backgroundImage;
} else {
// just update the attribute for when the node gets the binding applied
aTileNode.setAttribute("customImage", aSite.backgroundImage);
}
}

View File

@ -87,9 +87,9 @@ View.prototype = {
// get the rgb value that represents this color at given opacity over a white matte
let tintColor = ColorUtils.addRgbColors(matteColor, ColorUtils.createDecimalColorWord(r,g,b,alpha));
aItem.setAttribute("tintColor", ColorUtils.convertDecimalToRgbColor(tintColor));
if (aItem.refresh) {
aItem.refresh();
// when bound, use the setter to propogate the color change through the tile
if ('color' in aItem) {
aItem.color = background;
}
};
let failureAction = function() {};

View File

@ -449,7 +449,7 @@ pref("app.update.silent", true);
pref("app.update.staging.enabled", true);
// Update service URL:
#ifdef NIGHTLY_BUILD
#ifndef RELEASE_BUILD
pref("app.update.url", "https://aus4.mozilla.org/update/3/%PRODUCT%/%VERSION%/%BUILD_ID%/%BUILD_TARGET%/%LOCALE%/%CHANNEL%/%OS_VERSION%/%DISTRIBUTION%/%DISTRIBUTION_VERSION%/update.xml");
#else
pref("app.update.url", "https://aus3.mozilla.org/update/3/%PRODUCT%/%VERSION%/%BUILD_ID%/%BUILD_TARGET%/%LOCALE%/%CHANNEL%/%OS_VERSION%/%DISTRIBUTION%/%DISTRIBUTION_VERSION%/update.xml");
@ -522,8 +522,9 @@ pref("app.update.cert.maxErrors", 5);
// the |app.update.url.override| preference should ONLY be used for testing.
// IMPORTANT! firefox.js should also be updated for updates to certs.X.issuerName
// Nightly builds have switched over to aus4.mozilla.org, but we don't want anything else to yet.
#ifdef NIGHTLY_BUILD
// Non-release builds (Nightly, Aurora, etc.) have been switched over to aus4.mozilla.org.
// This condition protects us against accidentally using it for release builds.
#ifndef RELEASE_BUILD
pref("app.update.certs.1.issuerName", "CN=DigiCert Secure Server CA,O=DigiCert Inc,C=US");
pref("app.update.certs.1.commonName", "aus4.mozilla.org");
pref("app.update.certs.2.issuerName", "CN=Thawte SSL CA,O=\"Thawte, Inc.\",C=US");

426
browser/modules/UITour.jsm Normal file
View File

@ -0,0 +1,426 @@
// 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/.
this.EXPORTED_SYMBOLS = ["UITour"];
const {classes: Cc, interfaces: Ci, utils: Cu, results: Cr} = Components;
Cu.import("resource://gre/modules/Services.jsm");
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "LightweightThemeManager",
"resource://gre/modules/LightweightThemeManager.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "PermissionsUtils",
"resource://gre/modules/PermissionsUtils.jsm");
const UITOUR_PERMISSION = "uitour";
const PREF_PERM_BRANCH = "browser.uitour.";
this.UITour = {
originTabs: new WeakMap(),
pinnedTabs: new WeakMap(),
urlbarCapture: new WeakMap(),
highlightEffects: ["wobble", "zoom", "color"],
targets: new Map([
["backforward", "#unified-back-forward-button"],
["appmenu", "#appmenu-button"],
["home", "#home-button"],
["urlbar", "#urlbar"],
["bookmarks", "#bookmarks-menu-button"],
["search", "#searchbar"],
["searchprovider", function UITour_target_searchprovider(aDocument) {
let searchbar = aDocument.getElementById("searchbar");
return aDocument.getAnonymousElementByAttribute(searchbar,
"anonid",
"searchbar-engine-button");
}],
]),
onPageEvent: function(aEvent) {
let contentDocument = null;
if (aEvent.target instanceof Ci.nsIDOMHTMLDocument)
contentDocument = aEvent.target;
else if (aEvent.target instanceof Ci.nsIDOMHTMLElement)
contentDocument = aEvent.target.ownerDocument;
else
return false;
// Ignore events if they're not from a trusted origin.
if (!this.ensureTrustedOrigin(contentDocument))
return false;
if (typeof aEvent.detail != "object")
return false;
let action = aEvent.detail.action;
if (typeof action != "string" || !action)
return false;
let data = aEvent.detail.data;
if (typeof data != "object")
return false;
let window = this.getChromeWindow(contentDocument);
switch (action) {
case "showHighlight": {
let target = this.getTarget(window, data.target);
if (!target)
return false;
this.showHighlight(target);
break;
}
case "hideHighlight": {
this.hideHighlight(window);
break;
}
case "showInfo": {
let target = this.getTarget(window, data.target, true);
if (!target)
return false;
this.showInfo(target, data.title, data.text);
break;
}
case "hideInfo": {
this.hideInfo(window);
break;
}
case "previewTheme": {
this.previewTheme(data.theme);
break;
}
case "resetTheme": {
this.resetTheme();
break;
}
case "addPinnedTab": {
this.ensurePinnedTab(window, true);
break;
}
case "removePinnedTab": {
this.removePinnedTab(window);
break;
}
case "showMenu": {
this.showMenu(window, data.name);
break;
}
case "startUrlbarCapture": {
if (typeof data.text != "string" || !data.text ||
typeof data.url != "string" || !data.url) {
return false;
}
let uri = null;
try {
uri = Services.io.newURI(data.url, null, null);
} catch (e) {
return false;
}
let secman = Services.scriptSecurityManager;
let principal = contentDocument.nodePrincipal;
let flags = secman.DISALLOW_INHERIT_PRINCIPAL;
try {
secman.checkLoadURIWithPrincipal(principal, uri, flags);
} catch (e) {
return false;
}
this.startUrlbarCapture(window, data.text, data.url);
break;
}
case "endUrlbarCapture": {
this.endUrlbarCapture(window);
break;
}
}
let tab = window.gBrowser._getTabForContentWindow(contentDocument.defaultView);
if (!this.originTabs.has(window))
this.originTabs.set(window, new Set());
this.originTabs.get(window).add(tab);
tab.addEventListener("TabClose", this);
window.gBrowser.tabContainer.addEventListener("TabSelect", this);
window.addEventListener("SSWindowClosing", this);
return true;
},
handleEvent: function(aEvent) {
switch (aEvent.type) {
case "pagehide": {
let window = this.getChromeWindow(aEvent.target);
this.teardownTour(window);
break;
}
case "TabClose": {
let window = aEvent.target.ownerDocument.defaultView;
this.teardownTour(window);
break;
}
case "TabSelect": {
let window = aEvent.target.ownerDocument.defaultView;
let pinnedTab = this.pinnedTabs.get(window);
if (pinnedTab && pinnedTab.tab == window.gBrowser.selectedTab)
break;
let originTabs = this.originTabs.get(window);
if (originTabs && originTabs.has(window.gBrowser.selectedTab))
break;
this.teardownTour(window);
break;
}
case "SSWindowClosing": {
let window = aEvent.target;
this.teardownTour(window, true);
break;
}
case "input": {
if (aEvent.target.id == "urlbar") {
let window = aEvent.target.ownerDocument.defaultView;
this.handleUrlbarInput(window);
}
break;
}
}
},
teardownTour: function(aWindow, aWindowClosing = false) {
aWindow.gBrowser.tabContainer.removeEventListener("TabSelect", this);
aWindow.removeEventListener("SSWindowClosing", this);
let originTabs = this.originTabs.get(aWindow);
if (originTabs) {
for (let tab of originTabs)
tab.removeEventListener("TabClose", this);
}
this.originTabs.delete(aWindow);
if (!aWindowClosing) {
this.hideHighlight(aWindow);
this.hideInfo(aWindow);
}
this.endUrlbarCapture(aWindow);
this.removePinnedTab(aWindow);
this.resetTheme();
},
getChromeWindow: function(aContentDocument) {
return aContentDocument.defaultView
.window
.QueryInterface(Ci.nsIInterfaceRequestor)
.getInterface(Ci.nsIWebNavigation)
.QueryInterface(Ci.nsIDocShellTreeItem)
.rootTreeItem
.QueryInterface(Ci.nsIInterfaceRequestor)
.getInterface(Ci.nsIDOMWindow)
.wrappedJSObject;
},
importPermissions: function() {
try {
PermissionsUtils.importFromPrefs(PREF_PERM_BRANCH, UITOUR_PERMISSION);
} catch (e) {
Cu.reportError(e);
}
},
ensureTrustedOrigin: function(aDocument) {
if (aDocument.defaultView.top != aDocument.defaultView)
return false;
let uri = aDocument.documentURIObject;
if (uri.schemeIs("chrome"))
return true;
if (!uri.schemeIs("https"))
return false;
this.importPermissions();
let permission = Services.perms.testPermission(uri, UITOUR_PERMISSION);
return permission == Services.perms.ALLOW_ACTION;
},
getTarget: function(aWindow, aTargetName, aSticky = false) {
if (typeof aTargetName != "string" || !aTargetName)
return null;
if (aTargetName == "pinnedtab")
return this.ensurePinnedTab(aWindow, aSticky);
let targetQuery = this.targets.get(aTargetName);
if (!targetQuery)
return null;
if (typeof targetQuery == "function")
return targetQuery(aWindow.document);
return aWindow.document.querySelector(targetQuery);
},
previewTheme: function(aTheme) {
let origin = Services.prefs.getCharPref("browser.uitour.themeOrigin");
let data = LightweightThemeManager.parseTheme(aTheme, origin);
if (data)
LightweightThemeManager.previewTheme(data);
},
resetTheme: function() {
LightweightThemeManager.resetPreview();
},
ensurePinnedTab: function(aWindow, aSticky = false) {
let tabInfo = this.pinnedTabs.get(aWindow);
if (tabInfo) {
tabInfo.sticky = tabInfo.sticky || aSticky;
} else {
let url = Services.urlFormatter.formatURLPref("browser.uitour.pinnedTabUrl");
let tab = aWindow.gBrowser.addTab(url);
aWindow.gBrowser.pinTab(tab);
tab.addEventListener("TabClose", () => {
this.pinnedTabs.delete(aWindow);
});
tabInfo = {
tab: tab,
sticky: aSticky
};
this.pinnedTabs.set(aWindow, tabInfo);
}
return tabInfo.tab;
},
removePinnedTab: function(aWindow) {
let tabInfo = this.pinnedTabs.get(aWindow);
if (tabInfo)
aWindow.gBrowser.removeTab(tabInfo.tab);
},
showHighlight: function(aTarget) {
let highlighter = aTarget.ownerDocument.getElementById("UITourHighlight");
let randomEffect = Math.floor(Math.random() * this.highlightEffects.length);
if (randomEffect == this.highlightEffects.length)
randomEffect--; // On the order of 1 in 2^62 chance of this happening.
highlighter.setAttribute("active", this.highlightEffects[randomEffect]);
let targetRect = aTarget.getBoundingClientRect();
highlighter.style.height = targetRect.height + "px";
highlighter.style.width = targetRect.width + "px";
let highlighterRect = highlighter.getBoundingClientRect();
let top = targetRect.top + (targetRect.height / 2) - (highlighterRect.height / 2);
highlighter.style.top = top + "px";
let left = targetRect.left + (targetRect.width / 2) - (highlighterRect.width / 2);
highlighter.style.left = left + "px";
},
hideHighlight: function(aWindow) {
let tabData = this.pinnedTabs.get(aWindow);
if (tabData && !tabData.sticky)
this.removePinnedTab(aWindow);
let highlighter = aWindow.document.getElementById("UITourHighlight");
highlighter.removeAttribute("active");
},
showInfo: function(aAnchor, aTitle, aDescription) {
aAnchor.focus();
let document = aAnchor.ownerDocument;
let tooltip = document.getElementById("UITourTooltip");
let tooltipTitle = document.getElementById("UITourTooltipTitle");
let tooltipDesc = document.getElementById("UITourTooltipDescription");
tooltip.hidePopup();
tooltipTitle.textContent = aTitle;
tooltipDesc.textContent = aDescription;
let alignment = "bottomcenter topright";
let anchorRect = aAnchor.getBoundingClientRect();
tooltip.hidden = false;
tooltip.openPopup(aAnchor, alignment);
},
hideInfo: function(aWindow) {
let tooltip = aWindow.document.getElementById("UITourTooltip");
tooltip.hidePopup();
},
showMenu: function(aWindow, aMenuName) {
function openMenuButton(aId) {
let menuBtn = aWindow.document.getElementById(aId);
if (menuBtn && menuBtn.boxObject)
menuBtn.boxObject.QueryInterface(Ci.nsIMenuBoxObject).openMenu(true);
}
if (aMenuName == "appmenu")
openMenuButton("appmenu-button");
else if (aMenuName == "bookmarks")
openMenuButton("bookmarks-menu-button");
},
startUrlbarCapture: function(aWindow, aExpectedText, aUrl) {
let urlbar = aWindow.document.getElementById("urlbar");
this.urlbarCapture.set(aWindow, {
expected: aExpectedText.toLocaleLowerCase(),
url: aUrl
});
urlbar.addEventListener("input", this);
},
endUrlbarCapture: function(aWindow) {
let urlbar = aWindow.document.getElementById("urlbar");
urlbar.removeEventListener("input", this);
this.urlbarCapture.delete(aWindow);
},
handleUrlbarInput: function(aWindow) {
if (!this.urlbarCapture.has(aWindow))
return;
let urlbar = aWindow.document.getElementById("urlbar");
let {expected, url} = this.urlbarCapture.get(aWindow);
if (urlbar.value.toLocaleLowerCase().localeCompare(expected) != 0)
return;
urlbar.handleRevert();
let tab = aWindow.gBrowser.addTab(url, {
owner: aWindow.gBrowser.selectedTab,
relatedToCurrent: true
});
aWindow.gBrowser.selectedTab = tab;
},
};

View File

@ -15,6 +15,7 @@ EXTRA_JS_MODULES += [
'SitePermissions.jsm',
'Social.jsm',
'TabCrashReporter.jsm',
'UITour.jsm',
'offlineAppCache.jsm',
'openLocationLastURL.jsm',
'webappsUI.jsm',

View File

@ -1,3 +1,5 @@
[DEFAULT]
[browser_NetworkPrioritizer.js]
[browser_UITour.js]
support-files = uitour.*

View File

@ -0,0 +1,212 @@
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
let gTestTab;
let gContentAPI;
Components.utils.import("resource:///modules/UITour.jsm");
function is_hidden(element) {
var style = element.ownerDocument.defaultView.getComputedStyle(element, "");
if (style.display == "none")
return true;
if (style.visibility != "visible")
return true;
// Hiding a parent element will hide all its children
if (element.parentNode != element.ownerDocument)
return is_hidden(element.parentNode);
return false;
}
function is_element_visible(element, msg) {
isnot(element, null, "Element should not be null, when checking visibility");
ok(!is_hidden(element), msg);
}
function is_element_hidden(element, msg) {
isnot(element, null, "Element should not be null, when checking visibility");
ok(is_hidden(element), msg);
}
function loadTestPage(callback, untrustedHost = false) {
if (gTestTab)
gBrowser.removeTab(gTestTab);
let url = getRootDirectory(gTestPath) + "uitour.html";
if (untrustedHost)
url = url.replace("chrome://mochitests/content/", "http://example.com/");
gTestTab = gBrowser.addTab(url);
gBrowser.selectedTab = gTestTab;
gTestTab.linkedBrowser.addEventListener("load", function onLoad() {
gTestTab.linkedBrowser.removeEventListener("load", onLoad);
let contentWindow = Components.utils.waiveXrays(gTestTab.linkedBrowser.contentDocument.defaultView);
gContentAPI = contentWindow.Mozilla.UITour;
waitForFocus(callback, contentWindow);
}, true);
}
function test() {
Services.prefs.setBoolPref("browser.uitour.enabled", true);
waitForExplicitFinish();
registerCleanupFunction(function() {
delete window.UITour;
delete window.gContentAPI;
if (gTestTab)
gBrowser.removeTab(gTestTab);
delete window.gTestTab;
Services.prefs.clearUserPref("browser.uitour.enabled", true);
});
function done() {
if (gTestTab)
gBrowser.removeTab(gTestTab);
gTestTab = null;
let highlight = document.getElementById("UITourHighlight");
is_element_hidden(highlight, "Highlight should be hidden after UITour tab is closed");
let popup = document.getElementById("UITourTooltip");
isnot(["hidding","closed"].indexOf(popup.state), -1, "Popup should be closed/hidding after UITour tab is closed");
is(UITour.pinnedTabs.get(window), null, "Any pinned tab should be closed after UITour tab is closed");
executeSoon(nextTest);
}
function nextTest() {
if (tests.length == 0) {
finish();
return;
}
let test = tests.shift();
loadTestPage(function() {
test(done);
});
}
nextTest();
}
let tests = [
function test_disabled(done) {
Services.prefs.setBoolPref("browser.uitour.enabled", false);
let highlight = document.getElementById("UITourHighlight");
is_element_hidden(highlight, "Highlight should initially be hidden");
gContentAPI.showHighlight("urlbar");
is_element_hidden(highlight, "Highlight should not be shown when feature is disabled");
Services.prefs.setBoolPref("browser.uitour.enabled", true);
done();
},
function test_untrusted_host(done) {
loadTestPage(function() {
let highlight = document.getElementById("UITourHighlight");
is_element_hidden(highlight, "Highlight should initially be hidden");
gContentAPI.showHighlight("urlbar");
is_element_hidden(highlight, "Highlight should not be shown on a untrusted domain");
done();
}, true);
},
function test_highlight(done) {
let highlight = document.getElementById("UITourHighlight");
is_element_hidden(highlight, "Highlight should initially be hidden");
gContentAPI.showHighlight("urlbar");
is_element_visible(highlight, "Highlight should be shown after showHighlight()");
gContentAPI.hideHighlight();
is_element_hidden(highlight, "Highlight should be hidden after hideHighlight()");
gContentAPI.showHighlight("urlbar");
is_element_visible(highlight, "Highlight should be shown after showHighlight()");
gContentAPI.showHighlight("backforward");
is_element_visible(highlight, "Highlight should be shown after showHighlight()");
done();
},
function test_info_1(done) {
let popup = document.getElementById("UITourTooltip");
let title = document.getElementById("UITourTooltipTitle");
let desc = document.getElementById("UITourTooltipDescription");
popup.addEventListener("popupshown", function onPopupShown() {
popup.removeEventListener("popupshown", onPopupShown);
is(popup.popupBoxObject.anchorNode, document.getElementById("urlbar"), "Popup should be anchored to the urlbar");
is(title.textContent, "test title", "Popup should have correct title");
is(desc.textContent, "test text", "Popup should have correct description text");
popup.addEventListener("popuphidden", function onPopupHidden() {
popup.removeEventListener("popuphidden", onPopupHidden);
popup.addEventListener("popupshown", function onPopupShown() {
popup.removeEventListener("popupshown", onPopupShown);
done();
});
gContentAPI.showInfo("urlbar", "test title", "test text");
});
gContentAPI.hideInfo();
});
gContentAPI.showInfo("urlbar", "test title", "test text");
},
function test_info_2(done) {
let popup = document.getElementById("UITourTooltip");
let title = document.getElementById("UITourTooltipTitle");
let desc = document.getElementById("UITourTooltipDescription");
popup.addEventListener("popupshown", function onPopupShown() {
popup.removeEventListener("popupshown", onPopupShown);
is(popup.popupBoxObject.anchorNode, document.getElementById("urlbar"), "Popup should be anchored to the urlbar");
is(title.textContent, "urlbar title", "Popup should have correct title");
is(desc.textContent, "urlbar text", "Popup should have correct description text");
gContentAPI.showInfo("search", "search title", "search text");
executeSoon(function() {
is(popup.popupBoxObject.anchorNode, document.getElementById("searchbar"), "Popup should be anchored to the searchbar");
is(title.textContent, "search title", "Popup should have correct title");
is(desc.textContent, "search text", "Popup should have correct description text");
done();
});
});
gContentAPI.showInfo("urlbar", "urlbar title", "urlbar text");
},
function test_pinnedTab(done) {
is(UITour.pinnedTabs.get(window), null, "Should not already have a pinned tab");
gContentAPI.addPinnedTab();
let tabInfo = UITour.pinnedTabs.get(window);
isnot(tabInfo, null, "Should have recorded data about a pinned tab after addPinnedTab()");
isnot(tabInfo.tab, null, "Should have added a pinned tab after addPinnedTab()");
is(tabInfo.tab.pinned, true, "Tab should be marked as pinned");
let tab = tabInfo.tab;
gContentAPI.removePinnedTab();
isnot(gBrowser.tabs[0], tab, "First tab should not be the pinned tab");
let tabInfo = UITour.pinnedTabs.get(window);
is(tabInfo, null, "Should not have any data about the removed pinned tab after removePinnedTab()");
gContentAPI.addPinnedTab();
gContentAPI.addPinnedTab();
gContentAPI.addPinnedTab();
is(gBrowser.tabs[1].pinned, false, "After multiple calls of addPinnedTab, should still only have one pinned tab");
done();
},
];

View File

@ -0,0 +1,15 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>UITour test</title>
<script type="application/javascript" src="uitour.js">
</script>
</head>
<body>
<h1>UITour tests</h1>
<p>Because Firefox is...</p>
<p>Never gonna let you down</p>
<p>Never gonna give you up</p>
</body>
</html>

View File

@ -0,0 +1,115 @@
/* 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/. */
// Copied from the proposed JS library for Bedrock (ie, www.mozilla.org).
// create namespace
if (typeof Mozilla == 'undefined') {
var Mozilla = {};
}
(function($) {
'use strict';
// create namespace
if (typeof Mozilla.UITour == 'undefined') {
Mozilla.UITour = {};
}
var themeIntervalId = null;
function _stopCyclingThemes() {
if (themeIntervalId) {
clearInterval(themeIntervalId);
themeIntervalId = null;
}
}
function _sendEvent(action, data) {
var event = new CustomEvent('mozUITour', {
bubbles: true,
detail: {
action: action,
data: data || {}
}
});
console.log("Sending mozUITour event: ", event);
document.dispatchEvent(event);
}
Mozilla.UITour.DEFAULT_THEME_CYCLE_DELAY = 10 * 1000;
Mozilla.UITour.showHighlight = function(target) {
_sendEvent('showHighlight', {
target: target
});
};
Mozilla.UITour.hideHighlight = function() {
_sendEvent('hideHighlight');
};
Mozilla.UITour.showInfo = function(target, title, text) {
_sendEvent('showInfo', {
target: target,
title: title,
text: text
});
};
Mozilla.UITour.hideInfo = function() {
_sendEvent('hideInfo');
};
Mozilla.UITour.previewTheme = function(theme) {
_stopCyclingThemes();
_sendEvent('previewTheme', {
theme: JSON.stringify(theme)
});
};
Mozilla.UITour.resetTheme = function() {
_stopCyclingThemes();
_sendEvent('resetTheme');
};
Mozilla.UITour.cycleThemes = function(themes, delay, callback) {
_stopCyclingThemes();
if (!delay) {
delay = Mozilla.UITour.DEFAULT_THEME_CYCLE_DELAY;
}
function nextTheme() {
var theme = themes.shift();
themes.push(theme);
_sendEvent('previewTheme', {
theme: JSON.stringify(theme),
state: true
});
callback(theme);
}
themeIntervalId = setInterval(nextTheme, delay);
nextTheme();
};
Mozilla.UITour.addPinnedTab = function() {
_sendEvent('addPinnedTab');
};
Mozilla.UITour.removePinnedTab = function() {
_sendEvent('removePinnedTab');
};
Mozilla.UITour.showMenu = function(name) {
_sendEvent('showMenu', {
name: name
});
};
})();

View File

@ -30,9 +30,8 @@ this.webappsUI = {
Services.obs.addObserver(this, "webapps-launch", false);
Services.obs.addObserver(this, "webapps-uninstall", false);
cpmm.addMessageListener("Webapps:Install:Return:OK", this);
cpmm.addMessageListener("Webapps:OfflineCache", this);
cpmm.addMessageListener("Webapps:Install:Return:KO", this);
cpmm.addMessageListener("Webapps:PackageEvent", this);
cpmm.addMessageListener("Webapps:UpdateState", this);
},
uninit: function webappsUI_uninit() {
@ -40,9 +39,8 @@ this.webappsUI = {
Services.obs.removeObserver(this, "webapps-launch");
Services.obs.removeObserver(this, "webapps-uninstall");
cpmm.removeMessageListener("Webapps:Install:Return:OK", this);
cpmm.removeMessageListener("Webapps:OfflineCache", this);
cpmm.removeMessageListener("Webapps:Install:Return:KO", this);
cpmm.removeMessageListener("Webapps:PackageEvent", this);
cpmm.removeMessageListener("Webapps:UpdateState", this);
},
receiveMessage: function(aMessage) {
@ -56,10 +54,10 @@ this.webappsUI = {
return;
}
if (aMessage.name == "Webapps:OfflineCache") {
if (aMessage.name == "Webapps:UpdateState") {
if (data.error) {
this.installations[manifestURL].reject(data.error);
} else if (data.installState == "installed") {
} else if (data.app.installState == "installed") {
this.installations[manifestURL].resolve();
}
} else if (aMessage.name == "Webapps:Install:Return:OK" &&
@ -70,12 +68,6 @@ this.webappsUI = {
}
} else if (aMessage.name == "Webapps:Install:Return:KO") {
this.installations[manifestURL].reject(data.error);
} else if (aMessage.name == "Webapps:PackageEvent") {
if (data.type == "installed") {
this.installations[manifestURL].resolve();
} else if (data.type == "error") {
this.installations[manifestURL].reject(data.error);
}
}
},

View File

@ -2113,6 +2113,90 @@ toolbar[mode="text"] toolbarbutton.chevron > .toolbarbutton-icon {
-moz-margin-end: 2px;
}
/* UI Tour */
@keyframes uitour-wobble {
from {
transform: rotate(0deg) translateX(2px) rotate(0deg);
}
to {
transform: rotate(360deg) translateX(2px) rotate(-360deg);
}
}
@keyframes uitour-zoom {
from {
transform: scale(0.9);
}
50% {
transform: scale(1.1);
}
to {
transform: scale(0.9);
}
}
@keyframes uitour-color {
from {
border-color: #5B9CD9;
}
50% {
border-color: #FF0000;
}
to {
border-color: #5B9CD9;
}
}
html|div#UITourHighlight {
display: none;
position: absolute;
min-height: 32px;
min-width: 32px;
display: none;
border: 2px #5B9CD9 solid;
box-shadow: 0 0 2px #5B9CD9, inset 0 0 1px #5B9CD9;
border-radius: 20px;
z-index: 10000000000;
}
html|div#UITourHighlight[active] {
display: block;
animation-delay: 2s;
animation-timing-function: linear;
animation-iteration-count: infinite;
animation-fill-mode: forwards;
}
html|div#UITourHighlight[active="wobble"] {
animation-name: uitour-wobble;
animation-duration: 1s;
}
html|div#UITourHighlight[active="zoom"] {
animation-name: uitour-zoom;
animation-duration: 1s;
}
html|div#UITourHighlight[active="color"] {
animation-name: uitour-color;
animation-duration: 2s;
}
#UITourTooltip {
max-width: 20em;
}
#UITourTooltipTitle {
font-weight: bold;
font-size: 130%;
margin: 0 0 5px 0;
}
#UITourTooltipDescription {
max-width: 20em;
}
/* Social toolbar item */
#social-provider-button {
-moz-image-region: rect(0, 16px, 16px, 0);
list-style-image: url(chrome://browser/skin/social/services-16.png);

View File

@ -3728,6 +3728,88 @@ toolbarbutton.chevron > .toolbarbutton-menu-dropmarker {
border-radius: 1px;
}
/* UI Tour */
@keyframes uitour-wobble {
from {
transform: rotate(0deg) translateX(2px) rotate(0deg);
}
to {
transform: rotate(360deg) translateX(2px) rotate(-360deg);
}
}
@keyframes uitour-zoom {
from {
transform: scale(0.9);
}
50% {
transform: scale(1.1);
}
to {
transform: scale(0.9);
}
}
@keyframes uitour-color {
from {
border-color: #5B9CD9;
}
50% {
border-color: #FF0000;
}
to {
border-color: #5B9CD9;
}
}
html|div#UITourHighlight {
display: none;
position: absolute;
min-height: 32px;
min-width: 32px;
display: none;
border: 2px #5B9CD9 solid;
box-shadow: 0 0 2px #5B9CD9, inset 0 0 1px #5B9CD9;
border-radius: 20px;
z-index: 10000000000;
}
html|div#UITourHighlight[active] {
display: block;
animation-delay: 2s;
animation-timing-function: linear;
animation-iteration-count: infinite;
animation-fill-mode: forwards;
}
html|div#UITourHighlight[active="wobble"] {
animation-name: uitour-wobble;
animation-duration: 1s;
}
html|div#UITourHighlight[active="zoom"] {
animation-name: uitour-zoom;
animation-duration: 1s;
}
html|div#UITourHighlight[active="color"] {
animation-name: uitour-color;
animation-duration: 2s;
}
#UITourTooltip {
max-width: 20em;
}
#UITourTooltipTitle {
font-weight: bold;
font-size: 130%;
margin: 0 0 5px 0;
}
#UITourTooltipDescription {
max-width: 20em;
}
/* === social toolbar button === */
#social-toolbar-item > .toolbarbutton-1 {

View File

@ -2855,6 +2855,87 @@ toolbarbutton.bookmark-item[dragover="true"][open="true"] {
-moz-margin-end: 5px;
}
/* UI Tour */
@keyframes uitour-wobble {
from {
transform: rotate(0deg) translateX(2px) rotate(0deg);
}
to {
transform: rotate(360deg) translateX(2px) rotate(-360deg);
}
}
@keyframes uitour-zoom {
from {
transform: scale(0.9);
}
50% {
transform: scale(1.1);
}
to {
transform: scale(0.9);
}
}
@keyframes uitour-color {
from {
border-color: #5B9CD9;
}
50% {
border-color: #FF0000;
}
to {
border-color: #5B9CD9;
}
}
html|div#UITourHighlight {
display: none;
position: absolute;
min-height: 32px;
min-width: 32px;
display: none;
border: 2px #5B9CD9 solid;
box-shadow: 0 0 2px #5B9CD9, inset 0 0 1px #5B9CD9;
border-radius: 20px;
z-index: 10000000000;
}
html|div#UITourHighlight[active] {
display: block;
animation-delay: 2s;
animation-timing-function: linear;
animation-iteration-count: infinite;
animation-fill-mode: forwards;
}
html|div#UITourHighlight[active="wobble"] {
animation-name: uitour-wobble;
animation-duration: 1s;
}
html|div#UITourHighlight[active="zoom"] {
animation-name: uitour-zoom;
animation-duration: 1s;
}
html|div#UITourHighlight[active="color"] {
animation-name: uitour-color;
animation-duration: 2s;
}
#UITourTooltip {
}
#UITourTooltipTitle {
font-weight: bold;
font-size: 130%;
margin: 0 0 5px 0;
}
#UITourTooltipDescription {
max-width: 20em;
}
/* Social toolbar item */
#social-provider-button {

View File

@ -29,9 +29,9 @@ toolkit/library
editor
parser
js/src
js/xpconnect
js/xpconnect/loader
mfbt
js/xpconnect
js/xpconnect/loader
view
caps
xpfe/appshell

View File

@ -86,27 +86,41 @@ dnl ========================================================
MOZ_USE_PTHREADS=
_PTHREAD_LDFLAGS=""
dnl Do not allow a separate objdir build if a srcdir build exists.
dnl Do not allow objdir == srcdir builds.
dnl ==============================================================
_topsrcdir=`cd \`dirname $0\`; pwd`
_objdir=`pwd`
if test "$_topsrcdir" != "$_objdir"
then
# Check for a couple representative files in the source tree
_conflict_files=
for file in $_topsrcdir/Makefile $_topsrcdir/config/autoconf.mk; do
if test -f $file; then
_conflict_files="$_conflict_files $file"
fi
dnl TODO Don't exempt L10N builds once bug 842760 is resolved.
if test "$_topsrcdir" = "$_objdir" -a "${with_l10n_base+set}" != set; then
echo " ***"
echo " * Building directly in the main source directory is not allowed."
echo " *"
echo " * To build, you must run configure from a separate directory"
echo " * (referred to as an object directory)."
echo " *"
echo " * If you are building with a mozconfig, you will need to change your"
echo " * mozconfig to point to a different object directory."
echo " ***"
exit 1
fi
# Check for a couple representative files in the source tree
_conflict_files=
for file in $_topsrcdir/Makefile $_topsrcdir/config/autoconf.mk; do
if test -f $file; then
_conflict_files="$_conflict_files $file"
fi
done
if test "$_conflict_files"; then
echo "***"
echo "* Your source tree contains these files:"
for file in $_conflict_files; do
echo "* $file"
done
if test "$_conflict_files"; then
echo "***"
echo "* Your source tree contains these files:"
for file in $_conflict_files; do
echo "* $file"
done
cat 1>&2 <<-EOF
cat 1>&2 <<-EOF
* This indicates that you previously built in the source tree.
* A source tree build can confuse the separate objdir build.
*
@ -115,9 +129,8 @@ then
* 2. gmake distclean
***
EOF
exit 1
break
fi
exit 1
break
fi
MOZ_BUILD_ROOT=`pwd`
@ -209,6 +222,7 @@ if test -n "$gonkdir" ; then
15)
GONK_INCLUDES="-I$gonkdir/frameworks/base/opengl/include -I$gonkdir/frameworks/base/native/include -I$gonkdir/frameworks/base/include -I$gonkdir/frameworks/base/services/camera -I$gonkdir/frameworks/base/include/media/stagefright -I$gonkdir/frameworks/base/include/media/stagefright/openmax -I$gonkdir/frameworks/base/media/libstagefright/rtsp -I$gonkdir/frameworks/base/media/libstagefright/include -I$gonkdir/external/dbus -I$gonkdir/external/bluetooth/bluez/lib -I$gonkdir/dalvik/libnativehelper/include/nativehelper"
MOZ_B2G_BT=1
MOZ_B2G_BT_BLUEZ=1
MOZ_B2G_CAMERA=1
MOZ_OMX_DECODER=1
AC_SUBST(MOZ_OMX_DECODER)
@ -217,9 +231,15 @@ if test -n "$gonkdir" ; then
18)
GONK_INCLUDES="-I$gonkdir/frameworks/native/include -I$gonkdir/frameworks/av/include -I$gonkdir/frameworks/av/include/media -I$gonkdir/frameworks/av/include/camera -I$gonkdir/frameworks/native/include/media/openmax -I$gonkdir/frameworks/av/media/libstagefright/include"
if test -d "$gonkdir/external/bluetooth/bluez"; then
GONK_INCLUDES+=" -I$gonkdir/external/dbus -I$gonkdir/external/bluetooth/bluez/lib"
GONK_INCLUDES="$GONK_INCLUDES -I$gonkdir/external/dbus -I$gonkdir/external/bluetooth/bluez/lib"
MOZ_B2G_BT=1
MOZ_B2G_BT_BLUEZ=1
fi
if test -d "$gonkdir/external/bluetooth/bluedroid"; then
MOZ_B2G_BT=1
MOZ_B2G_BT_BLUEDROID=1
fi
MOZ_B2G_CAMERA=1
MOZ_OMX_DECODER=1
AC_SUBST(MOZ_OMX_DECODER)
@ -7275,6 +7295,8 @@ if test -n "$MOZ_B2G_BT"; then
AC_DEFINE(MOZ_B2G_BT)
fi
AC_SUBST(MOZ_B2G_BT)
AC_SUBST(MOZ_B2G_BT_BLUEZ)
AC_SUBST(MOZ_B2G_BT_BLUEDROID)
dnl ========================================================
dnl = Enable Pico Speech Synthesis (Gonk usually)

View File

@ -19,6 +19,7 @@
#endif
#include "js/TypeDecls.h"
#include "js/Value.h"
#include "js/RootingAPI.h"
#include "mozilla/Assertions.h"
#include "mozilla/EventForwards.h"
@ -1637,7 +1638,7 @@ public:
static nsresult WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsISupports *native, const nsIID* aIID,
JS::Value *vp,
JS::MutableHandle<JS::Value> vp,
// If non-null aHolder will keep the Value alive
// while there's a ref to it
nsIXPConnectJSObjectHolder** aHolder = nullptr,
@ -1649,7 +1650,7 @@ public:
// Same as the WrapNative above, but use this one if aIID is nsISupports' IID.
static nsresult WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsISupports *native, JS::Value *vp,
nsISupports *native, JS::MutableHandle<JS::Value> vp,
// If non-null aHolder will keep the Value alive
// while there's a ref to it
nsIXPConnectJSObjectHolder** aHolder = nullptr,
@ -1660,7 +1661,7 @@ public:
}
static nsresult WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsISupports *native, nsWrapperCache *cache,
JS::Value *vp,
JS::MutableHandle<JS::Value> vp,
// If non-null aHolder will keep the Value alive
// while there's a ref to it
nsIXPConnectJSObjectHolder** aHolder = nullptr,
@ -2091,7 +2092,7 @@ private:
static nsresult WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsISupports *native, nsWrapperCache *cache,
const nsIID* aIID, JS::Value *vp,
const nsIID* aIID, JS::MutableHandle<JS::Value> vp,
nsIXPConnectJSObjectHolder** aHolder,
bool aAllowWrapping);

View File

@ -45,6 +45,7 @@ CSPService::CSPService()
CSPService::~CSPService()
{
mAppStatusCache.Clear();
}
NS_IMPL_ISUPPORTS2(CSPService, nsIContentPolicy, nsIChannelEventSink)
@ -105,6 +106,55 @@ CSPService::ShouldLoad(uint32_t aContentType,
return NS_OK;
}
// ----- THIS IS A TEMPORARY FAST PATH FOR CERTIFIED APPS. -----
// ----- PLEASE REMOVE ONCE bug 925004 LANDS. -----
// Cache the app status for this origin.
uint16_t status = nsIPrincipal::APP_STATUS_NOT_INSTALLED;
nsAutoCString contentOrigin;
aContentLocation->GetPrePath(contentOrigin);
if (aRequestPrincipal && !mAppStatusCache.Get(contentOrigin, &status)) {
aRequestPrincipal->GetAppStatus(&status);
mAppStatusCache.Put(contentOrigin, status);
}
if (status == nsIPrincipal::APP_STATUS_CERTIFIED) {
// The CSP for certified apps is :
// "default-src *; script-src 'self'; object-src 'none'; style-src 'self'"
// That means we can optimize for this case by:
// - loading only same origin scripts and stylesheets.
// - never loading objects.
// - accepting everything else.
switch (aContentType) {
case nsIContentPolicy::TYPE_SCRIPT:
case nsIContentPolicy::TYPE_STYLESHEET:
{
nsAutoCString sourceOrigin;
aRequestOrigin->GetPrePath(sourceOrigin);
if (!sourceOrigin.Equals(contentOrigin)) {
*aDecision = nsIContentPolicy::REJECT_SERVER;
}
}
break;
case nsIContentPolicy::TYPE_OBJECT:
*aDecision = nsIContentPolicy::REJECT_SERVER;
break;
default:
*aDecision = nsIContentPolicy::ACCEPT;
}
// Only cache and return if we are successful. If not, we want the error
// to be reported, and thus fallback to the slow path.
if (*aDecision == nsIContentPolicy::ACCEPT) {
return NS_OK;
}
}
// ----- END OF TEMPORARY FAST PATH FOR CERTIFIED APPS. -----
// find the principal of the document that initiated this request and see
// if it has a CSP policy object
nsCOMPtr<nsINode> node(do_QueryInterface(aRequestContext));

View File

@ -23,4 +23,7 @@ public:
CSPService();
virtual ~CSPService();
static bool sCSPEnabled;
private:
// Maps origins to app status.
nsDataHashtable<nsCStringHashKey, uint16_t> mAppStatusCache;
};

View File

@ -5659,14 +5659,14 @@ nsContentUtils::DispatchXULCommand(nsIContent* aTarget,
nsresult
nsContentUtils::WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsISupports *native, nsWrapperCache *cache,
const nsIID* aIID, JS::Value *vp,
const nsIID* aIID, JS::MutableHandleValue vp,
nsIXPConnectJSObjectHolder **aHolder,
bool aAllowWrapping)
{
if (!native) {
NS_ASSERTION(!aHolder || !*aHolder, "*aHolder should be null!");
*vp = JSVAL_NULL;
vp.setNull();
return NS_OK;
}
@ -5685,7 +5685,7 @@ nsContentUtils::WrapNative(JSContext *cx, JS::Handle<JSObject*> scope,
nsresult rv = NS_OK;
AutoPushJSContext context(cx);
rv = sXPConnect->WrapNativeToJSVal(context, scope, native, cache, aIID,
aAllowWrapping, vp, aHolder);
aAllowWrapping, vp.address(), aHolder);
return rv;
}
@ -5728,8 +5728,7 @@ nsContentUtils::CreateBlobBuffer(JSContext* aCx,
return NS_ERROR_OUT_OF_MEMORY;
}
JS::Rooted<JSObject*> scope(aCx, JS::CurrentGlobalOrNull(aCx));
return nsContentUtils::WrapNative(aCx, scope, blob, aBlob.address(), nullptr,
true);
return nsContentUtils::WrapNative(aCx, scope, blob, aBlob, nullptr, true);
}
void

View File

@ -206,9 +206,11 @@ nsDOMFileReader::GetResult(JSContext* aCx, JS::Value* aResult)
}
nsString tmpResult = mResult;
if (!xpc::StringToJsval(aCx, tmpResult, aResult)) {
JS::Rooted<JS::Value> result(aCx);
if (!xpc::StringToJsval(aCx, tmpResult, &result)) {
return NS_ERROR_FAILURE;
}
*aResult = result;
return NS_OK;
}

View File

@ -5167,7 +5167,7 @@ CustomElementConstructor(JSContext *aCx, unsigned aArgc, JS::Value* aVp)
nsresult rv = document->CreateElem(elemName, nullptr, kNameSpaceID_XHTML,
getter_AddRefs(newElement));
rv = nsContentUtils::WrapNative(aCx, global, newElement, newElement,
args.rval().address());
args.rval());
NS_ENSURE_SUCCESS(rv, false);
return true;
@ -6732,7 +6732,7 @@ nsIDocument::AdoptNode(nsINode& aAdoptedNode, ErrorResult& rv)
JS::Rooted<JSObject*> global(cx, GetScopeObject()->GetGlobalJSObject());
JS::Rooted<JS::Value> v(cx);
rv = nsContentUtils::WrapNative(cx, global, this, this, v.address(),
rv = nsContentUtils::WrapNative(cx, global, this, this, &v,
nullptr, /* aAllowWrapping = */ false);
if (rv.Failed())
return nullptr;
@ -11345,7 +11345,7 @@ nsIDocument::WrapObject(JSContext *aCx, JS::Handle<JSObject*> aScope)
nsCOMPtr<nsIXPConnectJSObjectHolder> holder;
nsresult rv = nsContentUtils::WrapNative(aCx, obj, win,
&NS_GET_IID(nsIDOMWindow),
winVal.address(),
&winVal,
getter_AddRefs(holder),
false);
if (NS_FAILED(rv)) {

View File

@ -832,7 +832,7 @@ nsFrameMessageManager::ReceiveMessage(nsISupports* aTarget,
JS::Rooted<JS::Value> targetv(ctx);
JS::Rooted<JSObject*> global(ctx, JS_GetGlobalForObject(ctx, object));
nsContentUtils::WrapNative(ctx, global, aTarget, targetv.address(),
nsContentUtils::WrapNative(ctx, global, aTarget, &targetv,
nullptr, true);
JS::RootedObject cpows(ctx);
@ -888,7 +888,7 @@ nsFrameMessageManager::ReceiveMessage(nsISupports* aTarget,
}
JS::Rooted<JSObject*> global(ctx, JS_GetGlobalForObject(ctx, object));
nsContentUtils::WrapNative(ctx, global, defaultThisValue,
thisValue.address(), nullptr, true);
&thisValue, nullptr, true);
} else {
// If the listener is a JS object which has receiveMessage function:
if (!JS_GetProperty(ctx, object, "receiveMessage", &funval) ||

View File

@ -49,7 +49,15 @@ void
nsHostObjectProtocolHandler::RemoveDataEntry(const nsACString& aUri)
{
if (gDataTable) {
gDataTable->Remove(aUri);
nsCString uriIgnoringRef;
int32_t hashPos = aUri.FindChar('#');
if (hashPos < 0) {
uriIgnoringRef = aUri;
}
else {
uriIgnoringRef = StringHead(aUri, hashPos);
}
gDataTable->Remove(uriIgnoringRef);
if (gDataTable->Count() == 0) {
delete gDataTable;
gDataTable = nullptr;
@ -80,6 +88,27 @@ nsHostObjectProtocolHandler::GenerateURIString(const nsACString &aScheme,
return NS_OK;
}
static DataInfo*
GetDataInfo(const nsACString& aUri)
{
if (!gDataTable) {
return nullptr;
}
DataInfo* res;
nsCString uriIgnoringRef;
int32_t hashPos = aUri.FindChar('#');
if (hashPos < 0) {
uriIgnoringRef = aUri;
}
else {
uriIgnoringRef = StringHead(aUri, hashPos);
}
gDataTable->Get(uriIgnoringRef, &res);
return res;
}
nsIPrincipal*
nsHostObjectProtocolHandler::GetDataEntryPrincipal(const nsACString& aUri)
{
@ -87,8 +116,8 @@ nsHostObjectProtocolHandler::GetDataEntryPrincipal(const nsACString& aUri)
return nullptr;
}
DataInfo* res;
gDataTable->Get(aUri, &res);
DataInfo* res = GetDataInfo(aUri);
if (!res) {
return nullptr;
}
@ -114,18 +143,6 @@ nsHostObjectProtocolHandler::Traverse(const nsACString& aUri,
aCallback.NoteXPCOMChild(res->mObject);
}
static DataInfo*
GetDataInfo(const nsACString& aUri)
{
if (!gDataTable) {
return nullptr;
}
DataInfo* res;
gDataTable->Get(aUri, &res);
return res;
}
static nsISupports*
GetDataObject(nsIURI* aURI)
{

View File

@ -966,7 +966,7 @@ nsXMLHttpRequest::GetResponse(JSContext* aCx, ErrorResult& aRv)
if (aRv.Failed()) {
return JSVAL_NULL;
}
JS::Value result;
JS::Rooted<JS::Value> result(aCx);
if (!xpc::StringToJsval(aCx, str, &result)) {
aRv.Throw(NS_ERROR_OUT_OF_MEMORY);
return JSVAL_NULL;
@ -1014,7 +1014,7 @@ nsXMLHttpRequest::GetResponse(JSContext* aCx, ErrorResult& aRv)
JS::Rooted<JS::Value> result(aCx, JSVAL_NULL);
JS::Rooted<JSObject*> scope(aCx, JS::CurrentGlobalOrNull(aCx));
aRv = nsContentUtils::WrapNative(aCx, scope, mResponseBlob, result.address(),
aRv = nsContentUtils::WrapNative(aCx, scope, mResponseBlob, &result,
nullptr, true);
return result;
}
@ -1026,7 +1026,7 @@ nsXMLHttpRequest::GetResponse(JSContext* aCx, ErrorResult& aRv)
JS::Rooted<JSObject*> scope(aCx, JS::CurrentGlobalOrNull(aCx));
JS::Rooted<JS::Value> result(aCx, JSVAL_NULL);
aRv = nsContentUtils::WrapNative(aCx, scope, mResponseXML, result.address(),
aRv = nsContentUtils::WrapNative(aCx, scope, mResponseXML, &result,
nullptr, true);
return result;
}
@ -3659,7 +3659,7 @@ nsXMLHttpRequest::GetInterface(JSContext* aCx, nsIJSID* aIID, ErrorResult& aRv)
JS::Rooted<JSObject*> wrapper(aCx, GetWrapper());
JSAutoCompartment ac(aCx, wrapper);
JS::Rooted<JSObject*> global(aCx, JS_GetGlobalForObject(aCx, wrapper));
aRv = nsContentUtils::WrapNative(aCx, global, result, iid, v.address());
aRv = nsContentUtils::WrapNative(aCx, global, result, iid, &v);
return aRv.Failed() ? JSVAL_NULL : v;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

View File

@ -0,0 +1 @@
== test_bug920877.html test_bug920877-ref.html

View File

@ -0,0 +1,20 @@
<html>
<body>
<script>
var img = document.createElement("img");
img.id = "img-ori";
img.src = "mixed-bmp-png.ico";
document.body.appendChild(img);
img = document.createElement("img");
img.id = "img-res32";
img.src = "mixed-bmp-png.ico#-moz-resolution=32,32";
document.body.appendChild(img);
img = document.createElement("img");
img.id = "img-res48";
img.src = "mixed-bmp-png.ico#-moz-resolution=48,48";
document.body.appendChild(img);
</script>
</body>
</html>

File diff suppressed because one or more lines are too long

View File

@ -114,7 +114,7 @@ HTMLAudioElement::MozSetup(uint32_t aChannels, uint32_t aRate, ErrorResult& aRv)
#endif
mAudioStream = AudioStream::AllocateStream();
aRv = mAudioStream->Init(aChannels, aRate, mAudioChannelType);
aRv = mAudioStream->Init(aChannels, aRate, mAudioChannelType, AudioStream::HighLatency);
if (aRv.Failed()) {
mAudioStream->Shutdown();
mAudioStream = nullptr;

View File

@ -3155,7 +3155,7 @@ nsGenericHTMLElement::GetItemValue(JSContext* aCx, JSObject* aScope,
nsString string;
GetItemValueText(string);
JS::Value v;
JS::Rooted<JS::Value> v(aCx);
if (!xpc::NonVoidStringToJsval(aCx, string, &v)) {
aError.Throw(NS_ERROR_FAILURE);
return JS::UndefinedValue();

View File

@ -41,6 +41,11 @@ PRLogModuleInfo* gAudioStreamLog = nullptr;
static Mutex* gAudioPrefsLock = nullptr;
static double gVolumeScale;
static uint32_t gCubebLatency;
static bool gCubebLatencyPrefSet;
static const uint32_t CUBEB_NORMAL_LATENCY_MS = 100;
StaticMutex AudioStream::mMutex;
uint32_t AudioStream::mPreferredSampleRate = 0;
/**
* When MOZ_DUMP_AUDIO is set in the environment (to anything),
@ -65,9 +70,10 @@ static int PrefChanged(const char* aPref, void* aClosure)
// Arbitrary default stream latency of 100ms. The higher this
// value, the longer stream volume changes will take to become
// audible.
uint32_t value = Preferences::GetUint(aPref, 100);
gCubebLatencyPrefSet = Preferences::HasUserValue(aPref);
uint32_t value = Preferences::GetUint(aPref, CUBEB_NORMAL_LATENCY_MS);
MutexAutoLock lock(*gAudioPrefsLock);
gCubebLatency = std::min<uint32_t>(std::max<uint32_t>(value, 20), 1000);
gCubebLatency = std::min<uint32_t>(std::max<uint32_t>(value, 1), 1000);
}
return 0;
}
@ -97,6 +103,12 @@ static uint32_t GetCubebLatency()
MutexAutoLock lock(*gAudioPrefsLock);
return gCubebLatency;
}
static bool CubebLatencyPrefSet()
{
MutexAutoLock lock(*gAudioPrefsLock);
return gCubebLatencyPrefSet;
}
#endif
#if defined(MOZ_CUBEB) && defined(__ANDROID__) && defined(MOZ_B2G)
@ -311,7 +323,8 @@ class BufferedAudioStream : public AudioStream
~BufferedAudioStream();
nsresult Init(int32_t aNumChannels, int32_t aRate,
const dom::AudioChannelType aAudioChannelType);
const dom::AudioChannelType aAudioChannelType,
AudioStream::LatencyRequest aLatencyRequest);
void Shutdown();
nsresult Write(const AudioDataValue* aBuf, uint32_t aFrames);
uint32_t Available();
@ -431,6 +444,23 @@ int AudioStream::MaxNumberOfChannels()
return static_cast<int>(maxNumberOfChannels);
}
int AudioStream::PreferredSampleRate()
{
StaticMutexAutoLock lock(AudioStream::mMutex);
// Get the preferred samplerate for this platform, or fallback to something
// sensible if we fail. We cache the value, because this might be accessed
// often, and the complexity of the function call below depends on the
// backend used.
const int fallbackSampleRate = 44100;
if (mPreferredSampleRate == 0) {
if (cubeb_get_preferred_sample_rate(GetCubebContext(), &mPreferredSampleRate) != CUBEB_OK) {
mPreferredSampleRate = fallbackSampleRate;
}
}
return mPreferredSampleRate;
}
static void SetUint16LE(uint8_t* aDest, uint16_t aValue)
{
aDest[0] = aValue & 0xFF;
@ -526,7 +556,8 @@ BufferedAudioStream::EnsureTimeStretcherInitialized()
nsresult
BufferedAudioStream::Init(int32_t aNumChannels, int32_t aRate,
const dom::AudioChannelType aAudioChannelType)
const dom::AudioChannelType aAudioChannelType,
AudioStream::LatencyRequest aLatencyRequest)
{
cubeb* cubebContext = GetCubebContext();
@ -562,10 +593,22 @@ BufferedAudioStream::Init(int32_t aNumChannels, int32_t aRate,
mAudioClock.Init();
// If the latency pref is set, use it. Otherwise, if this stream is intended
// for low latency playback, try to get the lowest latency possible.
// Otherwise, for normal streams, use 100ms.
uint32_t latency;
if (aLatencyRequest == AudioStream::LowLatency && !CubebLatencyPrefSet()) {
if (cubeb_get_min_latency(cubebContext, params, &latency) != CUBEB_OK) {
latency = GetCubebLatency();
}
} else {
latency = GetCubebLatency();
}
{
cubeb_stream* stream;
if (cubeb_stream_init(cubebContext, &stream, "BufferedAudioStream", params,
GetCubebLatency(), DataCallback_S, StateCallback_S, this) == CUBEB_OK) {
latency, DataCallback_S, StateCallback_S, this) == CUBEB_OK) {
mCubebStream.own(stream);
}
}

View File

@ -11,6 +11,7 @@
#include "nsAutoPtr.h"
#include "nsCOMPtr.h"
#include "Latency.h"
#include "mozilla/StaticMutex.h"
namespace soundtouch {
class SoundTouch;
@ -92,6 +93,10 @@ class AudioClock
class AudioStream
{
public:
enum LatencyRequest {
HighLatency,
LowLatency
};
AudioStream();
virtual ~AudioStream();
@ -112,11 +117,16 @@ public:
// Returns the maximum number of channels supported by the audio hardware.
static int MaxNumberOfChannels();
// Returns the samplerate the systems prefer, because it is the
// samplerate the hardware/mixer supports.
static int PreferredSampleRate();
// Initialize the audio stream. aNumChannels is the number of audio
// channels (1 for mono, 2 for stereo, etc) and aRate is the sample rate
// (22050Hz, 44100Hz, etc).
virtual nsresult Init(int32_t aNumChannels, int32_t aRate,
const dom::AudioChannelType aAudioStreamType) = 0;
const dom::AudioChannelType aAudioStreamType,
LatencyRequest aLatencyRequest) = 0;
// Closes the stream. All future use of the stream is an error.
virtual void Shutdown() = 0;
@ -178,6 +188,11 @@ public:
virtual nsresult SetPreservesPitch(bool aPreservesPitch);
protected:
// This mutex protects the mPreferedSamplerate member below.
static StaticMutex mMutex;
// Prefered samplerate, in Hz (characteristic of the
// hardware/mixer/platform/API used).
static uint32_t mPreferredSampleRate;
// Input rate in Hz (characteristic of the media being played)
int mInRate;
// Output rate in Hz (characteristic of the playback rate)

View File

@ -1059,7 +1059,7 @@ void MediaDecoderStateMachine::AudioLoop()
// circumstances, so we take care to drop the decoder monitor while
// initializing.
nsAutoPtr<AudioStream> audioStream(AudioStream::AllocateStream());
audioStream->Init(channels, rate, audioChannelType);
audioStream->Init(channels, rate, audioChannelType, AudioStream::HighLatency);
audioStream->SetVolume(volume);
if (audioStream->SetPreservesPitch(preservesPitch) != NS_OK) {
NS_WARNING("Setting the pitch preservation failed at AudioLoop start.");

View File

@ -768,7 +768,7 @@ MediaStreamGraphImpl::CreateOrDestroyAudioStreams(GraphTime aAudioOutputStartTim
audioOutputStream->mStream = AudioStream::AllocateStream();
// XXX for now, allocate stereo output. But we need to fix this to
// match the system's ideal channel configuration.
audioOutputStream->mStream->Init(2, tracks->GetRate(), AUDIO_CHANNEL_NORMAL);
audioOutputStream->mStream->Init(2, tracks->GetRate(), AUDIO_CHANNEL_NORMAL, AudioStream::LowLatency);
audioOutputStream->mTrackID = tracks->GetID();
}
}

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