Merge m-c to inbound on a CLOSED TREE.
@ -19,7 +19,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="ca283b9db2b151d465cfd2e19346cf58fe89e413"/>
|
||||
|
@ -17,7 +17,7 @@
|
||||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="ce95d372e6d285725b96490afdaaf489ad8f9ca9"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="3691614d0045f7968addce45d4140fb360c3ceaf"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="65fba428f8d76336b33ddd9e15900357953600ba">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="ce95d372e6d285725b96490afdaaf489ad8f9ca9"/>
|
||||
|
@ -19,7 +19,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="ca283b9db2b151d465cfd2e19346cf58fe89e413"/>
|
||||
|
@ -18,7 +18,7 @@
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="ce95d372e6d285725b96490afdaaf489ad8f9ca9"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="3691614d0045f7968addce45d4140fb360c3ceaf"/>
|
||||
@ -119,7 +119,7 @@
|
||||
<!-- Flame specific things -->
|
||||
<project name="device/generic/armv7-a-neon" path="device/generic/armv7-a-neon" revision="e8a318f7690092e639ba88891606f4183e846d3f"/>
|
||||
<project name="device/qcom/common" path="device/qcom/common" revision="234ed34543345f58c0d4dcb1aa012de68802b9dc"/>
|
||||
<project name="device-flame" path="device/t2m/flame" remote="b2g" revision="2173c7c1f90ccd28915eed1d58077311d8296ec4"/>
|
||||
<project name="device-flame" path="device/t2m/flame" remote="b2g" revision="2a3f4c782daad9740f1b78766b636e0e00a0ff30"/>
|
||||
<project name="kernel/msm" path="kernel" revision="1f47f3a180ed8b070f3cf3c4d11ff2523cca6c8a"/>
|
||||
<project name="platform/bootable/recovery" path="bootable/recovery" revision="f2914eacee9120680a41463708bb6ee8291749fc"/>
|
||||
<project name="platform/external/bluetooth/bluedroid" path="external/bluetooth/bluedroid" revision="fa892235a9bd8983f8b591129fc1a9398f64e514"/>
|
||||
|
@ -4,6 +4,6 @@
|
||||
"remote": "",
|
||||
"branch": ""
|
||||
},
|
||||
"revision": "2c31857e31048d05f9bb335d8ef2408c612195af",
|
||||
"revision": "18441d7d35b6a96732575fb5c28cedfed8269fb2",
|
||||
"repo_path": "/integration/gaia-central"
|
||||
}
|
||||
|
@ -17,7 +17,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
|
@ -19,7 +19,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
|
@ -17,7 +17,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
|
@ -17,7 +17,7 @@
|
||||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="ce95d372e6d285725b96490afdaaf489ad8f9ca9"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="3691614d0045f7968addce45d4140fb360c3ceaf"/>
|
||||
|
@ -17,7 +17,7 @@
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="68f7b3d4c3734a699b053cc897c1d11b8326fb93"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="4f352142a54f7f7ae2c460aad9049eda4b0edb14"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="f313e6d3aaaefe8c82eaed15912a09b120fb7260"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1f6a1fe07f81c5bc5e1d079c9b60f7f78ca2bf4f"/>
|
||||
|
@ -784,6 +784,30 @@ pref("plugin.state.npvidyoweb", 2);
|
||||
pref("plugin.state.vidyoweb", 2);
|
||||
#endif
|
||||
|
||||
// McAfee Virtual Technician, bug 981503
|
||||
#ifdef XP_WIN
|
||||
pref("plugin.state.npmvtplugin", 2);
|
||||
#endif
|
||||
|
||||
// Verimatrix ViewRightWeb, bug 989872
|
||||
#ifdef XP_WIN
|
||||
pref("plugin.state.npviewright", 2);
|
||||
#endif
|
||||
#ifdef XP_MACOSX
|
||||
pref("plugin.state.viewrightwebplayer", 2);
|
||||
#endif
|
||||
|
||||
// McAfee SiteAdvisor Enterprise, bug 987057
|
||||
#ifdef XP_WIN
|
||||
pref("plugin.state.npmcffplg", 2);
|
||||
#endif
|
||||
|
||||
// F5 Networks SSLVPN plugin, bug 985640
|
||||
#ifdef XP_MACOSX
|
||||
pref("plugin.state.f5 ssl vpn plugin", 2);
|
||||
pref("plugin.state.f5 sam inspection host plugin", 2);
|
||||
#endif
|
||||
|
||||
// display door hanger if flash not installed
|
||||
pref("plugins.notifyMissingFlash", true);
|
||||
|
||||
|
Before Width: | Height: | Size: 2.4 KiB After Width: | Height: | Size: 1.9 KiB |
Before Width: | Height: | Size: 9.1 KiB After Width: | Height: | Size: 6.3 KiB |
Before Width: | Height: | Size: 19 KiB After Width: | Height: | Size: 13 KiB |
@ -1545,6 +1545,10 @@ let BookmarkingUI = {
|
||||
viewToolbar.removeAttribute("checked");
|
||||
else
|
||||
viewToolbar.setAttribute("checked", "true");
|
||||
// Get all statically placed buttons to supply them with keyboard shortcuts.
|
||||
let staticButtons = viewToolbar.parentNode.getElementsByTagName("toolbarbutton");
|
||||
for (let i = 0, l = staticButtons.length; i < l; ++i)
|
||||
CustomizableUI.addShortcut(staticButtons[i]);
|
||||
// Setup the Places view.
|
||||
this._panelMenuView = new PlacesPanelMenuView("place:folder=BOOKMARKS_MENU",
|
||||
"panelMenu_bookmarksMenu",
|
||||
|
@ -867,6 +867,7 @@
|
||||
during the customization of the toolbar, in the palette, and before
|
||||
the Downloads Indicator overlay is loaded. -->
|
||||
<toolbarbutton id="downloads-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
|
||||
key="key_openDownloads"
|
||||
oncommand="DownloadsIndicatorView.onCommand(event);"
|
||||
ondrop="DownloadsIndicatorView.onDrop(event);"
|
||||
ondragover="DownloadsIndicatorView.onDragOver(event);"
|
||||
@ -883,6 +884,7 @@
|
||||
ondragenter="homeButtonObserver.onDragOver(event)"
|
||||
ondrop="homeButtonObserver.onDrop(event)"
|
||||
ondragexit="homeButtonObserver.onDragExit(event)"
|
||||
key="goHome"
|
||||
onclick="BrowserGoHome(event);"
|
||||
cui-areatype="toolbar"
|
||||
aboutHomeOverrideTooltip="&abouthome.pageTitle;"/>
|
||||
@ -1005,10 +1007,12 @@
|
||||
<toolbarbutton id="print-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
|
||||
#ifdef XP_MACOSX
|
||||
command="cmd_print"
|
||||
tooltip="dynamic-shortcut-tooltip"
|
||||
#else
|
||||
command="cmd_printPreview"
|
||||
tooltiptext="&printButton.tooltip;"
|
||||
#endif
|
||||
tooltip="dynamic-shortcut-tooltip" label="&printButton.label;"/>
|
||||
label="&printButton.label;"/>
|
||||
|
||||
|
||||
<toolbarbutton id="new-window-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
|
||||
|
@ -59,6 +59,7 @@
|
||||
label="&appMenuHistory.viewSidebar.label;"
|
||||
type="checkbox"
|
||||
class="subviewbutton"
|
||||
key="key_gotoHistory"
|
||||
oncommand="toggleSidebar('viewHistorySidebar'); PanelUI.hide();">
|
||||
<observes element="viewHistorySidebar" attribute="checked"/>
|
||||
</toolbarbutton>
|
||||
@ -102,6 +103,7 @@
|
||||
<toolbarbutton id="panelMenu_viewBookmarksSidebar"
|
||||
label="&viewBookmarksSidebar2.label;"
|
||||
class="subviewbutton"
|
||||
key="viewBookmarksSidebarKb"
|
||||
oncommand="toggleSidebar('viewBookmarksSidebar'); PanelUI.hide();">
|
||||
<observes element="viewBookmarksSidebar" attribute="checked"/>
|
||||
</toolbarbutton>
|
||||
|
@ -1244,6 +1244,32 @@ let CustomizableUIInternal = {
|
||||
return def;
|
||||
},
|
||||
|
||||
addShortcut: function(aShortcutNode, aTargetNode) {
|
||||
if (!aTargetNode)
|
||||
aTargetNode = aShortcutNode;
|
||||
let document = aShortcutNode.ownerDocument;
|
||||
|
||||
// Detect if we've already been here before.
|
||||
if (!aTargetNode || aTargetNode.hasAttribute("shortcut"))
|
||||
return;
|
||||
|
||||
let shortcutId = aShortcutNode.getAttribute("key");
|
||||
let shortcut;
|
||||
if (shortcutId) {
|
||||
shortcut = document.getElementById(shortcutId);
|
||||
} else {
|
||||
let commandId = aShortcutNode.getAttribute("command");
|
||||
if (commandId)
|
||||
shortcut = ShortcutUtils.findShortcut(document.getElementById(commandId));
|
||||
}
|
||||
if (!shortcut) {
|
||||
ERROR("Could not find a keyboard shortcut for '" + aShortcutNode.outerHTML + "'.");
|
||||
return;
|
||||
}
|
||||
|
||||
aTargetNode.setAttribute("shortcut", ShortcutUtils.prettifyShortcut(shortcut));
|
||||
},
|
||||
|
||||
handleWidgetCommand: function(aWidget, aNode, aEvent) {
|
||||
LOG("handleWidgetCommand");
|
||||
|
||||
@ -3250,6 +3276,18 @@ this.CustomizableUI = {
|
||||
return CustomizableUIInternal.getLocalizedProperty(aWidget, aProp,
|
||||
aFormatArgs, aDef);
|
||||
},
|
||||
/**
|
||||
* Utility function to detect, find and set a keyboard shortcut for a menuitem
|
||||
* or (toolbar)button.
|
||||
*
|
||||
* @param aShortcutNode the XUL node where the shortcut will be derived from;
|
||||
* @param aTargetNode (optional) the XUL node on which the `shortcut`
|
||||
* attribute will be set. If NULL, the shortcut will be
|
||||
* set on aShortcutNode;
|
||||
*/
|
||||
addShortcut: function(aShortcutNode, aTargetNode) {
|
||||
return CustomizableUIInternal.addShortcut(aShortcutNode, aTargetNode);
|
||||
},
|
||||
/**
|
||||
* Given a node, walk up to the first panel in its ancestor chain, and
|
||||
* close it.
|
||||
|
@ -78,18 +78,6 @@ function updateCombinedWidgetStyle(aNode, aArea, aModifyCloseMenu) {
|
||||
}
|
||||
}
|
||||
|
||||
function addShortcut(aNode, aDocument, aItem) {
|
||||
let shortcutId = aNode.getAttribute("key");
|
||||
if (!shortcutId) {
|
||||
return;
|
||||
}
|
||||
let shortcut = aDocument.getElementById(shortcutId);
|
||||
if (!shortcut) {
|
||||
return;
|
||||
}
|
||||
aItem.setAttribute("shortcut", ShortcutUtils.prettifyShortcut(shortcut));
|
||||
}
|
||||
|
||||
function fillSubviewFromMenuItems(aMenuItems, aSubview) {
|
||||
let attrs = ["oncommand", "onclick", "label", "key", "disabled",
|
||||
"command", "observes", "hidden", "class", "origin",
|
||||
@ -111,7 +99,7 @@ function fillSubviewFromMenuItems(aMenuItems, aSubview) {
|
||||
subviewItem = doc.createElementNS(kNSXUL, "menuseparator");
|
||||
} else if (menuChild.localName == "menuitem") {
|
||||
subviewItem = doc.createElementNS(kNSXUL, "toolbarbutton");
|
||||
addShortcut(menuChild, doc, subviewItem);
|
||||
CustomizableUI.addShortcut(menuChild, subviewItem);
|
||||
} else {
|
||||
continue;
|
||||
}
|
||||
@ -169,6 +157,11 @@ const CustomizableWidgets = [{
|
||||
items.removeChild(items.firstChild);
|
||||
}
|
||||
|
||||
// Get all statically placed buttons to supply them with keyboard shortcuts.
|
||||
let staticButtons = items.parentNode.getElementsByTagNameNS(kNSXUL, "toolbarbutton");
|
||||
for (let i = 0, l = staticButtons.length; i < l; ++i)
|
||||
CustomizableUI.addShortcut(staticButtons[i]);
|
||||
|
||||
PlacesUtils.history.QueryInterface(Ci.nsPIPlacesDatabase)
|
||||
.asyncExecuteLegacyQueries([query], 1, options, {
|
||||
handleResult: function (aResultSet) {
|
||||
|
@ -90,6 +90,7 @@ const FRAME_TYPE = {
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/devtools/event-emitter.js");
|
||||
Cu.import("resource://gre/modules/Task.jsm");
|
||||
Cu.import("resource:///modules/devtools/SimpleListWidget.jsm");
|
||||
Cu.import("resource:///modules/devtools/BreadcrumbsWidget.jsm");
|
||||
Cu.import("resource:///modules/devtools/SideMenuWidget.jsm");
|
||||
@ -1835,24 +1836,23 @@ Breakpoints.prototype = {
|
||||
* A promise that is resolved after the breakpoint is added, or
|
||||
* rejected if there was an error.
|
||||
*/
|
||||
addBreakpoint: function(aLocation, aOptions = {}) {
|
||||
addBreakpoint: Task.async(function*(aLocation, aOptions = {}) {
|
||||
// Make sure a proper location is available.
|
||||
if (!aLocation) {
|
||||
return promise.reject(new Error("Invalid breakpoint location."));
|
||||
throw new Error("Invalid breakpoint location.");
|
||||
}
|
||||
let addedPromise, removingPromise;
|
||||
|
||||
// If the breakpoint was already added, or is currently being added at the
|
||||
// specified location, then return that promise immediately.
|
||||
let addedPromise = this._getAdded(aLocation);
|
||||
if (addedPromise) {
|
||||
if ((addedPromise = this._getAdded(aLocation))) {
|
||||
return addedPromise;
|
||||
}
|
||||
|
||||
// If the breakpoint is currently being removed from the specified location,
|
||||
// then wait for that to finish and retry afterwards.
|
||||
let removingPromise = this._getRemoving(aLocation);
|
||||
if (removingPromise) {
|
||||
return removingPromise.then(() => this.addBreakpoint(aLocation, aOptions));
|
||||
// then wait for that to finish.
|
||||
if ((removingPromise = this._getRemoving(aLocation))) {
|
||||
yield removingPromise;
|
||||
}
|
||||
|
||||
let deferred = promise.defer();
|
||||
@ -1862,7 +1862,7 @@ Breakpoints.prototype = {
|
||||
this._added.set(identifier, deferred.promise);
|
||||
|
||||
// Try adding the breakpoint.
|
||||
gThreadClient.setBreakpoint(aLocation, (aResponse, aBreakpointClient) => {
|
||||
gThreadClient.setBreakpoint(aLocation, Task.async(function*(aResponse, aBreakpointClient) {
|
||||
// If the breakpoint response has an "actualLocation" attached, then
|
||||
// the original requested placement for the breakpoint wasn't accepted.
|
||||
if (aResponse.actualLocation) {
|
||||
@ -1871,11 +1871,6 @@ Breakpoints.prototype = {
|
||||
let newIdentifier = identifier = this.getIdentifier(aResponse.actualLocation);
|
||||
this._added.delete(oldIdentifier);
|
||||
this._added.set(newIdentifier, deferred.promise);
|
||||
|
||||
// Store the originally requested location in case it's ever needed
|
||||
// and update the breakpoint client with the actual location.
|
||||
aBreakpointClient.requestedLocation = aLocation;
|
||||
aBreakpointClient.location = aResponse.actualLocation;
|
||||
}
|
||||
|
||||
// By default, new breakpoints are always enabled. Disabled breakpoints
|
||||
@ -1883,13 +1878,23 @@ Breakpoints.prototype = {
|
||||
// so that they may not be forgotten across target navigations.
|
||||
let disabledPromise = this._disabled.get(identifier);
|
||||
if (disabledPromise) {
|
||||
disabledPromise.then((aPrevBreakpointClient) => {
|
||||
let condition = aPrevBreakpointClient.getCondition();
|
||||
if (condition) {
|
||||
aBreakpointClient.setCondition(gThreadClient, condition);
|
||||
}
|
||||
});
|
||||
let aPrevBreakpointClient = yield disabledPromise;
|
||||
let condition = aPrevBreakpointClient.getCondition();
|
||||
this._disabled.delete(identifier);
|
||||
|
||||
if (condition) {
|
||||
aBreakpointClient = yield aBreakpointClient.setCondition(
|
||||
gThreadClient,
|
||||
condition
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if (aResponse.actualLocation) {
|
||||
// Store the originally requested location in case it's ever needed
|
||||
// and update the breakpoint client with the actual location.
|
||||
aBreakpointClient.requestedLocation = aLocation;
|
||||
aBreakpointClient.location = aResponse.actualLocation;
|
||||
}
|
||||
|
||||
// Preserve information about the breakpoint's line text, to display it
|
||||
@ -1905,10 +1910,10 @@ Breakpoints.prototype = {
|
||||
// Notify that we've added a breakpoint.
|
||||
window.emit(EVENTS.BREAKPOINT_ADDED, aBreakpointClient);
|
||||
deferred.resolve(aBreakpointClient);
|
||||
});
|
||||
}.bind(this)));
|
||||
|
||||
return deferred.promise;
|
||||
},
|
||||
}),
|
||||
|
||||
/**
|
||||
* Remove a breakpoint.
|
||||
@ -2032,12 +2037,14 @@ Breakpoints.prototype = {
|
||||
'in specified location'));
|
||||
}
|
||||
|
||||
return addedPromise.then(aBreakpointClient => {
|
||||
var promise = addedPromise.then(aBreakpointClient => {
|
||||
return aBreakpointClient.setCondition(gThreadClient, aCondition);
|
||||
}, err => {
|
||||
DevToolsUtils.reportException("Breakpoints.prototype.updateCondition",
|
||||
err);
|
||||
});
|
||||
|
||||
// `setCondition` returns a new breakpoint that has the condition,
|
||||
// so we need to update the store
|
||||
this._added.set(this.getIdentifier(aLocation), promise);
|
||||
return promise;
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -26,7 +26,8 @@ function test() {
|
||||
.then(() => clickBreakpointAndCheck(2, 1, 7))
|
||||
.then(() => clickBreakpointAndCheck(3, 1, 8))
|
||||
.then(() => clickBreakpointAndCheck(4, 1, 9))
|
||||
.then(() => resumeDebuggerThenCloseAndFinish(gPanel))
|
||||
.then(() => ensureThreadClientState(gPanel, "resumed"))
|
||||
.then(() => closeDebuggerAndFinish(gPanel))
|
||||
.then(null, aError => {
|
||||
ok(false, "Got an error: " + aError.message + "\n" + aError.stack);
|
||||
});
|
||||
|
@ -41,7 +41,15 @@ function test() {
|
||||
.then(() => resumeAndTestBreakpoint(25))
|
||||
.then(() => resumeAndTestBreakpoint(27))
|
||||
.then(() => resumeAndTestBreakpoint(28))
|
||||
.then(() => resumeAndTestBreakpoint(29))
|
||||
.then(() => {
|
||||
// Note: the breakpoint on line 29 should not be hit since the
|
||||
// conditional expression evaluates to undefined. It used to
|
||||
// be on line 30, but it can't be the last breakpoint because
|
||||
// there is a race condition (the "frames cleared" event might
|
||||
// fire from the conditional expression evaluation if it's too
|
||||
// slow, which is what we wait for to reload the page)
|
||||
return resumeAndTestBreakpoint(30);
|
||||
})
|
||||
.then(() => resumeAndTestNoBreakpoint())
|
||||
.then(() => reloadActiveTab(gPanel, gDebugger.EVENTS.BREAKPOINT_SHOWN, 13))
|
||||
.then(() => testAfterReload())
|
||||
@ -78,9 +86,9 @@ function test() {
|
||||
.then(() => gPanel.addBreakpoint({ url: gSources.selectedValue, line: 28 }))
|
||||
.then(aClient => aClient.conditionalExpression = "a !== undefined")
|
||||
.then(() => gPanel.addBreakpoint({ url: gSources.selectedValue, line: 29 }))
|
||||
.then(aClient => aClient.conditionalExpression = "a !== null")
|
||||
.then(() => gPanel.addBreakpoint({ url: gSources.selectedValue, line: 30 }))
|
||||
.then(aClient => aClient.conditionalExpression = "b")
|
||||
.then(() => gPanel.addBreakpoint({ url: gSources.selectedValue, line: 30 }))
|
||||
.then(aClient => aClient.conditionalExpression = "a !== null");
|
||||
}
|
||||
|
||||
function initialChecks() {
|
||||
@ -157,7 +165,7 @@ function test() {
|
||||
ok(selectedUrl,
|
||||
"There should be a selected item in the sources pane.");
|
||||
ok(selectedBreakpoint,
|
||||
"There should be a selected brekapoint in the sources pane.");
|
||||
"There should be a selected breakpoint in the sources pane.");
|
||||
|
||||
is(selectedBreakpoint.attachment.url, selectedUrl,
|
||||
"The breakpoint on line " + aLine + " wasn't added on the correct source.");
|
||||
@ -190,7 +198,7 @@ function test() {
|
||||
ok(selectedUrl,
|
||||
"There should be a selected item in the sources pane after reload.");
|
||||
ok(!selectedBreakpoint,
|
||||
"There should be no selected brekapoint in the sources pane after reload.");
|
||||
"There should be no selected breakpoint in the sources pane after reload.");
|
||||
|
||||
return promise.resolve(null)
|
||||
.then(() => testBreakpoint(18, true))
|
||||
|
@ -55,7 +55,7 @@ function test() {
|
||||
}
|
||||
|
||||
function setConditional(aClient) {
|
||||
aClient.condition = "hello";
|
||||
return gBreakpoints.updateCondition(aClient.location, "hello");
|
||||
}
|
||||
|
||||
function toggleBreakpoint() {
|
||||
|
@ -58,7 +58,7 @@ function test() {
|
||||
function setDummyConditional(aClient) {
|
||||
// This happens when a conditional expression input popup is shown
|
||||
// but the user doesn't type anything into it.
|
||||
aClient.condition = "";
|
||||
return gBreakpoints.updateCondition(aClient.location, '');
|
||||
}
|
||||
|
||||
function toggleBreakpoint() {
|
||||
|
@ -165,6 +165,7 @@ These should match what Safari and other Apple applications use on OS X Lion. --
|
||||
<!ENTITY stopButton.tooltip "Stop loading this page">
|
||||
<!ENTITY goEndCap.tooltip "Go to the address in the Location Bar">
|
||||
<!ENTITY printButton.label "Print">
|
||||
<!ENTITY printButton.tooltip "Print this page">
|
||||
|
||||
<!ENTITY locationItem.title "Location">
|
||||
<!ENTITY searchItem.title "Search">
|
||||
|
@ -157,8 +157,8 @@ browser.jar:
|
||||
skin/classic/browser/social/chat-icons.png (social/chat-icons.png)
|
||||
skin/classic/browser/social/gear_default.png (../shared/social/gear_default.png)
|
||||
skin/classic/browser/social/gear_clicked.png (../shared/social/gear_clicked.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (../shared/tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (../shared/tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/tab.png (tabbrowser/tab.png)
|
||||
skin/classic/browser/tabbrowser/tab-active-middle.png (tabbrowser/tab-active-middle.png)
|
||||
skin/classic/browser/tabbrowser/tab-background-end.png (tabbrowser/tab-background-end.png)
|
||||
|
Before Width: | Height: | Size: 8.3 KiB |
Before Width: | Height: | Size: 14 KiB |
@ -255,10 +255,10 @@ browser.jar:
|
||||
skin/classic/browser/tabbrowser/newtab@2x.png (tabbrowser/newtab@2x.png)
|
||||
skin/classic/browser/tabbrowser/newtab-inverted.png (tabbrowser/newtab-inverted.png)
|
||||
skin/classic/browser/tabbrowser/newtab-inverted@2x.png (tabbrowser/newtab-inverted@2x.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/connecting@2x.png (tabbrowser/connecting@2x.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/loading@2x.png (tabbrowser/loading@2x.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (../shared/tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/connecting@2x.png (../shared/tabbrowser/connecting@2x.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (../shared/tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/loading@2x.png (../shared/tabbrowser/loading@2x.png)
|
||||
skin/classic/browser/tabbrowser/tab-active-middle.png (tabbrowser/tab-active-middle.png)
|
||||
skin/classic/browser/tabbrowser/tab-active-middle@2x.png (tabbrowser/tab-active-middle@2x.png)
|
||||
skin/classic/browser/tabbrowser/tab-arrow-left.png (tabbrowser/tab-arrow-left.png)
|
||||
|
Before Width: | Height: | Size: 8.3 KiB |
Before Width: | Height: | Size: 29 KiB |
Before Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 39 KiB |
BIN
browser/themes/shared/tabbrowser/connecting.png
Normal file
After Width: | Height: | Size: 16 KiB |
BIN
browser/themes/shared/tabbrowser/connecting@2x.png
Normal file
After Width: | Height: | Size: 28 KiB |
BIN
browser/themes/shared/tabbrowser/loading.png
Normal file
After Width: | Height: | Size: 6.7 KiB |
BIN
browser/themes/shared/tabbrowser/loading@2x.png
Normal file
After Width: | Height: | Size: 15 KiB |
@ -182,8 +182,8 @@ browser.jar:
|
||||
skin/classic/browser/social/gear_clicked.png (../shared/social/gear_clicked.png)
|
||||
skin/classic/browser/tabbrowser/newtab.png (tabbrowser/newtab.png)
|
||||
skin/classic/browser/tabbrowser/newtab-inverted.png (tabbrowser/newtab-inverted.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/connecting.png (../shared/tabbrowser/connecting.png)
|
||||
skin/classic/browser/tabbrowser/loading.png (../shared/tabbrowser/loading.png)
|
||||
skin/classic/browser/tabbrowser/tab.png (tabbrowser/tab.png)
|
||||
skin/classic/browser/tabbrowser/tab-active-middle.png (tabbrowser/tab-active-middle.png)
|
||||
skin/classic/browser/tabbrowser/tab-active-middle@2x.png (tabbrowser/tab-active-middle@2x.png)
|
||||
@ -549,8 +549,8 @@ browser.jar:
|
||||
skin/classic/aero/browser/social/gear_clicked.png (../shared/social/gear_clicked.png)
|
||||
skin/classic/aero/browser/tabbrowser/newtab.png (tabbrowser/newtab.png)
|
||||
skin/classic/aero/browser/tabbrowser/newtab-inverted.png (tabbrowser/newtab-inverted.png)
|
||||
skin/classic/aero/browser/tabbrowser/connecting.png (tabbrowser/connecting.png)
|
||||
skin/classic/aero/browser/tabbrowser/loading.png (tabbrowser/loading.png)
|
||||
skin/classic/aero/browser/tabbrowser/connecting.png (../shared/tabbrowser/connecting.png)
|
||||
skin/classic/aero/browser/tabbrowser/loading.png (../shared/tabbrowser/loading.png)
|
||||
skin/classic/aero/browser/tabbrowser/tab.png (tabbrowser/tab.png)
|
||||
skin/classic/aero/browser/tabbrowser/tab-active-middle.png (tabbrowser/tab-active-middle.png)
|
||||
skin/classic/aero/browser/tabbrowser/tab-active-middle@2x.png (tabbrowser/tab-active-middle@2x.png)
|
||||
|
Before Width: | Height: | Size: 8.3 KiB |
Before Width: | Height: | Size: 10 KiB |
@ -357,6 +357,7 @@ RtspMediaResource::RtspMediaResource(MediaDecoder* aDecoder,
|
||||
: BaseMediaResource(aDecoder, aChannel, aURI, aContentType)
|
||||
, mIsConnected(false)
|
||||
, mRealTime(false)
|
||||
, mIsSuspend(true)
|
||||
{
|
||||
#ifndef NECKO_PROTOCOL_rtsp
|
||||
MOZ_CRASH("Should not be called except for B2G platform");
|
||||
@ -384,6 +385,28 @@ RtspMediaResource::~RtspMediaResource()
|
||||
}
|
||||
}
|
||||
|
||||
void RtspMediaResource::SetSuspend(bool aIsSuspend)
|
||||
{
|
||||
NS_ASSERTION(!NS_IsMainThread(), "Don't call on main thread");
|
||||
RTSPMLOG("SetSuspend %d",aIsSuspend);
|
||||
|
||||
nsCOMPtr<nsIRunnable> runnable =
|
||||
NS_NewRunnableMethodWithArg<bool>(this, &RtspMediaResource::NotifySuspend,
|
||||
aIsSuspend);
|
||||
NS_DispatchToMainThread(runnable);
|
||||
}
|
||||
|
||||
void RtspMediaResource::NotifySuspend(bool aIsSuspend)
|
||||
{
|
||||
NS_ASSERTION(NS_IsMainThread(), "Only call on main thread");
|
||||
RTSPMLOG("NotifySuspend %d",aIsSuspend);
|
||||
|
||||
mIsSuspend = aIsSuspend;
|
||||
if (mDecoder) {
|
||||
mDecoder->NotifySuspendedStatusChanged();
|
||||
}
|
||||
}
|
||||
|
||||
size_t
|
||||
RtspMediaResource::SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const
|
||||
{
|
||||
@ -638,6 +661,8 @@ RtspMediaResource::OnDisconnected(uint8_t aTrackIdx, nsresult aReason)
|
||||
void RtspMediaResource::Suspend(bool aCloseImmediately)
|
||||
{
|
||||
NS_ASSERTION(NS_IsMainThread(), "Don't call on non-main thread");
|
||||
|
||||
mIsSuspend = true;
|
||||
if (NS_WARN_IF(!mDecoder)) {
|
||||
return;
|
||||
}
|
||||
@ -649,11 +674,14 @@ void RtspMediaResource::Suspend(bool aCloseImmediately)
|
||||
|
||||
mMediaStreamController->Suspend();
|
||||
element->DownloadSuspended();
|
||||
mDecoder->NotifySuspendedStatusChanged();
|
||||
}
|
||||
|
||||
void RtspMediaResource::Resume()
|
||||
{
|
||||
NS_ASSERTION(NS_IsMainThread(), "Don't call on non-main thread");
|
||||
|
||||
mIsSuspend = false;
|
||||
if (NS_WARN_IF(!mDecoder)) {
|
||||
return;
|
||||
}
|
||||
@ -667,6 +695,7 @@ void RtspMediaResource::Resume()
|
||||
element->DownloadResumed();
|
||||
}
|
||||
mMediaStreamController->Resume();
|
||||
mDecoder->NotifySuspendedStatusChanged();
|
||||
}
|
||||
|
||||
nsresult RtspMediaResource::Open(nsIStreamListener **aStreamListener)
|
||||
|
@ -93,6 +93,10 @@ public:
|
||||
return mRealTime;
|
||||
}
|
||||
|
||||
// Called by RtspOmxReader, dispatch a runnable to notify mDecoder.
|
||||
// Other thread only.
|
||||
void SetSuspend(bool aIsSuspend);
|
||||
|
||||
// The following methods can be called on any thread except main thread.
|
||||
|
||||
// Read data from track.
|
||||
@ -137,8 +141,7 @@ public:
|
||||
virtual void Pin() MOZ_OVERRIDE {}
|
||||
virtual void Unpin() MOZ_OVERRIDE {}
|
||||
|
||||
// dummy
|
||||
virtual bool IsSuspendedByCache() MOZ_OVERRIDE { return false; }
|
||||
virtual bool IsSuspendedByCache() MOZ_OVERRIDE { return mIsSuspend; }
|
||||
|
||||
virtual bool IsSuspended() MOZ_OVERRIDE { return false; }
|
||||
virtual bool IsTransportSeekable() MOZ_OVERRIDE { return true; }
|
||||
@ -224,6 +227,8 @@ protected:
|
||||
nsRefPtr<Listener> mListener;
|
||||
|
||||
private:
|
||||
// Notify mDecoder the rtsp stream is suspend. Main thread only.
|
||||
void NotifySuspend(bool aIsSuspend);
|
||||
bool IsVideoEnabled();
|
||||
bool IsVideo(uint8_t tracks, nsIStreamingProtocolMetaData *meta);
|
||||
// These two members are created at |RtspMediaResource::OnConnected|.
|
||||
@ -235,6 +240,8 @@ private:
|
||||
bool mIsConnected;
|
||||
// live stream
|
||||
bool mRealTime;
|
||||
// Indicate the rtsp controller is suspended or not. Main thread only.
|
||||
bool mIsSuspend;
|
||||
};
|
||||
|
||||
} // namespace mozilla
|
||||
|
@ -322,6 +322,7 @@ void RtspOmxReader::SetIdle() {
|
||||
if (controller) {
|
||||
controller->Pause();
|
||||
}
|
||||
mRtspResource->SetSuspend(true);
|
||||
}
|
||||
}
|
||||
|
||||
@ -333,6 +334,7 @@ void RtspOmxReader::SetActive() {
|
||||
if (controller) {
|
||||
controller->Play();
|
||||
}
|
||||
mRtspResource->SetSuspend(false);
|
||||
}
|
||||
|
||||
// Call parent class to set OMXCodec active.
|
||||
|
@ -11,7 +11,6 @@ const Cr = Components.results;
|
||||
|
||||
Cu.import("resource://gre/modules/osfile.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/Task.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Promise.jsm");
|
||||
|
||||
|
@ -5,11 +5,12 @@
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "BluetoothProfileController.h"
|
||||
#include "BluetoothReplyRunnable.h"
|
||||
|
||||
#include "BluetoothA2dpManager.h"
|
||||
#include "BluetoothHfpManager.h"
|
||||
#include "BluetoothHidManager.h"
|
||||
#include "BluetoothReplyRunnable.h"
|
||||
#include "BluetoothService.h"
|
||||
#include "BluetoothUtils.h"
|
||||
|
||||
#include "mozilla/dom/bluetooth/BluetoothTypes.h"
|
||||
@ -217,6 +218,11 @@ BluetoothProfileController::StartSession()
|
||||
MOZ_ASSERT(mProfilesIndex == -1);
|
||||
MOZ_ASSERT(mTimer);
|
||||
|
||||
if (!IsBtServiceAvailable()) {
|
||||
EndSession();
|
||||
return;
|
||||
}
|
||||
|
||||
if (mProfiles.Length() < 1) {
|
||||
BT_LOGR("No queued profile.");
|
||||
EndSession();
|
||||
@ -240,6 +246,12 @@ BluetoothProfileController::EndSession()
|
||||
|
||||
BT_LOGR("mSuccess %d", mSuccess);
|
||||
|
||||
// Don't have to check profile status and retrigger session after connection
|
||||
// timeout, since session is end.
|
||||
if (mTimer) {
|
||||
mTimer->Cancel();
|
||||
}
|
||||
|
||||
// The action has completed, so the DOM request should be replied then invoke
|
||||
// the callback.
|
||||
if (mSuccess) {
|
||||
@ -265,6 +277,11 @@ BluetoothProfileController::Next()
|
||||
|
||||
mCurrentProfileFinished = false;
|
||||
|
||||
if (!IsBtServiceAvailable()) {
|
||||
EndSession();
|
||||
return;
|
||||
}
|
||||
|
||||
if (++mProfilesIndex >= (int)mProfiles.Length()) {
|
||||
EndSession();
|
||||
return;
|
||||
@ -279,6 +296,13 @@ BluetoothProfileController::Next()
|
||||
}
|
||||
}
|
||||
|
||||
bool
|
||||
BluetoothProfileController::IsBtServiceAvailable() const
|
||||
{
|
||||
BluetoothService* bs = BluetoothService::Get();
|
||||
return (bs && bs->IsEnabled() && !bs->IsToggling());
|
||||
}
|
||||
|
||||
void
|
||||
BluetoothProfileController::NotifyCompletion(const nsAString& aErrorStr)
|
||||
{
|
||||
@ -308,6 +332,11 @@ BluetoothProfileController::GiveupAndContinue()
|
||||
|
||||
BT_LOGR_PROFILE(mProfiles[mProfilesIndex], ERR_OPERATION_TIMEOUT);
|
||||
mProfiles[mProfilesIndex]->Reset();
|
||||
Next();
|
||||
|
||||
if (IsBtServiceAvailable()) {
|
||||
Next();
|
||||
} else {
|
||||
EndSession();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -122,6 +122,9 @@ private:
|
||||
// Connect/Disconnect next profile in the array
|
||||
void Next();
|
||||
|
||||
// Is Bluetooth service available for profile connection/disconnection ?
|
||||
bool IsBtServiceAvailable() const;
|
||||
|
||||
const bool mConnect;
|
||||
nsString mDeviceAddress;
|
||||
nsRefPtr<BluetoothReplyRunnable> mRunnable;
|
||||
|
@ -95,6 +95,14 @@ public:
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
// Bluetooth just enabled, clear profile controllers and runnable arrays.
|
||||
sControllerArray.Clear();
|
||||
sBondingRunnableArray.Clear();
|
||||
sChangeDiscoveryRunnableArray.Clear();
|
||||
sGetDeviceRunnableArray.Clear();
|
||||
sSetPropertyRunnableArray.Clear();
|
||||
sUnbondingRunnableArray.Clear();
|
||||
|
||||
// Bluetooth scan mode is NONE by default
|
||||
bt_scan_mode_t mode = BT_SCAN_MODE_CONNECTABLE;
|
||||
bt_property_t prop;
|
||||
@ -1149,8 +1157,9 @@ NextBluetoothProfileController()
|
||||
NS_ENSURE_FALSE_VOID(sControllerArray.IsEmpty());
|
||||
sControllerArray.RemoveElementAt(0);
|
||||
// Re-check if the task array is empty, if it's not, the next task will begin.
|
||||
NS_ENSURE_FALSE_VOID(sControllerArray.IsEmpty());
|
||||
sControllerArray[0]->StartSession();
|
||||
if (!sControllerArray.IsEmpty()) {
|
||||
sControllerArray[0]->StartSession();
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -254,9 +254,9 @@ BrowserElementParent.prototype = {
|
||||
"hello": this._recvHello,
|
||||
"contextmenu": this._fireCtxMenuEvent,
|
||||
"locationchange": this._fireEventFromMsg,
|
||||
"loadstart": this._fireEventFromMsg,
|
||||
"loadend": this._fireEventFromMsg,
|
||||
"titlechange": this._fireEventFromMsg,
|
||||
"loadstart": this._fireProfiledEventFromMsg,
|
||||
"loadend": this._fireProfiledEventFromMsg,
|
||||
"titlechange": this._fireProfiledEventFromMsg,
|
||||
"iconchange": this._fireEventFromMsg,
|
||||
"manifestchange": this._fireEventFromMsg,
|
||||
"metachange": this._fireEventFromMsg,
|
||||
@ -267,8 +267,8 @@ BrowserElementParent.prototype = {
|
||||
"securitychange": this._fireEventFromMsg,
|
||||
"error": this._fireEventFromMsg,
|
||||
"scroll": this._fireEventFromMsg,
|
||||
"firstpaint": this._fireEventFromMsg,
|
||||
"documentfirstpaint": this._fireEventFromMsg,
|
||||
"firstpaint": this._fireProfiledEventFromMsg,
|
||||
"documentfirstpaint": this._fireProfiledEventFromMsg,
|
||||
"nextpaint": this._recvNextPaint,
|
||||
"keyevent": this._fireKeyEvent,
|
||||
"showmodalprompt": this._handleShowModalPrompt,
|
||||
@ -407,6 +407,16 @@ BrowserElementParent.prototype = {
|
||||
return !this._frameElement.dispatchEvent(evt);
|
||||
},
|
||||
|
||||
/**
|
||||
* add profiler marker for each event fired.
|
||||
*/
|
||||
_fireProfiledEventFromMsg: function(data) {
|
||||
if (Services.profiler !== undefined) {
|
||||
Services.profiler.AddMarker(data.json.msg_name);
|
||||
}
|
||||
this._fireEventFromMsg(data);
|
||||
},
|
||||
|
||||
/**
|
||||
* Fire either a vanilla or a custom event, depending on the contents of
|
||||
* |data|.
|
||||
|
@ -15,9 +15,11 @@ const Cu = Components.utils;
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/IndexedDBHelper.jsm");
|
||||
Cu.import("resource://gre/modules/PhoneNumberUtils.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumberUtils",
|
||||
"resource://gre/modules/PhoneNumberUtils.jsm");
|
||||
Cu.importGlobalProperties(["indexedDB"]);
|
||||
|
||||
/* all exported symbols need to be bound to this on B2G - Bug 961777 */
|
||||
|
@ -15,8 +15,11 @@ this.EXPORTED_SYMBOLS = ["ContactService"];
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/ContactDB.jsm");
|
||||
Cu.import("resource://gre/modules/PhoneNumberUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "ContactDB",
|
||||
"resource://gre/modules/ContactDB.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumberUtils",
|
||||
"resource://gre/modules/PhoneNumberUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyServiceGetter(this, "ppmm",
|
||||
"@mozilla.org/parentprocessmessagemanager;1",
|
||||
|
@ -265,6 +265,24 @@ function ensureMobileConnection(aAdditionalPermissions, aServiceId) {
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get MozMobileConnection by ServiceId
|
||||
*
|
||||
* @param aServiceId [optional]
|
||||
* A numeric DSDS service id. Default: the one indicated in
|
||||
* start*TestCommon() or 0 if not indicated.
|
||||
*
|
||||
* @return A MozMobileConnection.
|
||||
*/
|
||||
function getMozMobileConnectionByServiceId(aServiceId) {
|
||||
let mobileConn = mobileConnection;
|
||||
if (aServiceId !== undefined) {
|
||||
mobileConn =
|
||||
workingFrame.contentWindow.navigator.mozMobileConnections[aServiceId];
|
||||
}
|
||||
return mobileConn;
|
||||
}
|
||||
|
||||
/**
|
||||
* Wait for one named MobileConnection event.
|
||||
*
|
||||
@ -283,11 +301,7 @@ function ensureMobileConnection(aAdditionalPermissions, aServiceId) {
|
||||
function waitForManagerEvent(aEventName, aServiceId) {
|
||||
let deferred = Promise.defer();
|
||||
|
||||
let mobileConn = mobileConnection;
|
||||
if (aServiceId !== undefined) {
|
||||
mobileConn =
|
||||
workingFrame.contentWindow.navigator.mozMobileConnections[aServiceId];
|
||||
}
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
|
||||
mobileConn.addEventListener(aEventName, function onevent(aEvent) {
|
||||
mobileConn.removeEventListener(aEventName, onevent);
|
||||
@ -426,11 +440,7 @@ function setDataEnabledAndWait(aEnabled, aServiceId) {
|
||||
promises.push(waitForManagerEvent("datachange", aServiceId));
|
||||
promises.push(setDataEnabled(aEnabled));
|
||||
Promise.all(promises).then(function keepWaiting() {
|
||||
let mobileConn = mobileConnection;
|
||||
if (aServiceId !== undefined) {
|
||||
mobileConn =
|
||||
workingFrame.contentWindow.navigator.mozMobileConnections[aServiceId];
|
||||
}
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
// To ignore some transient states, we only resolve that deferred promise
|
||||
// when the |connected| state equals to the expected one and never rejects.
|
||||
let connected = mobileConn.data.connected;
|
||||
@ -445,6 +455,114 @@ function setDataEnabledAndWait(aEnabled, aServiceId) {
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set radio enabling state.
|
||||
*
|
||||
* Resolve no matter the request succeeds or fails. Never reject.
|
||||
*
|
||||
* Fulfill params: (none)
|
||||
*
|
||||
* @param aEnabled
|
||||
* A boolean state.
|
||||
* @param aServiceId [optional]
|
||||
* A numeric DSDS service id. Default: the one indicated in
|
||||
* start*TestCommon() or 0 if not indicated.
|
||||
*
|
||||
* @return A deferred promise.
|
||||
*/
|
||||
function setRadioEnabled(aEnabled, aServiceId) {
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
let request = mobileConn.setRadioEnabled(aEnabled);
|
||||
return wrapDomRequestAsPromise(request)
|
||||
.then(function onsuccess() {
|
||||
ok(true, "setRadioEnabled " + aEnabled + " on " + aServiceId + " success.");
|
||||
}, function onerror() {
|
||||
ok(false, "setRadioEnabled " + aEnabled + " on " + aServiceId + " " +
|
||||
request.error.name);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Set radio enabling state and wait for "radiostatechange" event.
|
||||
*
|
||||
* Resolve if radio state changed to the expected one. Never reject.
|
||||
*
|
||||
* Fulfill params: (none)
|
||||
*
|
||||
* @param aEnabled
|
||||
* A boolean state.
|
||||
* @param aServiceId [optional]
|
||||
* A numeric DSDS service id. Default: the one indicated in
|
||||
* start*TestCommon() or 0 if not indicated.
|
||||
*
|
||||
* @return A deferred promise.
|
||||
*/
|
||||
function setRadioEnabledAndWait(aEnabled, aServiceId) {
|
||||
let deferred = Promise.defer();
|
||||
|
||||
let promises = [];
|
||||
promises.push(waitForManagerEvent("radiostatechange", aServiceId));
|
||||
promises.push(setRadioEnabled(aEnabled, aServiceId));
|
||||
Promise.all(promises).then(function keepWaiting() {
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
// To ignore some transient states, we only resolve that deferred promise
|
||||
// when |radioState| equals to the expected one and never rejects.
|
||||
let state = mobileConn.radioState;
|
||||
aEnabled = aEnabled ? "enabled" : "disabled";
|
||||
if (state == aEnabled) {
|
||||
deferred.resolve();
|
||||
return;
|
||||
}
|
||||
|
||||
return waitForManagerEvent("radiostatechange", aServiceId).then(keepWaiting);
|
||||
});
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set CLIR (calling line id restriction).
|
||||
*
|
||||
* Fulfill params: (none)
|
||||
* Reject params:
|
||||
* 'RadioNotAvailable', 'RequestNotSupported', or 'GenericFailure'
|
||||
*
|
||||
* @param aMode
|
||||
* A short number.
|
||||
* @param aServiceId [optional]
|
||||
* A numeric DSDS service id. Default: the one indicated in
|
||||
* start*TestCommon() or 0 if not indicated.
|
||||
*
|
||||
* @return A deferred promise.
|
||||
*/
|
||||
function setClir(aMode, aServiceId) {
|
||||
ok(true, "setClir(" + aMode + ", " + aServiceId + ")");
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
let request = mobileConn.setCallingLineIdRestriction(aMode);
|
||||
return wrapDomRequestAsPromise(request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get CLIR (calling line id restriction).
|
||||
*
|
||||
* Fulfill params:
|
||||
* CLIR mode.
|
||||
* Reject params:
|
||||
* 'RadioNotAvailable', 'RequestNotSupported', or 'GenericFailure'
|
||||
*
|
||||
* @param aServiceId [optional]
|
||||
* A numeric DSDS service id. Default: the one indicated in
|
||||
* start*TestCommon() or 0 if not indicated.
|
||||
*
|
||||
* @return A deferred promise.
|
||||
*/
|
||||
function getClir(aServiceId) {
|
||||
ok(true, "getClir(" + aServiceId + ")");
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
let request = mobileConn.getCallingLineIdRestriction();
|
||||
return wrapDomRequestAsPromise(request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set voice/data state and wait for state change.
|
||||
*
|
||||
@ -487,11 +605,7 @@ function setEmulatorRoamingAndWait(aRoaming, aServiceId) {
|
||||
let state = (aRoaming ? "roaming" : "home");
|
||||
return setEmulatorVoiceDataStateAndWait(aWhich, state, aServiceId)
|
||||
.then(() => {
|
||||
let mobileConn = mobileConnection;
|
||||
if (aServiceId !== undefined) {
|
||||
mobileConn =
|
||||
workingFrame.contentWindow.navigator.mozMobileConnections[aServiceId];
|
||||
}
|
||||
let mobileConn = getMozMobileConnectionByServiceId(aServiceId);
|
||||
is(mobileConn[aWhich].roaming, aRoaming,
|
||||
aWhich + ".roaming")
|
||||
});
|
||||
|
@ -27,3 +27,4 @@ qemu = true
|
||||
[test_mobile_data_ipv6.js]
|
||||
disabled = Bug 979137
|
||||
[test_dsds_mobile_data_connection.js]
|
||||
[test_mobile_clir_radio_off.js]
|
||||
|
@ -0,0 +1,36 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
MARIONETTE_TIMEOUT = 60000;
|
||||
MARIONETTE_HEAD_JS = "head.js";
|
||||
|
||||
function testSetClirOnRadioOff(aMode) {
|
||||
log("testSetClirOnRadioOff (set to mode: " + aMode + ")");
|
||||
return Promise.resolve()
|
||||
.then(() => setClir(aMode))
|
||||
.then(() => {
|
||||
ok(false, "shouldn't resolve");
|
||||
}, (evt) => {
|
||||
is(evt.target.error.name, "RadioNotAvailable");
|
||||
});
|
||||
}
|
||||
|
||||
function testGetClirOnRadioOff() {
|
||||
log("testGetClirOnRadioOff");
|
||||
return Promise.resolve()
|
||||
.then(() => getClir())
|
||||
.then(() => {
|
||||
ok(false, "shouldn't resolve");
|
||||
}, (evt) => {
|
||||
is(evt.target.error.name, "RadioNotAvailable");
|
||||
});
|
||||
}
|
||||
|
||||
startTestCommon(function() {
|
||||
return setRadioEnabledAndWait(false)
|
||||
.then(() => testSetClirOnRadioOff(0))
|
||||
.then(() => testGetClirOnRadioOff())
|
||||
// Restore radio state.
|
||||
.then(() => setRadioEnabledAndWait(true),
|
||||
() => setRadioEnabledAnWait(true));
|
||||
});
|
@ -189,6 +189,9 @@ function getRadioDisabledState() {
|
||||
function MmsConnection(aServiceId) {
|
||||
this.serviceId = aServiceId;
|
||||
this.radioInterface = gRil.getRadioInterface(aServiceId);
|
||||
this.pendingCallbacks = [];
|
||||
this.connectTimer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
|
||||
this.disconnectTimer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
|
||||
};
|
||||
|
||||
MmsConnection.prototype = {
|
||||
@ -232,14 +235,14 @@ MmsConnection.prototype = {
|
||||
//A queue to buffer the MMS HTTP requests when the MMS network
|
||||
//is not yet connected. The buffered requests will be cleared
|
||||
//if the MMS network fails to be connected within a timer.
|
||||
pendingCallbacks: [],
|
||||
pendingCallbacks: null,
|
||||
|
||||
/** MMS network connection reference count. */
|
||||
refCount: 0,
|
||||
|
||||
connectTimer: Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer),
|
||||
connectTimer: null,
|
||||
|
||||
disconnectTimer: Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer),
|
||||
disconnectTimer: null,
|
||||
|
||||
/**
|
||||
* Callback when |connectTimer| is timeout or cancelled by shutdown.
|
||||
@ -1324,6 +1327,9 @@ SendTransaction.prototype = Object.create(CancellableTransaction.prototype, {
|
||||
}
|
||||
|
||||
let response = MMS.PduHelper.parse(data, null);
|
||||
if (DEBUG) {
|
||||
debug("Parsed M-Send.conf: " + JSON.stringify(response));
|
||||
}
|
||||
if (!response || (response.type != MMS.MMS_PDU_TYPE_SEND_CONF)) {
|
||||
callback(MMS.MMS_PDU_RESPONSE_ERROR_UNSUPPORTED_MESSAGE, null);
|
||||
return;
|
||||
|
@ -11,8 +11,11 @@ Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/PhoneNumberUtils.jsm");
|
||||
Cu.importGlobalProperties(["indexedDB"]);
|
||||
|
||||
var RIL = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", RIL);
|
||||
XPCOMUtils.defineLazyGetter(this, "RIL", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
const RIL_GETMESSAGESCURSOR_CID =
|
||||
Components.ID("{484d1ad8-840e-4782-9dc4-9ebc4d914937}");
|
||||
|
@ -6,6 +6,4 @@ qemu=true
|
||||
[test_ndef.js]
|
||||
[test_nfc_enabled.js]
|
||||
[test_nfc_manager_tech_discovered.js]
|
||||
disabled = Bug 996426
|
||||
[test_nfc_peer.js]
|
||||
disabled = Bug 996426
|
||||
|
@ -8,9 +8,13 @@
|
||||
|
||||
this.EXPORTED_SYMBOLS = ["PhoneNumber"];
|
||||
|
||||
Components.utils.import("resource://gre/modules/PhoneNumberMetaData.jsm");
|
||||
Components.utils.import("resource://gre/modules/PhoneNumberNormalizer.jsm");
|
||||
const Cu = Components.utils;
|
||||
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PHONE_NUMBER_META_DATA",
|
||||
"resource://gre/modules/PhoneNumberMetaData.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumberNormalizer",
|
||||
"resource://gre/modules/PhoneNumberNormalizer.jsm");
|
||||
this.PhoneNumber = (function (dataBase) {
|
||||
// Use strict in our context only - users might not want it
|
||||
'use strict';
|
||||
|
@ -14,8 +14,10 @@ const Ci = Components.interfaces;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
Cu.import("resource://gre/modules/PhoneNumberNormalizer.jsm");
|
||||
Cu.import("resource://gre/modules/mcc_iso3166_table.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumberNormalizer",
|
||||
"resource://gre/modules/PhoneNumberNormalizer.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "MCC_ISO3166_TABLE",
|
||||
"resource://gre/modules/mcc_iso3166_table.jsm");
|
||||
|
||||
#ifdef MOZ_B2G_RIL
|
||||
XPCOMUtils.defineLazyServiceGetter(this, "mobileConnection",
|
||||
@ -196,7 +198,8 @@ this.PhoneNumberUtils = {
|
||||
let inParent = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime)
|
||||
.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT;
|
||||
if (inParent) {
|
||||
Cu.import("resource://gre/modules/PhoneNumber.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PhoneNumber",
|
||||
"resource://gre/modules/PhoneNumber.jsm");
|
||||
XPCOMUtils.defineLazyServiceGetter(this, "ppmm",
|
||||
"@mozilla.org/parentprocessmessagemanager;1",
|
||||
"nsIMessageListenerManager");
|
||||
|
@ -22,8 +22,11 @@ const {classes: Cc, interfaces: Ci, utils: Cu, results: Cr} = Components;
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
let NFC = {};
|
||||
Cu.import("resource://gre/modules/nfc_consts.js", NFC);
|
||||
XPCOMUtils.defineLazyGetter(this, "NFC", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/nfc_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
Cu.import("resource://gre/modules/systemlibs.js");
|
||||
const NFC_ENABLED = libcutils.property_get("ro.moz.nfc.enabled", "false") === "true";
|
||||
|
@ -23,8 +23,11 @@ Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/DOMRequestHelper.jsm");
|
||||
|
||||
let NFC = {};
|
||||
Cu.import("resource://gre/modules/nfc_consts.js", NFC);
|
||||
XPCOMUtils.defineLazyGetter(this, "NFC", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/nfc_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
Cu.import("resource://gre/modules/systemlibs.js");
|
||||
const NFC_ENABLED = libcutils.property_get("ro.moz.nfc.enabled", "false") === "true";
|
||||
|
@ -21,8 +21,11 @@ Cu.import("resource://gre/modules/DOMRequestHelper.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
var RIL = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", RIL);
|
||||
XPCOMUtils.defineLazyGetter(this, "RIL", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
const NS_XPCOM_SHUTDOWN_OBSERVER_ID = "xpcom-shutdown";
|
||||
|
||||
@ -1378,6 +1381,13 @@ RILContentHelper.prototype = {
|
||||
let request = Services.DOMRequest.createRequest(window);
|
||||
let requestId = this.getRequestId(request);
|
||||
|
||||
let radioState = this.rilContexts[clientId].radioState;
|
||||
if (radioState !== RIL.GECKO_DETAILED_RADIOSTATE_ENABLED) {
|
||||
this.dispatchFireRequestError(requestId,
|
||||
RIL.GECKO_ERROR_RADIO_NOT_AVAILABLE);
|
||||
return request;
|
||||
}
|
||||
|
||||
cpmm.sendAsyncMessage("RIL:GetCallingLineIdRestriction", {
|
||||
clientId: clientId,
|
||||
data: {
|
||||
@ -1389,7 +1399,6 @@ RILContentHelper.prototype = {
|
||||
},
|
||||
|
||||
setCallingLineIdRestriction: function(clientId, window, clirMode) {
|
||||
|
||||
if (window == null) {
|
||||
throw Components.Exception("Can't get window object",
|
||||
Cr.NS_ERROR_UNEXPECTED);
|
||||
@ -1397,6 +1406,13 @@ RILContentHelper.prototype = {
|
||||
let request = Services.DOMRequest.createRequest(window);
|
||||
let requestId = this.getRequestId(request);
|
||||
|
||||
let radioState = this.rilContexts[clientId].radioState;
|
||||
if (radioState !== RIL.GECKO_DETAILED_RADIOSTATE_ENABLED) {
|
||||
this.dispatchFireRequestError(requestId,
|
||||
RIL.GECKO_ERROR_RADIO_NOT_AVAILABLE);
|
||||
return request;
|
||||
}
|
||||
|
||||
cpmm.sendAsyncMessage("RIL:SetCallingLineIdRestriction", {
|
||||
clientId: clientId,
|
||||
data: {
|
||||
|
@ -24,8 +24,11 @@ Cu.import("resource://gre/modules/systemlibs.js");
|
||||
Cu.import("resource://gre/modules/Promise.jsm");
|
||||
Cu.import("resource://gre/modules/FileUtils.jsm");
|
||||
|
||||
var RIL = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", RIL);
|
||||
XPCOMUtils.defineLazyGetter(this, "RIL", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
// set to true in ril_consts.js to see debug messages
|
||||
var DEBUG = RIL.DEBUG_RIL;
|
||||
@ -96,7 +99,6 @@ const kSettingsTimezoneAutoUpdateAvailable = "time.timezone.automatic-update.ava
|
||||
const NS_PREFBRANCH_PREFCHANGE_TOPIC_ID = "nsPref:changed";
|
||||
|
||||
const kPrefCellBroadcastDisabled = "ril.cellbroadcast.disabled";
|
||||
const kPrefClirModePreference = "ril.clirMode";
|
||||
const kPrefRilNumRadioInterfaces = "ril.numRadioInterfaces";
|
||||
|
||||
const DOM_MOBILE_MESSAGE_DELIVERY_RECEIVED = "received";
|
||||
@ -1623,7 +1625,6 @@ WorkerMessenger.prototype = {
|
||||
let options = {
|
||||
debug: DEBUG,
|
||||
cellBroadcastDisabled: false,
|
||||
clirMode: RIL.CLIR_DEFAULT,
|
||||
quirks: {
|
||||
callstateExtraUint32:
|
||||
libcutils.property_get("ro.moz.ril.callstate_extra_int", "false") === "true",
|
||||
@ -1651,10 +1652,6 @@ WorkerMessenger.prototype = {
|
||||
Services.prefs.getBoolPref(kPrefCellBroadcastDisabled);
|
||||
} catch(e) {}
|
||||
|
||||
try {
|
||||
options.clirMode = Services.prefs.getIntPref(kPrefClirModePreference);
|
||||
} catch(e) {}
|
||||
|
||||
this.send(null, "setInitialOptions", options);
|
||||
},
|
||||
|
||||
@ -3502,16 +3499,6 @@ RadioInterface.prototype = {
|
||||
this.clientId, message);
|
||||
},
|
||||
|
||||
_updateCallingLineIdRestrictionPref: function(mode) {
|
||||
try {
|
||||
Services.prefs.setIntPref(kPrefClirModePreference, mode);
|
||||
Services.prefs.savePrefFile(null);
|
||||
if (DEBUG) {
|
||||
this.debug(kPrefClirModePreference + " pref is now " + mode);
|
||||
}
|
||||
} catch (e) {}
|
||||
},
|
||||
|
||||
sendMMI: function(target, message) {
|
||||
if (DEBUG) this.debug("SendMMI " + JSON.stringify(message));
|
||||
this.workerMessenger.send("sendMMI", message, (function(response) {
|
||||
@ -3519,7 +3506,6 @@ RadioInterface.prototype = {
|
||||
this._sendCfStateChanged(response);
|
||||
} else if (response.isSetCLIR && response.success) {
|
||||
this._sendClirModeChanged(response.clirMode);
|
||||
this._updateCallingLineIdRestrictionPref(response.clirMode);
|
||||
}
|
||||
|
||||
target.sendAsyncMessage("RIL:SendMMI", {
|
||||
@ -3550,7 +3536,6 @@ RadioInterface.prototype = {
|
||||
this.workerMessenger.send("setCLIR", message, (function(response) {
|
||||
if (response.success) {
|
||||
this._sendClirModeChanged(response.clirMode);
|
||||
this._updateCallingLineIdRestrictionPref(response.clirMode);
|
||||
}
|
||||
target.sendAsyncMessage("RIL:SetCallingLineIdRestriction", {
|
||||
clientId: this.clientId,
|
||||
|
@ -53,7 +53,6 @@ if (!this.debug) {
|
||||
}
|
||||
|
||||
let RIL_CELLBROADCAST_DISABLED;
|
||||
let RIL_CLIR_MODE;
|
||||
let RIL_EMERGENCY_NUMBERS;
|
||||
const DEFAULT_EMERGENCY_NUMBERS = ["112", "911"];
|
||||
|
||||
@ -226,7 +225,6 @@ function RilObject(aContext) {
|
||||
// Init properties that are only initialized once.
|
||||
this.v5Legacy = RILQUIRKS_V5_LEGACY;
|
||||
this.cellBroadcastDisabled = RIL_CELLBROADCAST_DISABLED;
|
||||
this.clirMode = RIL_CLIR_MODE;
|
||||
|
||||
this._hasHangUpPendingOutgoingCall = false;
|
||||
}
|
||||
@ -271,11 +269,6 @@ RilObject.prototype = {
|
||||
*/
|
||||
cellBroadcastDisabled: false,
|
||||
|
||||
/**
|
||||
* Global CLIR mode settings.
|
||||
*/
|
||||
clirMode: CLIR_DEFAULT,
|
||||
|
||||
/**
|
||||
* Parsed Cell Broadcast search lists.
|
||||
* cellBroadcastConfigs.MMI should be preserved over rild reset.
|
||||
@ -1121,13 +1114,10 @@ RilObject.prototype = {
|
||||
* nsIDOMMozMobileConnection interface.
|
||||
*/
|
||||
setCLIR: function(options) {
|
||||
if (options) {
|
||||
this.clirMode = options.clirMode;
|
||||
}
|
||||
let Buf = this.context.Buf;
|
||||
Buf.newParcel(REQUEST_SET_CLIR, options);
|
||||
Buf.writeInt32(1);
|
||||
Buf.writeInt32(this.clirMode);
|
||||
Buf.writeInt32(options.clirMode);
|
||||
Buf.sendParcel();
|
||||
},
|
||||
|
||||
@ -6489,7 +6479,6 @@ RilObject.prototype[UNSOLICITED_RESPONSE_RADIO_STATE_CHANGED] = function UNSOLIC
|
||||
this.getBasebandVersion();
|
||||
this.updateCellBroadcastConfig();
|
||||
this.setPreferredNetworkType();
|
||||
this.setCLIR();
|
||||
if ((RILQUIRKS_DATA_REGISTRATION_ON_DEMAND ||
|
||||
RILQUIRKS_SUBSCRIPTION_CONTROL) &&
|
||||
this._attachDataRegistration) {
|
||||
@ -14747,7 +14736,6 @@ let ContextPool = {
|
||||
DEBUG = DEBUG_WORKER || aOptions.debug;
|
||||
RIL_EMERGENCY_NUMBERS = aOptions.rilEmergencyNumbers;
|
||||
RIL_CELLBROADCAST_DISABLED = aOptions.cellBroadcastDisabled;
|
||||
RIL_CLIR_MODE = aOptions.clirMode;
|
||||
|
||||
let quirks = aOptions.quirks;
|
||||
RILQUIRKS_CALLSTATE_EXTRA_UINT32 = quirks.callstateExtraUint32;
|
||||
|
@ -11,8 +11,11 @@ Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/Promise.jsm");
|
||||
|
||||
var RIL = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", RIL);
|
||||
XPCOMUtils.defineLazyGetter(this, "RIL", function () {
|
||||
let obj = {};
|
||||
Cu.import("resource://gre/modules/ril_consts.js", obj);
|
||||
return obj;
|
||||
});
|
||||
|
||||
const GONK_TELEPHONYPROVIDER_CONTRACTID =
|
||||
"@mozilla.org/telephony/gonktelephonyprovider;1";
|
||||
|
@ -10,6 +10,7 @@ enum WifiWPSMethod {
|
||||
|
||||
enum ConnectionStatus {
|
||||
"connecting",
|
||||
"authenticating",
|
||||
"associated",
|
||||
"connected",
|
||||
"disconnected",
|
||||
@ -53,6 +54,7 @@ dictionary NetworkProperties {
|
||||
DOMString eap;
|
||||
DOMString pin;
|
||||
boolean dontConnect;
|
||||
DOMString serverCertificate;
|
||||
};
|
||||
|
||||
[Constructor(optional NetworkProperties properties),
|
||||
@ -87,6 +89,7 @@ interface MozWifiNetwork {
|
||||
attribute DOMString? eap;
|
||||
attribute DOMString? pin;
|
||||
attribute boolean? dontConnect;
|
||||
attribute DOMString? serverCertificate;
|
||||
};
|
||||
|
||||
[JSImplementation="@mozilla.org/mozwificonnection;1",
|
||||
|
@ -102,6 +102,7 @@ DOMWifiManager.prototype = {
|
||||
"WifiManager:onconnect", "WifiManager:ondisconnect",
|
||||
"WifiManager:onwpstimeout", "WifiManager:onwpsfail",
|
||||
"WifiManager:onwpsoverlap", "WifiManager:connectionInfoUpdate",
|
||||
"WifiManager:onauthenticating",
|
||||
"WifiManager:onconnectingfailed"];
|
||||
this.initDOMRequestHelper(aWindow, messages);
|
||||
this._mm = Cc["@mozilla.org/childprocessmessagemanager;1"].getService(Ci.nsISyncMessageSender);
|
||||
@ -365,6 +366,11 @@ DOMWifiManager.prototype = {
|
||||
this._lastConnectionInfo = null;
|
||||
this._fireStatusChangeEvent();
|
||||
break;
|
||||
case "WifiManager:onauthenticating":
|
||||
this._currentNetwork = msg.network;
|
||||
this._connectionStatus = "authenticating";
|
||||
this._fireStatusChangeEvent();
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -672,6 +672,27 @@ var WifiManager = (function() {
|
||||
});
|
||||
}
|
||||
|
||||
function handleWpaEapEvents(event) {
|
||||
if (event.indexOf("CTRL-EVENT-EAP-FAILURE") !== -1) {
|
||||
if (event.indexOf("EAP authentication failed") !== -1) {
|
||||
notify("passwordmaybeincorrect");
|
||||
}
|
||||
return true;
|
||||
}
|
||||
if (event.indexOf("CTRL-EVENT-EAP-TLS-CERT-ERROR") !== -1) {
|
||||
// Cert Error
|
||||
manager.disconnect(function() {
|
||||
manager.reassociate(function(){});
|
||||
});
|
||||
return true;
|
||||
}
|
||||
if (event.indexOf("CTRL-EVENT-EAP-STARTED") !== -1) {
|
||||
notifyStateChange({ state: "AUTHENTICATING" });
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// Handle events sent to us by the event worker.
|
||||
function handleEvent(event) {
|
||||
debug("Event coming in: " + event);
|
||||
@ -777,12 +798,6 @@ var WifiManager = (function() {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
if (eventData.indexOf("CTRL-EVENT-EAP-FAILURE") === 0) {
|
||||
if (event.indexOf("EAP authentication failed") !== -1) {
|
||||
notify("passwordmaybeincorrect");
|
||||
}
|
||||
return true;
|
||||
}
|
||||
if (eventData.indexOf("CTRL-EVENT-CONNECTED") === 0) {
|
||||
// Format: CTRL-EVENT-CONNECTED - Connection to 00:1e:58:ec:d5:6d completed (reauth) [id=1 id_str=]
|
||||
var bssid = event.split(" ")[4];
|
||||
@ -804,6 +819,9 @@ var WifiManager = (function() {
|
||||
notify("scanresultsavailable");
|
||||
return true;
|
||||
}
|
||||
if (eventData.indexOf("CTRL-EVENT-EAP") === 0) {
|
||||
return handleWpaEapEvents(event);
|
||||
}
|
||||
if (eventData.indexOf("WPS-TIMEOUT") === 0) {
|
||||
notifyStateChange({ state: "WPS_TIMEOUT", BSSID: null, id: -1 });
|
||||
return true;
|
||||
@ -1061,7 +1079,7 @@ var WifiManager = (function() {
|
||||
"ssid", "bssid", "psk", "wep_key0", "wep_key1", "wep_key2", "wep_key3",
|
||||
"wep_tx_keyidx", "priority", "key_mgmt", "scan_ssid", "disabled",
|
||||
"identity", "password", "auth_alg", "phase1", "phase2", "eap", "pin",
|
||||
"pcsc"
|
||||
"pcsc", "ca_cert"
|
||||
];
|
||||
|
||||
manager.getNetworkConfiguration = function(config, callback) {
|
||||
@ -1081,16 +1099,17 @@ var WifiManager = (function() {
|
||||
var netId = config.netId;
|
||||
var done = 0;
|
||||
var errors = 0;
|
||||
|
||||
function hasValidProperty(name) {
|
||||
return ((name in config) &&
|
||||
config[name] != null &&
|
||||
(["password", "wep_key0", "psk"].indexOf(name) !== -1 ||
|
||||
config[name] !== '*'));
|
||||
}
|
||||
|
||||
for (var n = 0; n < networkConfigurationFields.length; ++n) {
|
||||
let fieldName = networkConfigurationFields[n];
|
||||
if (!(fieldName in config) ||
|
||||
// These fields are special: We can't retrieve them from the
|
||||
// supplicant, and often we have a star in our config. In that case,
|
||||
// we need to avoid overwriting the correct password with a *.
|
||||
(fieldName === "password" ||
|
||||
fieldName === "wep_key0" ||
|
||||
fieldName === "psk") &&
|
||||
config[fieldName] === '*') {
|
||||
if (!hasValidProperty(fieldName)) {
|
||||
++done;
|
||||
} else {
|
||||
wifiCommand.setNetworkVariable(netId, fieldName, config[fieldName], function(ok) {
|
||||
@ -1532,7 +1551,8 @@ Network.api = {
|
||||
eap: "rw",
|
||||
pin: "rw",
|
||||
phase1: "rw",
|
||||
phase2: "rw"
|
||||
phase2: "rw",
|
||||
serverCertificate: "rw"
|
||||
};
|
||||
|
||||
// Note: We never use ScanResult.prototype, so the fact that it's unrelated to
|
||||
@ -1763,6 +1783,10 @@ function WifiWorker() {
|
||||
pub.known = true;
|
||||
if (net.scan_ssid === 1)
|
||||
pub.hidden = true;
|
||||
if ("ca_cert" in net && net.ca_cert &&
|
||||
net.ca_cert.indexOf("keystore://WIFI_SERVERCERT_" === 0)) {
|
||||
pub.serverCertificate = net.ca_cert.substr(27);
|
||||
}
|
||||
return pub;
|
||||
};
|
||||
|
||||
@ -1825,15 +1849,29 @@ function WifiWorker() {
|
||||
configured.auth_alg = net.auth_alg = "OPEN SHARED";
|
||||
}
|
||||
|
||||
if ("pin" in net) {
|
||||
net.pin = quote(net.pin);
|
||||
function hasValidProperty(name) {
|
||||
return ((name in net) && net[name] != null);
|
||||
}
|
||||
|
||||
if ("phase1" in net)
|
||||
net.phase1 = quote(net.phase1);
|
||||
if (hasValidProperty("eap")) {
|
||||
if (hasValidProperty("pin")) {
|
||||
net.pin = quote(net.pin);
|
||||
}
|
||||
|
||||
if ("phase2" in net)
|
||||
net.phase2 = quote(net.phase2);
|
||||
if (hasValidProperty("phase1"))
|
||||
net.phase1 = quote(net.phase1);
|
||||
|
||||
if (hasValidProperty("phase2")) {
|
||||
if (net.eap === "PEAP") {
|
||||
net.phase2 = quote("auth=" + net.phase2);
|
||||
} else { // TLS, TTLS
|
||||
net.phase2 = quote("autheap=" + net.phase2);
|
||||
}
|
||||
}
|
||||
|
||||
if (hasValidProperty("serverCertificate"))
|
||||
net.ca_cert = quote("keystore://WIFI_SERVERCERT_" + net.serverCertificate);
|
||||
}
|
||||
|
||||
return net;
|
||||
};
|
||||
@ -2057,6 +2095,9 @@ function WifiWorker() {
|
||||
case "WPS_OVERLAP_DETECTED":
|
||||
self._fireEvent("onwpsoverlap", {});
|
||||
break;
|
||||
case "AUTHENTICATING":
|
||||
self._fireEvent("onauthenticating", {network: netToDOM(self.currentNetwork)});
|
||||
break;
|
||||
case "SCANNING":
|
||||
// If we're already scanning in the background, we don't need to worry
|
||||
// about getting stuck while scanning.
|
||||
|
@ -704,6 +704,12 @@ AboutReader.prototype = {
|
||||
|
||||
aEvent.stopPropagation();
|
||||
|
||||
// Create a relative timestamp for telemetry
|
||||
let uptime = Date.now() - Services.startup.getStartupInfo().linkerInitialized;
|
||||
// Just pass the ID of the button as an extra and hope the ID doesn't change
|
||||
// unless the context changes
|
||||
UITelemetry.addEvent("action.1", "button", uptime, id);
|
||||
|
||||
let items = segmentedButton.children;
|
||||
for (let j = items.length - 1; j >= 0; j--) {
|
||||
items[j].classList.remove("selected");
|
||||
|
@ -1437,11 +1437,10 @@ ThreadClient.prototype = {
|
||||
location,
|
||||
root.traits.conditionalBreakpoints ? condition : undefined
|
||||
);
|
||||
if (aCallback) {
|
||||
aCallback(aOnResponse(aResponse, bpClient));
|
||||
} else {
|
||||
aOnResponse(aResponse, bpClient);
|
||||
}
|
||||
aOnResponse(aResponse, bpClient);
|
||||
}
|
||||
if (aCallback) {
|
||||
aCallback();
|
||||
}
|
||||
}.bind(this));
|
||||
}.bind(this);
|
||||
@ -1588,7 +1587,6 @@ ThreadClient.prototype = {
|
||||
*/
|
||||
fillFrames: function (aTotal, aCallback=noop) {
|
||||
this._assertPaused("fillFrames");
|
||||
|
||||
if (this._frameCache.length >= aTotal) {
|
||||
return false;
|
||||
}
|
||||
@ -2258,19 +2256,35 @@ BreakpointClient.prototype = {
|
||||
let info = {
|
||||
url: this.location.url,
|
||||
line: this.location.line,
|
||||
column: this.location.column,
|
||||
condition: aCondition
|
||||
};
|
||||
gThreadClient.setBreakpoint(info, (aResponse, ignoredBreakpoint) => {
|
||||
if(aResponse && aResponse.error) {
|
||||
|
||||
// Remove the current breakpoint and add a new one with the
|
||||
// condition.
|
||||
this.remove(aResponse => {
|
||||
if (aResponse && aResponse.error) {
|
||||
deferred.reject(aResponse);
|
||||
} else {
|
||||
this.condition = aCondition;
|
||||
deferred.resolve(null);
|
||||
return;
|
||||
}
|
||||
|
||||
gThreadClient.setBreakpoint(info, (aResponse, aNewBreakpoint) => {
|
||||
if (aResponse && aResponse.error) {
|
||||
deferred.reject(aResponse);
|
||||
} else {
|
||||
deferred.resolve(aNewBreakpoint);
|
||||
}
|
||||
});
|
||||
});
|
||||
} else {
|
||||
this.conditionalExpression = aCondition;
|
||||
deferred.resolve(null);
|
||||
// The property shouldn't even exist if the condition is blank
|
||||
if(aCondition === "") {
|
||||
delete this.conditionalExpression;
|
||||
}
|
||||
else {
|
||||
this.conditionalExpression = aCondition;
|
||||
}
|
||||
deferred.resolve(this);
|
||||
}
|
||||
|
||||
return deferred.promise;
|
||||
|
@ -114,24 +114,16 @@ BreakpointStore.prototype = {
|
||||
if (!this._breakpoints[url][line]) {
|
||||
this._breakpoints[url][line] = [];
|
||||
}
|
||||
if(this._breakpoints[url][line][column]) {
|
||||
updating = true;
|
||||
}
|
||||
this._breakpoints[url][line][column] = aBreakpoint;
|
||||
} else {
|
||||
// Add a breakpoint that breaks on the whole line.
|
||||
if (!this._wholeLineBreakpoints[url]) {
|
||||
this._wholeLineBreakpoints[url] = [];
|
||||
}
|
||||
if(this._wholeLineBreakpoints[url][line]) {
|
||||
updating = true;
|
||||
}
|
||||
this._wholeLineBreakpoints[url][line] = aBreakpoint;
|
||||
}
|
||||
|
||||
if (!updating) {
|
||||
this._size++;
|
||||
}
|
||||
this._size++;
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -64,6 +64,9 @@ let initTable = [
|
||||
["obs", "@mozilla.org/observer-service;1", "nsIObserverService"],
|
||||
["perms", "@mozilla.org/permissionmanager;1", "nsIPermissionManager"],
|
||||
["prompt", "@mozilla.org/embedcomp/prompt-service;1", "nsIPromptService"],
|
||||
#ifdef MOZ_ENABLE_PROFILER_SPS
|
||||
["profiler", "@mozilla.org/tools/profiler;1", "nsIProfiler"],
|
||||
#endif
|
||||
["scriptloader", "@mozilla.org/moz/jssubscript-loader;1", "mozIJSSubScriptLoader"],
|
||||
["scriptSecurityManager", "@mozilla.org/scriptsecuritymanager;1", "nsIScriptSecurityManager"],
|
||||
#ifdef MOZ_TOOLKIT_SEARCH
|
||||
|
@ -100,6 +100,11 @@ let ShortcutUtils = {
|
||||
key = key.toUpperCase();
|
||||
}
|
||||
return elemString + key;
|
||||
},
|
||||
|
||||
findShortcut: function(aElemCommand) {
|
||||
let document = aElemCommand.ownerDocument;
|
||||
return document.querySelector("key[command=\"" + aElemCommand.getAttribute("id") + "\"]");
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -67,6 +67,8 @@ Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/AsyncShutdown.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "Task",
|
||||
"resource://gre/modules/Task.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "Promise",
|
||||
"resource://gre/modules/Promise.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "AddonRepository",
|
||||
@ -477,7 +479,6 @@ var AddonManagerInternal = {
|
||||
// Store telemetry details per addon provider
|
||||
telemetryDetails: {},
|
||||
|
||||
|
||||
// A read-only wrapper around the types dictionary
|
||||
typesProxy: Proxy.create({
|
||||
getOwnPropertyDescriptor: function typesProxy_getOwnPropertyDescriptor(aName) {
|
||||
@ -1132,120 +1133,117 @@ var AddonManagerInternal = {
|
||||
/**
|
||||
* Performs a background update check by starting an update for all add-ons
|
||||
* that can be updated.
|
||||
* @return Promise{null} Resolves when the background update check is complete
|
||||
* (the resulting addon installations may still be in progress).
|
||||
*/
|
||||
backgroundUpdateCheck: function AMI_backgroundUpdateCheck() {
|
||||
if (!gStarted)
|
||||
throw Components.Exception("AddonManager is not initialized",
|
||||
Cr.NS_ERROR_NOT_INITIALIZED);
|
||||
|
||||
let hotfixID = this.hotfixID;
|
||||
logger.debug("Background update check beginning");
|
||||
|
||||
let checkHotfix = hotfixID &&
|
||||
Services.prefs.getBoolPref(PREF_APP_UPDATE_ENABLED) &&
|
||||
Services.prefs.getBoolPref(PREF_APP_UPDATE_AUTO);
|
||||
return Task.spawn(function* backgroundUpdateTask() {
|
||||
let hotfixID = this.hotfixID;
|
||||
|
||||
if (!this.updateEnabled && !checkHotfix)
|
||||
return;
|
||||
let checkHotfix = hotfixID &&
|
||||
Services.prefs.getBoolPref(PREF_APP_UPDATE_ENABLED) &&
|
||||
Services.prefs.getBoolPref(PREF_APP_UPDATE_AUTO);
|
||||
|
||||
Services.obs.notifyObservers(null, "addons-background-update-start", null);
|
||||
if (!this.updateEnabled && !checkHotfix)
|
||||
return;
|
||||
|
||||
// Start this from one to ensure the whole of this function completes before
|
||||
// we can send the complete notification. Some parts can in some cases
|
||||
// complete synchronously before later parts have a chance to increment
|
||||
// pendingUpdates.
|
||||
let pendingUpdates = 1;
|
||||
Services.obs.notifyObservers(null, "addons-background-update-start", null);
|
||||
|
||||
function notifyComplete() {
|
||||
if (--pendingUpdates == 0) {
|
||||
Services.obs.notifyObservers(null,
|
||||
"addons-background-update-complete",
|
||||
null);
|
||||
}
|
||||
}
|
||||
if (this.updateEnabled) {
|
||||
let scope = {};
|
||||
Components.utils.import("resource://gre/modules/LightweightThemeManager.jsm", scope);
|
||||
scope.LightweightThemeManager.updateCurrentTheme();
|
||||
|
||||
if (this.updateEnabled) {
|
||||
let scope = {};
|
||||
Components.utils.import("resource://gre/modules/LightweightThemeManager.jsm", scope);
|
||||
scope.LightweightThemeManager.updateCurrentTheme();
|
||||
let aAddons = yield new Promise((resolve, reject) => this.getAllAddons(resolve));
|
||||
|
||||
pendingUpdates++;
|
||||
this.getAllAddons(function getAddonsCallback(aAddons) {
|
||||
// If there is a known hotfix then exclude it from the list of add-ons to update.
|
||||
var ids = [a.id for each (a in aAddons) if (a.id != hotfixID)];
|
||||
|
||||
// Repopulate repository cache first, to ensure compatibility overrides
|
||||
// are up to date before checking for addon updates.
|
||||
AddonRepository.backgroundUpdateCheck(
|
||||
ids, function BUC_backgroundUpdateCheckCallback() {
|
||||
pendingUpdates += aAddons.length;
|
||||
aAddons.forEach(function BUC_forEachCallback(aAddon) {
|
||||
if (aAddon.id == hotfixID) {
|
||||
notifyComplete();
|
||||
return;
|
||||
}
|
||||
yield new Promise((resolve, reject) => AddonRepository.backgroundUpdateCheck(ids, resolve));
|
||||
|
||||
// Check all add-ons for updates so that any compatibility updates will
|
||||
// be applied
|
||||
// Keep track of all the async add-on updates happening in parallel
|
||||
let updates = [];
|
||||
|
||||
for (let aAddon of aAddons) {
|
||||
if (aAddon.id == hotfixID) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Check all add-ons for updates so that any compatibility updates will
|
||||
// be applied
|
||||
updates.push(new Promise((resolve, reject) => {
|
||||
aAddon.findUpdates({
|
||||
onUpdateAvailable: function BUC_onUpdateAvailable(aAddon, aInstall) {
|
||||
// Start installing updates when the add-on can be updated and
|
||||
// background updates should be applied.
|
||||
if (aAddon.permissions & AddonManager.PERM_CAN_UPGRADE &&
|
||||
AddonManager.shouldAutoUpdate(aAddon)) {
|
||||
// XXX we really should resolve when this install is done,
|
||||
// not when update-available check completes, no?
|
||||
aInstall.install();
|
||||
}
|
||||
},
|
||||
|
||||
onUpdateFinished: notifyComplete
|
||||
onUpdateFinished: resolve
|
||||
}, AddonManager.UPDATE_WHEN_PERIODIC_UPDATE);
|
||||
});
|
||||
|
||||
notifyComplete();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
if (checkHotfix) {
|
||||
var hotfixVersion = "";
|
||||
try {
|
||||
hotfixVersion = Services.prefs.getCharPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
}));
|
||||
}
|
||||
yield Promise.all(updates);
|
||||
}
|
||||
catch (e) { }
|
||||
|
||||
let url = null;
|
||||
if (Services.prefs.getPrefType(PREF_EM_HOTFIX_URL) == Ci.nsIPrefBranch.PREF_STRING)
|
||||
url = Services.prefs.getCharPref(PREF_EM_HOTFIX_URL);
|
||||
else
|
||||
url = Services.prefs.getCharPref(PREF_EM_UPDATE_BACKGROUND_URL);
|
||||
if (checkHotfix) {
|
||||
var hotfixVersion = "";
|
||||
try {
|
||||
hotfixVersion = Services.prefs.getCharPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
}
|
||||
catch (e) { }
|
||||
|
||||
// Build the URI from a fake add-on data.
|
||||
url = AddonManager.escapeAddonURI({
|
||||
id: hotfixID,
|
||||
version: hotfixVersion,
|
||||
userDisabled: false,
|
||||
appDisabled: false
|
||||
}, url);
|
||||
let url = null;
|
||||
if (Services.prefs.getPrefType(PREF_EM_HOTFIX_URL) == Ci.nsIPrefBranch.PREF_STRING)
|
||||
url = Services.prefs.getCharPref(PREF_EM_HOTFIX_URL);
|
||||
else
|
||||
url = Services.prefs.getCharPref(PREF_EM_UPDATE_BACKGROUND_URL);
|
||||
|
||||
pendingUpdates++;
|
||||
Components.utils.import("resource://gre/modules/addons/AddonUpdateChecker.jsm");
|
||||
AddonUpdateChecker.checkForUpdates(hotfixID, null, url, {
|
||||
onUpdateCheckComplete: function BUC_onUpdateCheckComplete(aUpdates) {
|
||||
let update = AddonUpdateChecker.getNewestCompatibleUpdate(aUpdates);
|
||||
if (!update) {
|
||||
notifyComplete();
|
||||
return;
|
||||
}
|
||||
// Build the URI from a fake add-on data.
|
||||
url = AddonManager.escapeAddonURI({
|
||||
id: hotfixID,
|
||||
version: hotfixVersion,
|
||||
userDisabled: false,
|
||||
appDisabled: false
|
||||
}, url);
|
||||
|
||||
// If the available version isn't newer than the last installed
|
||||
// version then ignore it.
|
||||
if (Services.vc.compare(hotfixVersion, update.version) >= 0) {
|
||||
notifyComplete();
|
||||
return;
|
||||
}
|
||||
Components.utils.import("resource://gre/modules/addons/AddonUpdateChecker.jsm");
|
||||
let update = null;
|
||||
try {
|
||||
let foundUpdates = yield new Promise((resolve, reject) => {
|
||||
AddonUpdateChecker.checkForUpdates(hotfixID, null, url, {
|
||||
onUpdateCheckComplete: resolve,
|
||||
onUpdateCheckError: reject
|
||||
});
|
||||
});
|
||||
update = AddonUpdateChecker.getNewestCompatibleUpdate(foundUpdates);
|
||||
} catch (e) {
|
||||
// AUC.checkForUpdates already logged the error
|
||||
}
|
||||
|
||||
// Check that we have a hotfix update, and it's newer than the one we already
|
||||
// have installed (if any)
|
||||
if (update) {
|
||||
if (Services.vc.compare(hotfixVersion, update.version) < 0) {
|
||||
logger.debug("Downloading hotfix version " + update.version);
|
||||
let aInstall = yield new Promise((resolve, reject) =>
|
||||
AddonManager.getInstallForURL(update.updateURL, resolve,
|
||||
"application/x-xpinstall", update.updateHash, null,
|
||||
null, update.version));
|
||||
|
||||
logger.debug("Downloading hotfix version " + update.version);
|
||||
AddonManager.getInstallForURL(update.updateURL,
|
||||
function BUC_getInstallForURL(aInstall) {
|
||||
aInstall.addListener({
|
||||
onDownloadEnded: function BUC_onDownloadEnded(aInstall) {
|
||||
try {
|
||||
@ -1283,17 +1281,15 @@ var AddonManagerInternal = {
|
||||
});
|
||||
|
||||
aInstall.install();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
notifyComplete();
|
||||
}, "application/x-xpinstall", update.updateHash, null,
|
||||
null, update.version);
|
||||
},
|
||||
|
||||
onUpdateCheckError: notifyComplete
|
||||
});
|
||||
}
|
||||
|
||||
notifyComplete();
|
||||
logger.debug("Background update check complete");
|
||||
Services.obs.notifyObservers(null,
|
||||
"addons-background-update-complete",
|
||||
null);
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
/**
|
||||
@ -2332,7 +2328,7 @@ this.AddonManagerPrivate = {
|
||||
},
|
||||
|
||||
backgroundUpdateCheck: function AMP_backgroundUpdateCheck() {
|
||||
AddonManagerInternal.backgroundUpdateCheck();
|
||||
return AddonManagerInternal.backgroundUpdateCheck();
|
||||
},
|
||||
|
||||
addStartupChange: function AMP_addStartupChange(aType, aID) {
|
||||
|
@ -3610,7 +3610,13 @@ this.XPIProvider = {
|
||||
* The AddonInstall to remove
|
||||
*/
|
||||
removeActiveInstall: function XPI_removeActiveInstall(aInstall) {
|
||||
this.installs = this.installs.filter(function installFilter(i) i != aInstall);
|
||||
let where = this.installs.indexOf(aInstall);
|
||||
if (where == -1) {
|
||||
logger.warn("removeActiveInstall: could not find active install for "
|
||||
+ aInstall.sourceURI.spec);
|
||||
return;
|
||||
}
|
||||
this.installs.splice(where, 1);
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -75,7 +75,7 @@ function install_test_addons(aCallback) {
|
||||
// Switch to the test update URL
|
||||
Services.prefs.setCharPref(PREF_UPDATEURL, TESTROOT + "browser_bug557956.rdf");
|
||||
|
||||
aCallback();
|
||||
executeSoon(aCallback);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
@ -41,7 +41,7 @@ add_test(function () {
|
||||
gInstall = new MockInstall(undefined, undefined, addon);
|
||||
gInstall.addTestListener({
|
||||
onNewInstall: function () {
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
});
|
||||
gProvider.addInstall(gInstall);
|
||||
@ -65,7 +65,7 @@ add_test(function () {
|
||||
}
|
||||
}
|
||||
ok(false, "Item with correct name was not found");
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
});
|
||||
gInstall.install();
|
||||
|
@ -21,17 +21,18 @@ var gTestInstallListener = {
|
||||
|
||||
onInstallEnded: function(aInstall) {
|
||||
check_hidden(false);
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
},
|
||||
|
||||
onInstallCancelled: function(aInstall) {
|
||||
ok(gExpectedCancel, "Should expect install cancel");
|
||||
check_hidden(false);
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
},
|
||||
|
||||
onInstallFailed: function(aInstall) {
|
||||
ok(false, "Did not expect onInstallFailed");
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -40,7 +40,7 @@ function install_locale(aCallback) {
|
||||
gInstall.addTestListener({
|
||||
onInstallEnded: function(aInstall) {
|
||||
gInstall.removeTestListener(this);
|
||||
aCallback();
|
||||
executeSoon(aCallback);
|
||||
}
|
||||
});
|
||||
gInstall.install();
|
||||
|
@ -97,7 +97,7 @@ add_test(function() {
|
||||
},
|
||||
onInstallEnded: function() {
|
||||
check_list(gItem);
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
});
|
||||
|
||||
@ -136,7 +136,7 @@ add_test(function() {
|
||||
onInstallEnded: function() {
|
||||
check_list(null);
|
||||
extension.cancel();
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -15,51 +15,56 @@ const PREF_APP_UPDATE_ENABLED = "app.update.enabled";
|
||||
|
||||
const HOTFIX_ID = "hotfix@tests.mozilla.org";
|
||||
|
||||
var gNextTest;
|
||||
|
||||
var SuccessfulInstallListener = {
|
||||
onDownloadCancelled: function(aInstall) {
|
||||
ok(false, "Should not have seen the download cancelled");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have seen the right add-on");
|
||||
|
||||
AddonManager.removeInstallListener(this);
|
||||
gNextTest();
|
||||
},
|
||||
|
||||
onInstallEnded: function(aInstall) {
|
||||
ok(true, "Should have seen the install complete");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have installed the right add-on");
|
||||
|
||||
AddonManager.removeInstallListener(this);
|
||||
aInstall.addon.uninstall();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
gNextTest();
|
||||
}
|
||||
/*
|
||||
* Register an addon install listener and return a promise that:
|
||||
* resolves with the AddonInstall object if the install succeeds
|
||||
* rejects with the AddonInstall if the install fails
|
||||
*/
|
||||
function promiseInstallListener() {
|
||||
return new Promise((resolve, reject) => {
|
||||
let listener = {
|
||||
onInstallEnded: ai => {
|
||||
AddonManager.removeInstallListener(listener);
|
||||
resolve(ai);
|
||||
},
|
||||
onDownloadCancelled: ai => {
|
||||
AddonManager.removeInstallListener(listener);
|
||||
reject(ai);
|
||||
}
|
||||
};
|
||||
AddonManager.addInstallListener(listener);
|
||||
});
|
||||
}
|
||||
|
||||
var FailedInstallListener = {
|
||||
onDownloadCancelled: function(aInstall) {
|
||||
ok(true, "Should have seen the download cancelled");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have seen the right add-on");
|
||||
|
||||
AddonManager.removeInstallListener(this);
|
||||
gNextTest();
|
||||
},
|
||||
|
||||
onInstallEnded: function(aInstall) {
|
||||
ok(false, "Should not have seen the install complete");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have installed the right add-on");
|
||||
|
||||
AddonManager.removeInstallListener(this);
|
||||
aInstall.addon.uninstall();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
gNextTest();
|
||||
}
|
||||
function promiseSuccessfulInstall() {
|
||||
return promiseInstallListener().then(
|
||||
aInstall => {
|
||||
ok(true, "Should have seen the install complete");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have installed the right add-on");
|
||||
aInstall.addon.uninstall();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
},
|
||||
aInstall => {
|
||||
ok(false, "Should not have seen the download cancelled");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have seen the right add-on");
|
||||
});
|
||||
}
|
||||
|
||||
function test() {
|
||||
waitForExplicitFinish();
|
||||
function promiseFailedInstall() {
|
||||
return promiseInstallListener().then(
|
||||
aInstall => {
|
||||
ok(false, "Should not have seen the install complete");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have installed the right add-on");
|
||||
aInstall.addon.uninstall();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_LASTVERSION);
|
||||
},
|
||||
aInstall => {
|
||||
ok(true, "Should have seen the download cancelled");
|
||||
is(aInstall.addon.id, HOTFIX_ID, "Should have seen the right add-on");
|
||||
});
|
||||
}
|
||||
|
||||
add_task(function setup() {
|
||||
Services.prefs.setBoolPref(PREF_APP_UPDATE_ENABLED, true);
|
||||
Services.prefs.setBoolPref(PREF_INSTALL_REQUIREBUILTINCERTS, false);
|
||||
Services.prefs.setBoolPref(PREF_UPDATE_REQUIREBUILTINCERTS, false);
|
||||
@ -78,109 +83,85 @@ function test() {
|
||||
var prefs = Services.prefs.getChildList(PREF_EM_HOTFIX_CERTS);
|
||||
prefs.forEach(Services.prefs.clearUserPref);
|
||||
});
|
||||
|
||||
run_next_test();
|
||||
}
|
||||
|
||||
function end_test() {
|
||||
finish();
|
||||
}
|
||||
|
||||
add_test(function check_no_cert_checks() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, false);
|
||||
AddonManager.addInstallListener(SuccessfulInstallListener);
|
||||
|
||||
gNextTest = run_next_test;
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
});
|
||||
|
||||
add_test(function check_wrong_cert_fingerprint() {
|
||||
add_task(function* check_no_cert_checks() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, false);
|
||||
yield Promise.all([
|
||||
promiseSuccessfulInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
});
|
||||
|
||||
add_task(function* check_wrong_cert_fingerprint() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, true);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint", "foo");
|
||||
|
||||
AddonManager.addInstallListener(FailedInstallListener);
|
||||
|
||||
gNextTest = function() {
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
|
||||
run_next_test();
|
||||
};
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
yield Promise.all([
|
||||
promiseFailedInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
});
|
||||
|
||||
add_test(function check_right_cert_fingerprint() {
|
||||
add_task(function* check_right_cert_fingerprint() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, true);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint", "3E:B9:4E:07:12:FE:3C:01:41:46:13:46:FC:84:52:1A:8C:BE:1D:A2");
|
||||
|
||||
AddonManager.addInstallListener(SuccessfulInstallListener);
|
||||
yield Promise.all([
|
||||
promiseSuccessfulInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
|
||||
gNextTest = function() {
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
|
||||
run_next_test();
|
||||
};
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
});
|
||||
|
||||
add_test(function check_multi_cert_fingerprint_1() {
|
||||
add_task(function* check_multi_cert_fingerprint_1() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, true);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint", "3E:B9:4E:07:12:FE:3C:01:41:46:13:46:FC:84:52:1A:8C:BE:1D:A2");
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint", "foo");
|
||||
|
||||
AddonManager.addInstallListener(SuccessfulInstallListener);
|
||||
yield Promise.all([
|
||||
promiseSuccessfulInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
|
||||
gNextTest = function() {
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint");
|
||||
|
||||
run_next_test();
|
||||
};
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint");
|
||||
});
|
||||
|
||||
add_test(function check_multi_cert_fingerprint_2() {
|
||||
add_task(function* check_multi_cert_fingerprint_2() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, true);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint", "foo");
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint", "3E:B9:4E:07:12:FE:3C:01:41:46:13:46:FC:84:52:1A:8C:BE:1D:A2");
|
||||
|
||||
AddonManager.addInstallListener(SuccessfulInstallListener);
|
||||
yield Promise.all([
|
||||
promiseSuccessfulInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
|
||||
gNextTest = function() {
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint");
|
||||
|
||||
run_next_test();
|
||||
};
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "2.sha1Fingerprint");
|
||||
});
|
||||
|
||||
add_test(function check_no_cert_no_checks() {
|
||||
add_task(function* check_no_cert_no_checks() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, false);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_URL, TESTROOT + "unsigned_hotfix.rdf");
|
||||
|
||||
AddonManager.addInstallListener(SuccessfulInstallListener);
|
||||
|
||||
gNextTest = run_next_test;
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
yield Promise.all([
|
||||
promiseSuccessfulInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
});
|
||||
|
||||
add_test(function check_no_cert_cert_fingerprint_check() {
|
||||
add_task(function* check_no_cert_cert_fingerprint_check() {
|
||||
Services.prefs.setBoolPref(PREF_EM_CERT_CHECKATTRIBUTES, true);
|
||||
Services.prefs.setCharPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint", "3E:B9:4E:07:12:FE:3C:01:41:46:13:46:FC:84:52:1A:8C:BE:1D:A2");
|
||||
|
||||
AddonManager.addInstallListener(FailedInstallListener);
|
||||
yield Promise.all([
|
||||
promiseFailedInstall(),
|
||||
AddonManagerPrivate.backgroundUpdateCheck()
|
||||
]);
|
||||
|
||||
gNextTest = function() {
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
|
||||
run_next_test();
|
||||
};
|
||||
|
||||
AddonManagerPrivate.backgroundUpdateCheck();
|
||||
Services.prefs.clearUserPref(PREF_EM_HOTFIX_CERTS + "1.sha1Fingerprint");
|
||||
});
|
||||
|
@ -184,7 +184,7 @@ add_test(function() {
|
||||
is_element_hidden(item._installStatus, "Install progress widget should be hidden");
|
||||
|
||||
if (badgeUpdated)
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
else
|
||||
installCompleted = true;
|
||||
}
|
||||
|
@ -566,7 +566,7 @@ add_test(function() {
|
||||
|
||||
is(installBtn.hidden, true, "Install button should be hidden after install ended");
|
||||
check_filtered_results(QUERY, "relevancescore", false);
|
||||
run_next_test();
|
||||
executeSoon(run_next_test);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -30,7 +30,7 @@ function install_test_addon(aCallback) {
|
||||
onInstallEnded: function() {
|
||||
AddonManager.getAddonByID("addon1@tests.mozilla.org", function(addon) {
|
||||
gTestAddon = addon;
|
||||
aCallback();
|
||||
executeSoon(aCallback);
|
||||
});
|
||||
}
|
||||
};
|
||||
|
@ -6,8 +6,10 @@ Components.utils.import("resource://gre/modules/NetUtil.jsm");
|
||||
|
||||
let tmp = {};
|
||||
Components.utils.import("resource://gre/modules/AddonManager.jsm", tmp);
|
||||
Components.utils.import("resource://gre/modules/Log.jsm", tmp);
|
||||
let AddonManager = tmp.AddonManager;
|
||||
let AddonManagerPrivate = tmp.AddonManagerPrivate;
|
||||
let Log = tmp.Log;
|
||||
|
||||
var pathParts = gTestPath.split("/");
|
||||
// Drop the test filename
|
||||
@ -124,17 +126,16 @@ registerCleanupFunction(function() {
|
||||
checkOpenWindows("Addons:Compatibility");
|
||||
checkOpenWindows("Addons:Install");
|
||||
|
||||
// We can for now know that getAllInstalls actually calls its callback before
|
||||
// it returns so this will complete before the next test start.
|
||||
AddonManager.getAllInstalls(function(aInstalls) {
|
||||
for (let install of aInstalls) {
|
||||
if (install instanceof MockInstall)
|
||||
continue;
|
||||
return new Promise((resolve, reject) => AddonManager.getAllInstalls(resolve))
|
||||
.then(aInstalls => {
|
||||
for (let install of aInstalls) {
|
||||
if (install instanceof MockInstall)
|
||||
continue;
|
||||
|
||||
ok(false, "Should not have seen an install of " + install.sourceURI.spec + " in state " + install.state);
|
||||
install.cancel();
|
||||
}
|
||||
});
|
||||
ok(false, "Should not have seen an install of " + install.sourceURI.spec + " in state " + install.state);
|
||||
install.cancel();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
function log_exceptions(aCallback, ...aArgs) {
|
||||
@ -583,6 +584,7 @@ function MockProvider(aUseAsyncCallbacks, aTypes) {
|
||||
this.addons = [];
|
||||
this.installs = [];
|
||||
this.callbackTimers = [];
|
||||
this.timerLocations = new Map();
|
||||
this.useAsyncCallbacks = (aUseAsyncCallbacks === undefined) ? true : aUseAsyncCallbacks;
|
||||
this.types = (aTypes === undefined) ? [{
|
||||
id: "extension",
|
||||
@ -606,6 +608,7 @@ MockProvider.prototype = {
|
||||
started: null,
|
||||
apiDelay: 10,
|
||||
callbackTimers: null,
|
||||
timerLocations: null,
|
||||
useAsyncCallbacks: null,
|
||||
types: null,
|
||||
|
||||
@ -786,11 +789,20 @@ MockProvider.prototype = {
|
||||
if (this.callbackTimers.length) {
|
||||
info("MockProvider: pending callbacks at shutdown(): calling immediately");
|
||||
}
|
||||
for (let timer of this.callbackTimers) {
|
||||
timer.callback();
|
||||
timer.cancel();
|
||||
while (this.callbackTimers.length > 0) {
|
||||
// When we notify the callback timer, it removes itself from our array
|
||||
let timer = this.callbackTimers[0];
|
||||
try {
|
||||
let setAt = this.timerLocations.get(timer);
|
||||
info("Notifying timer set at " + (setAt || "unknown location"));
|
||||
timer.callback.notify(timer);
|
||||
timer.cancel();
|
||||
} catch(e) {
|
||||
info("Timer notify failed: " + e);
|
||||
}
|
||||
}
|
||||
this.callbackTimers = [];
|
||||
this.timerLocations = null;
|
||||
|
||||
this.started = false;
|
||||
},
|
||||
@ -973,21 +985,26 @@ MockProvider.prototype = {
|
||||
*/
|
||||
_delayCallback: function MP_delayCallback(aCallback, ...aArgs) {
|
||||
if (!this.useAsyncCallbacks) {
|
||||
aCallback.apply(null, aArgs);
|
||||
aCallback(...aArgs);
|
||||
return;
|
||||
}
|
||||
|
||||
var timer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
|
||||
let timer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
|
||||
// Need to keep a reference to the timer, so it doesn't get GC'ed
|
||||
this.callbackTimers.push(timer);
|
||||
// Capture a stack trace where the timer was set
|
||||
// needs the 'new Error' hack until bug 1007656
|
||||
this.timerLocations.set(timer, Log.stackTrace(new Error("dummy")));
|
||||
timer.initWithCallback(() => {
|
||||
let idx = this.callbackTimers.indexOf(timer);
|
||||
if (idx == -1) {
|
||||
info("MockProvider._delayCallback lost track of a timer.");
|
||||
dump("MockProvider._delayCallback lost track of timer set at "
|
||||
+ (this.timerLocations.get(timer) || "unknown location") + "\n");
|
||||
} else {
|
||||
this.callbackTimers.splice(idx, 1);
|
||||
}
|
||||
aCallback.apply(null, aArgs);
|
||||
this.timerLocations.delete(timer);
|
||||
aCallback(...aArgs);
|
||||
}, this.apiDelay, timer.TYPE_ONE_SHOT);
|
||||
}
|
||||
};
|
||||
|