mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-08 12:37:37 +00:00
Merge m-c to fx-team a=merge
This commit is contained in:
commit
b0607333ce
@ -232,7 +232,7 @@ let AlertsHelper = {
|
||||
},
|
||||
|
||||
showNotification: function(imageURL, title, text, textClickable, cookie,
|
||||
uid, bidi, lang, dataObj, manifestURL, timestamp,
|
||||
uid, dir, lang, dataObj, manifestURL, timestamp,
|
||||
behavior) {
|
||||
function send(appName, appIcon) {
|
||||
SystemAppProxy._sendCustomEvent(kMozChromeNotificationEvent, {
|
||||
@ -241,7 +241,7 @@ let AlertsHelper = {
|
||||
icon: imageURL,
|
||||
title: title,
|
||||
text: text,
|
||||
bidi: bidi,
|
||||
dir: dir,
|
||||
lang: lang,
|
||||
appName: appName,
|
||||
appIcon: appIcon,
|
||||
@ -276,7 +276,7 @@ let AlertsHelper = {
|
||||
let dataObj = this.deserializeStructuredClone(data.dataStr);
|
||||
this.registerListener(data.name, data.cookie, data.alertListener);
|
||||
this.showNotification(data.imageURL, data.title, data.text,
|
||||
data.textClickable, data.cookie, data.name, data.bidi,
|
||||
data.textClickable, data.cookie, data.name, data.dir,
|
||||
data.lang, dataObj, null, data.inPrivateBrowsing);
|
||||
},
|
||||
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="a8ace1361d702eef293e48f2ea525dac686daa86">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="a8ace1361d702eef293e48f2ea525dac686daa86">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -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="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="9a9797062c6001d6346504161c51187a2968466b"/>
|
||||
|
@ -17,7 +17,7 @@
|
||||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="46da1a05ac04157669685246d70ac59d48699c9e"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="0627790166dccd8dd370fa7d9f434ed9fc027fb4"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="a8ace1361d702eef293e48f2ea525dac686daa86">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="61e82f99bb8bc78d52b5717e9a2481ec7267fa33">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -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="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="9a9797062c6001d6346504161c51187a2968466b"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="a8ace1361d702eef293e48f2ea525dac686daa86">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -1,9 +1,9 @@
|
||||
{
|
||||
"git": {
|
||||
"git_revision": "27f6760ceb0c8897bd21461e8b91136d7efff2a1",
|
||||
"git_revision": "84d77c1f3cbe06b91d4a5acac02a6c829e9a7488",
|
||||
"remote": "https://git.mozilla.org/releases/gaia.git",
|
||||
"branch": ""
|
||||
},
|
||||
"revision": "7fbbf564986896c9cf3a1e8d59b49e3eb6d7f7ef",
|
||||
"revision": "65b78de3c7968e078018096712a5e14321fe0a14",
|
||||
"repo_path": "integration/gaia-central"
|
||||
}
|
||||
|
@ -17,7 +17,7 @@
|
||||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="46da1a05ac04157669685246d70ac59d48699c9e"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="0627790166dccd8dd370fa7d9f434ed9fc027fb4"/>
|
||||
|
@ -15,7 +15,7 @@
|
||||
<project name="platform_build" path="build" remote="b2g" revision="61e82f99bb8bc78d52b5717e9a2481ec7267fa33">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="27f6760ceb0c8897bd21461e8b91136d7efff2a1"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="84d77c1f3cbe06b91d4a5acac02a6c829e9a7488"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
@ -633,6 +633,7 @@ static nsTArray<nsRefPtr<BluetoothReplyRunnable> > sGetDeviceRunnableArray;
|
||||
static nsTArray<nsRefPtr<BluetoothReplyRunnable> > sBondingRunnableArray;
|
||||
static nsTArray<nsRefPtr<BluetoothReplyRunnable> > sUnbondingRunnableArray;
|
||||
static bool sAdapterDiscoverable(false);
|
||||
static bool sAdapterDiscovering(false);
|
||||
static bool sIsRestart(false);
|
||||
static bool sIsFirstTimeToggleOffBt(false);
|
||||
static uint32_t sAdapterDiscoverableTimeout(0);
|
||||
@ -2490,8 +2491,9 @@ BluetoothServiceBluedroid::AdapterPropertiesNotification(
|
||||
*
|
||||
* (1) automatically by Bluedroid when BT is turning on, or
|
||||
* (2) as result of remote device properties update during discovery, or
|
||||
* (3) as result of GetRemoteDeviceProperties, or
|
||||
* (4) as result of GetRemoteServices.
|
||||
* (3) as result of CreateBond, or
|
||||
* (4) as result of GetRemoteDeviceProperties, or
|
||||
* (5) as result of GetRemoteServices.
|
||||
*/
|
||||
void
|
||||
BluetoothServiceBluedroid::RemoteDevicePropertiesNotification(
|
||||
@ -2665,15 +2667,17 @@ BluetoothServiceBluedroid::RemoteDevicePropertiesNotification(
|
||||
/**
|
||||
* This is possible when
|
||||
*
|
||||
* (1) the callback is called after Bluetooth is turned on, or
|
||||
* (2) remote device properties get updated during discovery.
|
||||
*
|
||||
* For (2), fire 'devicefound' again to update device name.
|
||||
* See bug 1076553 for more information.
|
||||
* (1) the callback is called when BT is turning on, or
|
||||
* (2) remote device properties get updated during discovery, or
|
||||
* (3) as result of CreateBond
|
||||
*/
|
||||
DistributeSignal(BluetoothSignal(NS_LITERAL_STRING("DeviceFound"),
|
||||
NS_LITERAL_STRING(KEY_ADAPTER),
|
||||
BluetoothValue(props)));
|
||||
if (sAdapterDiscovering) {
|
||||
// Fire 'devicefound' again to update device name for (2).
|
||||
// See bug 1076553 for more information.
|
||||
DistributeSignal(BluetoothSignal(NS_LITERAL_STRING("DeviceFound"),
|
||||
NS_LITERAL_STRING(KEY_ADAPTER),
|
||||
BluetoothValue(props)));
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
@ -2812,16 +2816,17 @@ BluetoothServiceBluedroid::DiscoveryStateChangedNotification(bool aState)
|
||||
#else
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
bool isDiscovering = (aState == true);
|
||||
sAdapterDiscovering = aState;
|
||||
|
||||
DistributeSignal(
|
||||
BluetoothSignal(NS_LITERAL_STRING(DISCOVERY_STATE_CHANGED_ID),
|
||||
NS_LITERAL_STRING(KEY_ADAPTER), isDiscovering));
|
||||
NS_LITERAL_STRING(KEY_ADAPTER), sAdapterDiscovering));
|
||||
|
||||
// Distribute "PropertyChanged" signal to notice adapter this change since
|
||||
// Bluedroid don' treat "discovering" as a property of adapter.
|
||||
InfallibleTArray<BluetoothNamedValue> props;
|
||||
BT_APPEND_NAMED_VALUE(props, "Discovering", BluetoothValue(isDiscovering));
|
||||
BT_APPEND_NAMED_VALUE(props, "Discovering",
|
||||
BluetoothValue(sAdapterDiscovering));
|
||||
DistributeSignal(BluetoothSignal(NS_LITERAL_STRING("PropertyChanged"),
|
||||
NS_LITERAL_STRING(KEY_ADAPTER),
|
||||
BluetoothValue(props)));
|
||||
|
@ -227,7 +227,6 @@ BluetoothHfpManager::Cleanup()
|
||||
void
|
||||
BluetoothHfpManager::Reset()
|
||||
{
|
||||
mFirstCKPD = false;
|
||||
// Phone & Device CIND
|
||||
ResetCallArray();
|
||||
// Clear Sco state
|
||||
@ -1315,8 +1314,6 @@ BluetoothHfpManager::OnConnect(const nsAString& aErrorStr)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
mFirstCKPD = true;
|
||||
|
||||
/**
|
||||
* On the one hand, notify the controller that we've done for outbound
|
||||
* connections. On the other hand, we do nothing for inbound connections.
|
||||
@ -1658,16 +1655,7 @@ BluetoothHfpManager::KeyPressedNotification(const nsAString& aBdAddress)
|
||||
* If there's no SCO, set up a SCO link.
|
||||
*/
|
||||
ConnectSco();
|
||||
} else if (mFirstCKPD) {
|
||||
/*
|
||||
* Bluetooth HSP spec 4.2 & 4.3
|
||||
* The SCO link connection may be set up prior to receiving the AT+CKPD=200
|
||||
* command from the HS.
|
||||
*
|
||||
* Once FxOS initiates a SCO connection before receiving the
|
||||
* AT+CKPD=200, we should ignore this key press.
|
||||
*/
|
||||
} else {
|
||||
} else {
|
||||
/*
|
||||
* Bluetooth HSP spec 4.5
|
||||
* There are two ways to release SCO: sending CHUP to dialer or closing
|
||||
@ -1676,10 +1664,8 @@ BluetoothHfpManager::KeyPressedNotification(const nsAString& aBdAddress)
|
||||
*/
|
||||
NotifyDialer(NS_LITERAL_STRING("CHUP"));
|
||||
}
|
||||
mFirstCKPD = false;
|
||||
} else {
|
||||
// BLDN
|
||||
mDialingRequestProcessed = false;
|
||||
|
||||
NotifyDialer(NS_LITERAL_STRING("BLDN"));
|
||||
|
||||
|
@ -211,8 +211,8 @@ private:
|
||||
int mCurrentVgs;
|
||||
int mCurrentVgm;
|
||||
bool mReceiveVgsFlag;
|
||||
// This flag is for HFP only, not for HSP.
|
||||
bool mDialingRequestProcessed;
|
||||
bool mFirstCKPD;
|
||||
PhoneType mPhoneType;
|
||||
nsString mDeviceAddress;
|
||||
nsString mMsisdn;
|
||||
|
@ -41,7 +41,7 @@ interface nsINotificationStorageCallback : nsISupports
|
||||
/**
|
||||
* Interface for notification persistence layer.
|
||||
*/
|
||||
[scriptable, uuid(f5145be6-e34b-468b-84da-c8c4c1ad60fe)]
|
||||
[scriptable, uuid(cac01fb0-c2eb-4252-b2f4-5b1fac933bd4)]
|
||||
interface nsINotificationStorage : nsISupports
|
||||
{
|
||||
|
||||
@ -94,6 +94,20 @@ interface nsINotificationStorage : nsISupports
|
||||
*/
|
||||
void delete(in DOMString origin,
|
||||
in DOMString id);
|
||||
|
||||
/**
|
||||
* Notifications are not supposed to be persistent, according to spec, at
|
||||
* least for now. But we want to be able to have this behavior on B2G. Thus,
|
||||
* this method will check if the origin sending the notifications is a valid
|
||||
* registered app with a manifest or not. Hence, a webpage that has none
|
||||
* will have its notification sent and available (via Notification.get())
|
||||
* during the life time of the page.
|
||||
*
|
||||
* @param origin: Origin from which the notification is sent.
|
||||
*
|
||||
* @return boolean
|
||||
*/
|
||||
boolean canPut(in DOMString origin);
|
||||
};
|
||||
|
||||
%{C++
|
||||
|
@ -37,6 +37,9 @@ const TEST_DATA = [
|
||||
}, {
|
||||
preferredNetworkType: "lte",
|
||||
expectedErrorMessage: "ModeNotSupported"
|
||||
}, {
|
||||
preferredNetworkType: "lte/wcdma",
|
||||
expectedErrorMessage: "ModeNotSupported"
|
||||
},
|
||||
// Test passing an invalid mode. We expect to get an exception here.
|
||||
{
|
||||
|
@ -24,6 +24,10 @@ XPCOMUtils.defineLazyServiceGetter(this, "ppmm",
|
||||
"@mozilla.org/parentprocessmessagemanager;1",
|
||||
"nsIMessageListenerManager");
|
||||
|
||||
XPCOMUtils.defineLazyServiceGetter(this, "notificationStorage",
|
||||
"@mozilla.org/notificationStorage;1",
|
||||
"nsINotificationStorage");
|
||||
|
||||
const NOTIFICATION_STORE_DIR = OS.Constants.Path.profileDir;
|
||||
const NOTIFICATION_STORE_PATH =
|
||||
OS.Path.join(NOTIFICATION_STORE_DIR, "notificationstore.json");
|
||||
@ -77,14 +81,29 @@ let NotificationDB = {
|
||||
}
|
||||
},
|
||||
|
||||
filterNonAppNotifications: function(notifications) {
|
||||
let origins = Object.keys(notifications);
|
||||
for (let origin of origins) {
|
||||
let canPut = notificationStorage.canPut(origin);
|
||||
if (!canPut) {
|
||||
if (DEBUG) debug("Origin " + origin + " is not linked to an app manifest, deleting.");
|
||||
delete notifications[origin];
|
||||
}
|
||||
}
|
||||
return notifications;
|
||||
},
|
||||
|
||||
// Attempt to read notification file, if it's not there we will create it.
|
||||
load: function() {
|
||||
var promise = OS.File.read(NOTIFICATION_STORE_PATH, { encoding: "utf-8"});
|
||||
return promise.then(
|
||||
function onSuccess(data) {
|
||||
if (data.length > 0) {
|
||||
this.notifications = JSON.parse(data);
|
||||
// Preprocessing phase intends to cleanly separate any migration-related
|
||||
// tasks.
|
||||
this.notifications = this.filterNonAppNotifications(JSON.parse(data));
|
||||
}
|
||||
|
||||
// populate the list of notifications by tag
|
||||
if (this.notifications) {
|
||||
for (var origin in this.notifications) {
|
||||
@ -97,6 +116,7 @@ let NotificationDB = {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
this.loaded = true;
|
||||
}.bind(this),
|
||||
|
||||
|
@ -23,6 +23,10 @@ XPCOMUtils.defineLazyServiceGetter(this, "cpmm",
|
||||
"@mozilla.org/childprocessmessagemanager;1",
|
||||
"nsIMessageSender");
|
||||
|
||||
XPCOMUtils.defineLazyServiceGetter(this, "appsService",
|
||||
"@mozilla.org/AppsService;1",
|
||||
"nsIAppsService");
|
||||
|
||||
const kMessageNotificationGetAllOk = "Notification:GetAll:Return:OK";
|
||||
const kMessageNotificationGetAllKo = "Notification:GetAll:Return:KO";
|
||||
const kMessageNotificationSaveKo = "Notification:Save:Return:KO";
|
||||
@ -45,6 +49,7 @@ function NotificationStorage() {
|
||||
this._requestCount = 0;
|
||||
|
||||
Services.obs.addObserver(this, "xpcom-shutdown", false);
|
||||
|
||||
// Register for message listeners.
|
||||
this.registerListeners();
|
||||
}
|
||||
@ -65,12 +70,19 @@ NotificationStorage.prototype = {
|
||||
|
||||
observe: function(aSubject, aTopic, aData) {
|
||||
if (DEBUG) debug("Topic: " + aTopic);
|
||||
if (aTopic == "xpcom-shutdown") {
|
||||
if (aTopic === "xpcom-shutdown") {
|
||||
Services.obs.removeObserver(this, "xpcom-shutdown");
|
||||
this.unregisterListeners();
|
||||
}
|
||||
},
|
||||
|
||||
canPut: function(aOrigin) {
|
||||
if (DEBUG) debug("Querying appService for: " + aOrigin);
|
||||
let rv = !!appsService.getAppByManifestURL(aOrigin);
|
||||
if (DEBUG) debug("appService returned: " + rv);
|
||||
return rv;
|
||||
},
|
||||
|
||||
put: function(origin, id, title, dir, lang, body, tag, icon, alertName,
|
||||
data, behavior) {
|
||||
if (DEBUG) { debug("PUT: " + id + ": " + title); }
|
||||
@ -105,10 +117,12 @@ NotificationStorage.prototype = {
|
||||
this._byTag[origin][tag] = notification;
|
||||
};
|
||||
|
||||
cpmm.sendAsyncMessage("Notification:Save", {
|
||||
origin: origin,
|
||||
notification: notification
|
||||
});
|
||||
if (this.canPut(origin)) {
|
||||
cpmm.sendAsyncMessage("Notification:Save", {
|
||||
origin: origin,
|
||||
notification: notification
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
get: function(origin, tag, callback) {
|
||||
|
@ -99,6 +99,7 @@ SEReaderImpl.prototype = {
|
||||
_sessions: [],
|
||||
|
||||
type: null,
|
||||
_isSEPresent: false,
|
||||
|
||||
classID: Components.ID("{1c7bdba3-cd35-4f8b-a546-55b3232457d5}"),
|
||||
contractID: "@mozilla.org/secureelement/reader;1",
|
||||
@ -112,22 +113,34 @@ SEReaderImpl.prototype = {
|
||||
}
|
||||
},
|
||||
|
||||
initialize: function initialize(win, type) {
|
||||
initialize: function initialize(win, type, isPresent) {
|
||||
this._window = win;
|
||||
this.type = type;
|
||||
this._isSEPresent = isPresent;
|
||||
},
|
||||
|
||||
_checkPresence: function _checkPresence() {
|
||||
if (!this._isSEPresent) {
|
||||
throw new Error(SE.ERROR_NOTPRESENT);
|
||||
}
|
||||
},
|
||||
|
||||
openSession: function openSession() {
|
||||
this._checkPresence();
|
||||
|
||||
return PromiseHelpers.createSEPromise((resolverId) => {
|
||||
let chromeObj = new SESessionImpl();
|
||||
chromeObj.initialize(this._window, this);
|
||||
let contentObj = this._window.SESession._create(this._window, chromeObj);
|
||||
this._sessions.push(contentObj);
|
||||
PromiseHelpers.takePromiseResolver(resolverId).resolve(contentObj);
|
||||
let sessionImpl = new SESessionImpl();
|
||||
sessionImpl.initialize(this._window, this);
|
||||
this._window.SESession._create(this._window, sessionImpl);
|
||||
this._sessions.push(sessionImpl);
|
||||
PromiseHelpers.takePromiseResolver(resolverId)
|
||||
.resolve(sessionImpl.__DOM_IMPL__);
|
||||
});
|
||||
},
|
||||
|
||||
closeAll: function closeAll() {
|
||||
this._checkPresence();
|
||||
|
||||
return PromiseHelpers.createSEPromise((resolverId) => {
|
||||
let promises = [];
|
||||
for (let session of this._sessions) {
|
||||
@ -148,10 +161,24 @@ SEReaderImpl.prototype = {
|
||||
});
|
||||
},
|
||||
|
||||
updateSEPresence: function updateSEPresence(isSEPresent) {
|
||||
if (!isSEPresent) {
|
||||
this.invalidate();
|
||||
return;
|
||||
}
|
||||
|
||||
this._isSEPresent = isSEPresent;
|
||||
},
|
||||
|
||||
invalidate: function invalidate() {
|
||||
debug("Invalidating SE reader: " + this.type);
|
||||
this._isSEPresent = false;
|
||||
this._sessions.forEach(s => s.invalidate());
|
||||
this._sessions = [];
|
||||
},
|
||||
|
||||
get isSEPresent() {
|
||||
// TODO: Bug 1119152 - Implement new idl with interfaces to detect
|
||||
// secureelement state changes.
|
||||
return true;
|
||||
return this._isSEPresent;
|
||||
}
|
||||
};
|
||||
|
||||
@ -254,6 +281,12 @@ SESessionImpl.prototype = {
|
||||
});
|
||||
},
|
||||
|
||||
invalidate: function invlidate() {
|
||||
this._isClosed = true;
|
||||
this._channels.forEach(ch => ch.invalidate());
|
||||
this._channels = [];
|
||||
},
|
||||
|
||||
get reader() {
|
||||
return this._reader.__DOM_IMPL__;
|
||||
},
|
||||
@ -261,10 +294,6 @@ SESessionImpl.prototype = {
|
||||
get isClosed() {
|
||||
return this._isClosed;
|
||||
},
|
||||
|
||||
set isClosed(isClosed) {
|
||||
this._isClosed = isClosed;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
@ -387,6 +416,10 @@ SEChannelImpl.prototype = {
|
||||
}, this);
|
||||
},
|
||||
|
||||
invalidate: function invalidate() {
|
||||
this._isClosed = true;
|
||||
},
|
||||
|
||||
get session() {
|
||||
return this._session.__DOM_IMPL__;
|
||||
},
|
||||
@ -394,10 +427,6 @@ SEChannelImpl.prototype = {
|
||||
get isClosed() {
|
||||
return this._isClosed;
|
||||
},
|
||||
|
||||
set isClosed(isClosed) {
|
||||
this._isClosed = isClosed;
|
||||
}
|
||||
};
|
||||
|
||||
function SEResponseImpl() {}
|
||||
@ -447,6 +476,8 @@ SEManagerImpl.prototype = {
|
||||
Ci.nsIObserver
|
||||
]),
|
||||
|
||||
_readers: [],
|
||||
|
||||
init: function init(win) {
|
||||
this._window = win;
|
||||
PromiseHelpers = new PromiseHelpersSubclass(this._window);
|
||||
@ -459,7 +490,8 @@ SEManagerImpl.prototype = {
|
||||
"SE:GetSEReadersRejected",
|
||||
"SE:OpenChannelRejected",
|
||||
"SE:CloseChannelRejected",
|
||||
"SE:TransmitAPDURejected"];
|
||||
"SE:TransmitAPDURejected",
|
||||
"SE:ReaderPresenceChanged"];
|
||||
|
||||
this.initDOMRequestHelper(win, messages);
|
||||
},
|
||||
@ -476,13 +508,13 @@ SEManagerImpl.prototype = {
|
||||
},
|
||||
|
||||
getSEReaders: function getSEReaders() {
|
||||
// invalidate previous readers on new request
|
||||
if (this._readers.length) {
|
||||
this._readers.forEach(r => r.invalidate());
|
||||
this._readers = [];
|
||||
}
|
||||
|
||||
return PromiseHelpers.createSEPromise((resolverId) => {
|
||||
/**
|
||||
* @params for 'SE:GetSEReaders'
|
||||
*
|
||||
* resolverId : Id that identifies this IPC request.
|
||||
* appId : Current appId obtained from 'Principal' obj
|
||||
*/
|
||||
cpmm.sendAsyncMessage("SE:GetSEReaders", {
|
||||
resolverId: resolverId,
|
||||
appId: this._window.document.nodePrincipal.appId
|
||||
@ -491,9 +523,9 @@ SEManagerImpl.prototype = {
|
||||
},
|
||||
|
||||
receiveMessage: function receiveMessage(message) {
|
||||
DEBUG && debug("Message received: " + JSON.stringify(message));
|
||||
|
||||
let result = message.data.result;
|
||||
let chromeObj = null;
|
||||
let contentObj = null;
|
||||
let resolver = null;
|
||||
let context = null;
|
||||
|
||||
@ -504,40 +536,41 @@ SEManagerImpl.prototype = {
|
||||
context = promiseResolver.context;
|
||||
}
|
||||
|
||||
debug("receiveMessage(): " + message.name);
|
||||
switch (message.name) {
|
||||
case "SE:GetSEReadersResolved":
|
||||
let readers = new this._window.Array();
|
||||
for (let i = 0; i < result.readerTypes.length; i++) {
|
||||
chromeObj = new SEReaderImpl();
|
||||
chromeObj.initialize(this._window, result.readerTypes[i]);
|
||||
contentObj = this._window.SEReader._create(this._window, chromeObj);
|
||||
readers.push(contentObj);
|
||||
}
|
||||
result.readers.forEach(reader => {
|
||||
let readerImpl = new SEReaderImpl();
|
||||
readerImpl.initialize(this._window, reader.type, reader.isPresent);
|
||||
this._window.SEReader._create(this._window, readerImpl);
|
||||
|
||||
this._readers.push(readerImpl);
|
||||
readers.push(readerImpl.__DOM_IMPL__);
|
||||
});
|
||||
resolver.resolve(readers);
|
||||
break;
|
||||
case "SE:OpenChannelResolved":
|
||||
chromeObj = new SEChannelImpl();
|
||||
chromeObj.initialize(this._window,
|
||||
result.channelToken,
|
||||
result.isBasicChannel,
|
||||
result.openResponse,
|
||||
context);
|
||||
contentObj = this._window.SEChannel._create(this._window, chromeObj);
|
||||
let channelImpl = new SEChannelImpl();
|
||||
channelImpl.initialize(this._window,
|
||||
result.channelToken,
|
||||
result.isBasicChannel,
|
||||
result.openResponse,
|
||||
context);
|
||||
this._window.SEChannel._create(this._window, channelImpl);
|
||||
if (context) {
|
||||
// Notify context's handler with SEChannel instance
|
||||
context.onChannelOpen(contentObj);
|
||||
context.onChannelOpen(channelImpl);
|
||||
}
|
||||
resolver.resolve(contentObj);
|
||||
resolver.resolve(channelImpl.__DOM_IMPL__);
|
||||
break;
|
||||
case "SE:TransmitAPDUResolved":
|
||||
chromeObj = new SEResponseImpl();
|
||||
chromeObj.initialize(result.sw1,
|
||||
result.sw2,
|
||||
result.response,
|
||||
context);
|
||||
contentObj = this._window.SEResponse._create(this._window, chromeObj);
|
||||
resolver.resolve(contentObj);
|
||||
let responseImpl = new SEResponseImpl();
|
||||
responseImpl.initialize(result.sw1,
|
||||
result.sw2,
|
||||
result.response,
|
||||
context);
|
||||
this._window.SEResponse._create(this._window, responseImpl);
|
||||
resolver.resolve(responseImpl.__DOM_IMPL__);
|
||||
break;
|
||||
case "SE:CloseChannelResolved":
|
||||
if (context) {
|
||||
@ -553,6 +586,13 @@ SEManagerImpl.prototype = {
|
||||
let error = result.error || SE.ERROR_GENERIC;
|
||||
resolver.reject(error);
|
||||
break;
|
||||
case "SE:ReaderPresenceChanged":
|
||||
debug("Reader " + result.type + " present: " + result.isPresent);
|
||||
let reader = this._readers.find(r => r.type === result.type);
|
||||
if (reader) {
|
||||
reader.updateSEPresence(result.isPresent);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
debug("Could not find a handler for " + message.name);
|
||||
resolver.reject();
|
||||
|
@ -91,7 +91,6 @@ XPCOMUtils.defineLazyGetter(this, "gMap", function() {
|
||||
// {
|
||||
// "appId1": {
|
||||
// target: target1,
|
||||
// readerType: ["uicc", "eSE"],
|
||||
// channels: {
|
||||
// "channelToken1": {
|
||||
// seType: "uicc",
|
||||
@ -105,7 +104,7 @@ XPCOMUtils.defineLazyGetter(this, "gMap", function() {
|
||||
// }
|
||||
appInfoMap: {},
|
||||
|
||||
registerSecureElementTarget: function(appId, readerTypes, target) {
|
||||
registerSecureElementTarget: function(appId, target) {
|
||||
if (this.isAppIdRegistered(appId)) {
|
||||
debug("AppId: " + appId + "already registered");
|
||||
return;
|
||||
@ -113,7 +112,6 @@ XPCOMUtils.defineLazyGetter(this, "gMap", function() {
|
||||
|
||||
this.appInfoMap[appId] = {
|
||||
target: target,
|
||||
readerTypes: readerTypes,
|
||||
channels: {}
|
||||
};
|
||||
|
||||
@ -181,6 +179,11 @@ XPCOMUtils.defineLazyGetter(this, "gMap", function() {
|
||||
return Object.keys(this.appInfoMap[appId].channels)
|
||||
.map(token => this.appInfoMap[appId].channels[token]);
|
||||
},
|
||||
|
||||
getTargets: function() {
|
||||
return Object.keys(this.appInfoMap)
|
||||
.map(appId => this.appInfoMap[appId].target);
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
@ -188,29 +191,39 @@ XPCOMUtils.defineLazyGetter(this, "gMap", function() {
|
||||
* 'SecureElementManager' is the main object that handles IPC messages from
|
||||
* child process. It interacts with other objects such as 'gMap' & 'Connector
|
||||
* instances (UiccConnector, eSEConnector)' to perform various
|
||||
* SE-related (open,close,transmit) operations.
|
||||
* SE-related (open, close, transmit) operations.
|
||||
* @TODO: Bug 1118097 Support slot based SE/reader names
|
||||
* @TODO: Bug 1118101 Introduce SE type specific permissions
|
||||
*/
|
||||
function SecureElementManager() {
|
||||
this._registerMessageListeners();
|
||||
this._registerSEListeners();
|
||||
Services.obs.addObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID, false);
|
||||
}
|
||||
|
||||
SecureElementManager.prototype = {
|
||||
QueryInterface: XPCOMUtils.generateQI([
|
||||
Ci.nsIMessageListener,
|
||||
Ci.nsISEListener,
|
||||
Ci.nsIObserver]),
|
||||
classID: SECUREELEMENTMANAGER_CID,
|
||||
classInfo: XPCOMUtils.generateCI({
|
||||
classID: SECUREELEMENTMANAGER_CID,
|
||||
classDescription: "SecureElementManager",
|
||||
interfaces: [Ci.nsIMessageListener,
|
||||
Ci.nsISEListener,
|
||||
Ci.nsIObserver]
|
||||
}),
|
||||
|
||||
// Stores information about supported SE types and their presence.
|
||||
// key: secure element type, value: (Boolean) is present/accessible
|
||||
_sePresence: {},
|
||||
|
||||
_shutdown: function() {
|
||||
this.secureelement = null;
|
||||
Services.obs.removeObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID);
|
||||
this._unregisterMessageListeners();
|
||||
this._unregisterSEListeners();
|
||||
},
|
||||
|
||||
_registerMessageListeners: function() {
|
||||
@ -228,19 +241,36 @@ SecureElementManager.prototype = {
|
||||
ppmm = null;
|
||||
},
|
||||
|
||||
_getAvailableReaderTypes: function() {
|
||||
let readerTypes = [];
|
||||
// TODO 1: Bug 1118096 - Add IDL so that other sub-systems such as RIL ,
|
||||
// NFC can implement it.
|
||||
// TODO 2: Bug 1118097 - According to OpenMobile spec, the reader names
|
||||
// should support slot based naming convention.
|
||||
// i;e; Instead of returning 'uicc', return 'uicc<slot#>'.
|
||||
|
||||
if (UiccConnector) {
|
||||
readerTypes.push(SE.TYPE_UICC);
|
||||
_registerSEListeners: function() {
|
||||
let connector = getConnector(SE.TYPE_UICC);
|
||||
if (!connector) {
|
||||
return;
|
||||
}
|
||||
|
||||
return readerTypes;
|
||||
this._sePresence[SE.TYPE_UICC] = false;
|
||||
connector.registerListener(this);
|
||||
},
|
||||
|
||||
_unregisterSEListeners: function() {
|
||||
Object.keys(this._sePresence).forEach((type) => {
|
||||
let connector = getConnector(type);
|
||||
if (connector) {
|
||||
connector.unregisterListener(this);
|
||||
}
|
||||
});
|
||||
|
||||
this._sePresence = {};
|
||||
},
|
||||
|
||||
notifySEPresenceChanged: function(type, isPresent) {
|
||||
// we need to notify all targets, even those without open channels,
|
||||
// app could've stored the reader without actually using it
|
||||
debug("notifying DOM about SE state change");
|
||||
this._sePresence[type] = isPresent;
|
||||
gMap.getTargets().forEach(target => {
|
||||
let result = { type: type, isPresent: isPresent };
|
||||
target.sendAsyncMessage("SE:ReaderPresenceChanged", { result: result });
|
||||
});
|
||||
},
|
||||
|
||||
_canOpenChannel: function(appId, type) {
|
||||
@ -357,11 +387,11 @@ SecureElementManager.prototype = {
|
||||
},
|
||||
|
||||
_handleGetSEReadersRequest: function(msg, target, callback) {
|
||||
// TODO: Bug 1118101 Get supported readerTypes based on the permissions
|
||||
// available for the given application.
|
||||
let seReaderTypes = this._getAvailableReaderTypes();
|
||||
gMap.registerSecureElementTarget(msg.appId, seReaderTypes, target);
|
||||
callback({ readerTypes: seReaderTypes, error: SE.ERROR_NONE });
|
||||
gMap.registerSecureElementTarget(msg.appId, target);
|
||||
let readers = Object.keys(this._sePresence).map(type => {
|
||||
return { type: type, isPresent: this._sePresence[type] };
|
||||
});
|
||||
callback({ readers: readers, error: SE.ERROR_NONE });
|
||||
},
|
||||
|
||||
_handleChildProcessShutdown: function(target) {
|
||||
|
@ -20,7 +20,7 @@
|
||||
/* globals Components, XPCOMUtils, SE, dump, libcutils, Services,
|
||||
iccProvider, iccService, SEUtils */
|
||||
|
||||
const { interfaces: Ci, utils: Cu } = Components;
|
||||
const { interfaces: Ci, utils: Cu, results: Cr } = Components;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
@ -73,7 +73,8 @@ function UiccConnector() {
|
||||
}
|
||||
|
||||
UiccConnector.prototype = {
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsISecureElementConnector]),
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsISecureElementConnector,
|
||||
Ci.nsIIccListener]),
|
||||
classID: UICCCONNECTOR_CID,
|
||||
classInfo: XPCOMUtils.generateCI({
|
||||
classID: UICCCONNECTOR_CID,
|
||||
@ -84,6 +85,7 @@ UiccConnector.prototype = {
|
||||
Ci.nsIObserver]
|
||||
}),
|
||||
|
||||
_SEListeners: [],
|
||||
_isPresent: false,
|
||||
|
||||
_init: function() {
|
||||
@ -113,8 +115,18 @@ UiccConnector.prototype = {
|
||||
];
|
||||
|
||||
let cardState = iccService.getIccByServiceId(PREFERRED_UICC_CLIENTID).cardState;
|
||||
this._isPresent = cardState !== null &&
|
||||
let uiccPresent = cardState !== null &&
|
||||
uiccNotReadyStates.indexOf(cardState) == -1;
|
||||
|
||||
if (this._isPresent === uiccPresent) {
|
||||
return;
|
||||
}
|
||||
|
||||
debug("Uicc presence changed " + this._isPresent + " -> " + uiccPresent);
|
||||
this._isPresent = uiccPresent;
|
||||
this._SEListeners.forEach((listener) => {
|
||||
listener.notifySEPresenceChanged(SE.TYPE_UICC, this._isPresent);
|
||||
});
|
||||
},
|
||||
|
||||
// See GP Spec, 11.1.4 Class Byte Coding
|
||||
@ -305,6 +317,23 @@ UiccConnector.prototype = {
|
||||
});
|
||||
},
|
||||
|
||||
registerListener: function(listener) {
|
||||
if (this._SEListeners.indexOf(listener) !== -1) {
|
||||
throw Cr.NS_ERROR_UNEXPECTED;
|
||||
}
|
||||
|
||||
this._SEListeners.push(listener);
|
||||
// immediately notify listener about the current state
|
||||
listener.notifySEPresenceChanged(SE.TYPE_UICC, this._isPresent);
|
||||
},
|
||||
|
||||
unregisterListener: function(listener) {
|
||||
let idx = this._SEListeners.indexOf(listener);
|
||||
if (idx !== -1) {
|
||||
this._listeners.splice(idx, 1);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* nsIIccListener interface methods.
|
||||
*/
|
||||
@ -315,6 +344,7 @@ UiccConnector.prototype = {
|
||||
notifyIccInfoChanged: function() {},
|
||||
|
||||
notifyCardStateChanged: function() {
|
||||
debug("Card state changed, updating UICC presence.");
|
||||
this._updatePresenceState();
|
||||
},
|
||||
|
||||
|
@ -46,7 +46,13 @@ interface nsISEChannelCallback : nsISupports
|
||||
void notifyError(in DOMString error);
|
||||
};
|
||||
|
||||
[scriptable, uuid(88e23684-0de3-4792-83a0-0eb67a6ca448)]
|
||||
[scriptable, uuid(417f59ee-f582-45b9-9a4e-e9dcefecb4f7)]
|
||||
interface nsISEListener : nsISupports
|
||||
{
|
||||
void notifySEPresenceChanged(in DOMString seType, in boolean isPresent);
|
||||
};
|
||||
|
||||
[scriptable, uuid(3cef313a-1d01-432d-9cd2-6610a80911f3)]
|
||||
interface nsISecureElementConnector : nsISupports
|
||||
{
|
||||
/**
|
||||
@ -101,4 +107,18 @@ interface nsISecureElementConnector : nsISupports
|
||||
*/
|
||||
void closeChannel(in long channel,
|
||||
in nsISEChannelCallback callback);
|
||||
|
||||
/**
|
||||
* Register a Secure Element listener
|
||||
*
|
||||
* @param listener
|
||||
*/
|
||||
void registerListener(in nsISEListener listener);
|
||||
|
||||
/**
|
||||
* Unregister a Secure Element listener
|
||||
*
|
||||
* @param listener
|
||||
*/
|
||||
void unregisterListener(in nsISEListener listener);
|
||||
};
|
||||
|
@ -400,6 +400,7 @@ this.GECKO_PREFERRED_NETWORK_TYPE_EVDO_ONLY = "evdo";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_WCDMA_GSM_CDMA_EVDO = "wcdma/gsm/cdma/evdo";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_LTE_CDMA_EVDO = "lte/cdma/evdo";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA_GSM = "lte/wcdma/gsm";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA = "lte/wcdma";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA_GSM_CDMA_EVDO = "lte/wcdma/gsm/cdma/evdo";
|
||||
this.GECKO_PREFERRED_NETWORK_TYPE_LTE_ONLY = "lte";
|
||||
this.RIL_PREFERRED_NETWORK_TYPE_TO_GECKO = [
|
||||
@ -414,7 +415,8 @@ this.RIL_PREFERRED_NETWORK_TYPE_TO_GECKO = [
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_CDMA_EVDO,
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA_GSM,
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA_GSM_CDMA_EVDO,
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_ONLY
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_ONLY,
|
||||
GECKO_PREFERRED_NETWORK_TYPE_LTE_WCDMA
|
||||
];
|
||||
|
||||
this.GECKO_SUPPORTED_NETWORK_TYPES_DEFAULT = "gsm,wcdma";
|
||||
|
@ -44,6 +44,19 @@ var NotificationTest = (function () {
|
||||
})(tests);
|
||||
}
|
||||
|
||||
function fakeApp(aManifest) {
|
||||
var aApp = {
|
||||
"origin": "{mochitest}",
|
||||
"manifestURL": aManifest
|
||||
};
|
||||
|
||||
SpecialPowers.injectApp("{mochitest}", aApp);
|
||||
}
|
||||
|
||||
function unfakeApp() {
|
||||
SpecialPowers.rejectApp("{mochitest}");
|
||||
}
|
||||
|
||||
var fakeCustomData = (function () {
|
||||
var buffer = new ArrayBuffer(2);
|
||||
var dv = new DataView(buffer).setInt16(0, 42, true);
|
||||
@ -107,6 +120,10 @@ var NotificationTest = (function () {
|
||||
|
||||
info: info,
|
||||
|
||||
fakeApp: fakeApp,
|
||||
|
||||
unfakeApp: unfakeApp,
|
||||
|
||||
customDataMatches: function(dataObj) {
|
||||
var url = "http://www.domain.com";
|
||||
try {
|
||||
|
@ -10,3 +10,6 @@ skip-if = toolkit == 'android' || toolkit == 'gonk' #bug 960762
|
||||
[test_bug931307.html]
|
||||
skip-if = (toolkit == 'gonk' && debug) #debug-only timeout
|
||||
[test_notification_resend.html]
|
||||
skip-if = e10s # On e10s, faking the app seems to be failing
|
||||
[test_notification_noresend.html]
|
||||
skip-if = (toolkit == 'gonk') # Mochitest on Gonk registers an app manifest that messes with the logic
|
||||
|
@ -0,0 +1,88 @@
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<head>
|
||||
<title>Testing mozResendAllNotifications() resend behavior for Pages</title>
|
||||
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<script type="text/javascript" src="MockServices.js"></script>
|
||||
<script type="text/javascript" src="NotificationTest.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
|
||||
</head>
|
||||
<body>
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1159128">Bug 1159128</a>
|
||||
<p id="display"></p>
|
||||
<div id="content" style="display: none"></div>
|
||||
<pre id="test"></pre>
|
||||
<script type="text/javascript">
|
||||
var info = NotificationTest.info;
|
||||
var notifications = [];
|
||||
|
||||
SimpleTest.requestFlakyTimeout("untriaged");
|
||||
|
||||
var steps = [
|
||||
function (done) {
|
||||
if (window.Notification) {
|
||||
SpecialPowers.pushPrefEnv({"set": [
|
||||
["dom.ignore_webidl_scope_checks", true],
|
||||
]}, done);
|
||||
} else {
|
||||
ok(true, "Notifications are not enabled on the platform.");
|
||||
done();
|
||||
}
|
||||
},
|
||||
|
||||
function (done) {
|
||||
info("Test that we have mozChromeNotifications API");
|
||||
ok(('mozChromeNotifications' in navigator), "should have mozChromeNotifications API");
|
||||
ok(('mozResendAllNotifications' in navigator.mozChromeNotifications), "should have mozResendAllNotifications()");
|
||||
done();
|
||||
},
|
||||
|
||||
function (done) {
|
||||
info("Making sure we have no previous notification pending");
|
||||
var promise = Notification.get();
|
||||
promise.then(function (notifications) {
|
||||
is(notifications.length, 0, "notifications are all cleaned");
|
||||
done();
|
||||
});
|
||||
},
|
||||
|
||||
// The notification is expected to be created and living properly
|
||||
// so it will be accessible via Notification.get(), but NotificationStorage
|
||||
// should not have sent it to NotificationDB.
|
||||
function (done) {
|
||||
info("Sending one notification");
|
||||
var notif = new Notification("title");
|
||||
ok(notif, "Notification object is valid");
|
||||
notifications.push(notif);
|
||||
|
||||
var promise = Notification.get();
|
||||
promise.then(function (notifications) {
|
||||
is(notifications.length, 1, "one notification has been sent");
|
||||
done();
|
||||
});
|
||||
},
|
||||
|
||||
// mozResendAllNotifications will poke directly NotificationDB, so we
|
||||
// expect our notification to NOT have been put there and thus not being
|
||||
// resent.
|
||||
function (done) {
|
||||
info("Trying to resend the notification");
|
||||
var notif = notifications.pop();
|
||||
notif.onclose = function() {
|
||||
done();
|
||||
};
|
||||
|
||||
navigator.mozChromeNotifications.mozResendAllNotifications(function(number) {
|
||||
is(number, 0, "No notification resent");
|
||||
notif.close();
|
||||
});
|
||||
}
|
||||
];
|
||||
|
||||
MockServices.register();
|
||||
NotificationTest.run(steps, function () {
|
||||
MockServices.unregister();
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
@ -1,7 +1,7 @@
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<head>
|
||||
<title>Testing mozResendAllNotifications() resend behavior</title>
|
||||
<title>Testing mozResendAllNotifications() resend behavior for Apps</title>
|
||||
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<script type="text/javascript" src="MockServices.js"></script>
|
||||
<script type="text/javascript" src="NotificationTest.js"></script>
|
||||
@ -21,17 +21,6 @@
|
||||
SimpleTest.requestFlakyTimeout("untriaged");
|
||||
|
||||
var steps = [
|
||||
function (done) {
|
||||
if (window.Notification) {
|
||||
SpecialPowers.pushPrefEnv({"set": [
|
||||
["dom.ignore_webidl_scope_checks", true],
|
||||
]}, done);
|
||||
} else {
|
||||
ok(true, "Notifications are not enabled on the platform.");
|
||||
done();
|
||||
}
|
||||
},
|
||||
|
||||
function (done) {
|
||||
info("Set manifestURL");
|
||||
var request = window.navigator.mozApps.getSelf();
|
||||
@ -46,6 +35,18 @@
|
||||
};
|
||||
},
|
||||
|
||||
function (done) {
|
||||
if (window.Notification) {
|
||||
NotificationTest.fakeApp(manifestURL);
|
||||
SpecialPowers.pushPrefEnv({"set": [
|
||||
["dom.ignore_webidl_scope_checks", true],
|
||||
]}, done);
|
||||
} else {
|
||||
ok(true, "Notifications are not enabled on the platform.");
|
||||
done();
|
||||
}
|
||||
},
|
||||
|
||||
function (done) {
|
||||
info("Test that we have mozChromeNotifications API");
|
||||
ok(('mozChromeNotifications' in navigator), "should have mozChromeNotifications API");
|
||||
@ -194,11 +195,12 @@
|
||||
|
||||
notif2.close();
|
||||
});
|
||||
}
|
||||
},
|
||||
];
|
||||
|
||||
MockServices.register();
|
||||
NotificationTest.run(steps, function () {
|
||||
NotificationTest.unfakeApp();
|
||||
MockServices.unregister();
|
||||
});
|
||||
</script>
|
||||
|
@ -9,7 +9,7 @@ enum MobilePreferredNetworkType {"wcdma/gsm", "gsm", "wcdma", "wcdma/gsm-auto",
|
||||
"cdma/evdo", "cdma", "evdo",
|
||||
"wcdma/gsm/cdma/evdo", "lte/cdma/evdo",
|
||||
"lte/wcdma/gsm", "lte/wcdma/gsm/cdma/evdo",
|
||||
"lte"};
|
||||
"lte", "lte/wcdma"};
|
||||
enum MobileRoamingMode {"home", "affiliated", "any"};
|
||||
|
||||
[Pref="dom.mobileconnection.enabled"]
|
||||
@ -187,7 +187,7 @@ interface MozMobileConnection : EventTarget
|
||||
* result will be a string indicating the current preferred network type.
|
||||
* The value will be either 'wcdma/gsm', 'gsm', 'wcdma', 'wcdma/gsm-auto',
|
||||
* 'cdma/evdo', 'cdma', 'evdo', 'wcdma/gsm/cdma/evdo', 'lte/cdma/evdo',
|
||||
* 'lte/wcdma/gsm', 'lte/wcdma/gsm/cdma/evdo' or 'lte'.
|
||||
* 'lte/wcdma/gsm', 'lte/wcdma/gsm/cdma/evdo', 'lte' or 'lte/wcdma'.
|
||||
*
|
||||
* Otherwise, the request's onerror will be called, and the request's error
|
||||
* will be either 'RadioNotAvailable', 'RequestNotSupported',
|
||||
|
@ -15,6 +15,7 @@ enum SEError {
|
||||
"SEBadStateError", // Error occuring as a result of bad state.
|
||||
"SEInvalidChannelError", // Opening a channel failed because no channel is available.
|
||||
"SEInvalidApplicationError", // The requested application was not found on the secure element.
|
||||
"SENotPresentError", // Secure Element is not present
|
||||
"SEGenericError" // Generic failures.
|
||||
};
|
||||
|
||||
|
@ -375,6 +375,33 @@ SpecialPowersObserverAPI.prototype = {
|
||||
scope.UserCustomizations._debug = aMessage.json.value;
|
||||
return;
|
||||
}
|
||||
case "inject-app":
|
||||
{
|
||||
let aAppId = aMessage.json.appId;
|
||||
let aApp = aMessage.json.app;
|
||||
|
||||
let keys = Object.keys(Webapps.DOMApplicationRegistry.webapps);
|
||||
let exists = keys.indexOf(aAppId) !== -1;
|
||||
if (exists) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Webapps.DOMApplicationRegistry.webapps[aAppId] = aApp;
|
||||
return true;
|
||||
}
|
||||
case "reject-app":
|
||||
{
|
||||
let aAppId = aMessage.json.appId;
|
||||
|
||||
let keys = Object.keys(Webapps.DOMApplicationRegistry.webapps);
|
||||
let exists = keys.indexOf(aAppId) !== -1;
|
||||
if (!exists) {
|
||||
return false;
|
||||
}
|
||||
|
||||
delete Webapps.DOMApplicationRegistry.webapps[aAppId];
|
||||
return true;
|
||||
}
|
||||
default:
|
||||
throw new SpecialPowersError("Invalid operation for SPWebAppsService");
|
||||
}
|
||||
|
@ -1135,6 +1135,23 @@ SpecialPowersAPI.prototype = {
|
||||
});
|
||||
},
|
||||
|
||||
// Force-registering an app in the registry
|
||||
injectApp: function(aAppId, aApp) {
|
||||
this._sendSyncMessage("SPWebAppService", {
|
||||
op: "inject-app",
|
||||
appId: aAppId,
|
||||
app: aApp
|
||||
});
|
||||
},
|
||||
|
||||
// Removing app from the registry
|
||||
rejectApp: function(aAppId) {
|
||||
this._sendSyncMessage("SPWebAppService", {
|
||||
op: "reject-app",
|
||||
appId: aAppId
|
||||
});
|
||||
},
|
||||
|
||||
_proxiedObservers: {
|
||||
"specialpowers-http-notify-request": function(aMessage) {
|
||||
let uri = aMessage.json.uri;
|
||||
|
@ -1,49 +0,0 @@
|
||||
---
|
||||
# For complete sample of all build and test jobs,
|
||||
# see <gecko>/testing/taskcluster/tasks/job_flags.yml
|
||||
|
||||
$inherits:
|
||||
from: tasks/branches/mozilla-central/job_flags.yml
|
||||
|
||||
builds:
|
||||
flame-kk:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_flame_kk_opt.yml
|
||||
flame-kk-eng:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_flame_kk_eng.yml
|
||||
aries-nightly:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_aries_lightsaber_nightly_opt.yml
|
||||
debug:
|
||||
task: tasks/builds/b2g_aries_lightsaber_nightly_debug.yml
|
||||
aries-eng:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_aries_lightsaber_eng.yml
|
||||
|
||||
tests:
|
||||
gaia-build:
|
||||
allowed_build_tasks:
|
||||
tasks/builds/b2g_flame_kk_opt.yml:
|
||||
task: tasks/tests/b2g_build_test.yml
|
||||
tasks/builds/b2g_flame_kk_eng.yml:
|
||||
task: tasks/tests/b2g_build_test.yml
|
||||
gaia-linter:
|
||||
allowed_build_tasks:
|
||||
tasks/builds/b2g_flame_kk_opt.yml:
|
||||
task: tasks/tests/b2g_linter.yml
|
||||
tasks/builds/b2g_flame_kk_eng.yml:
|
||||
task: tasks/tests/b2g_linter.yml
|
||||
|
@ -52,6 +52,20 @@ builds:
|
||||
task: tasks/builds/b2g_emulator_ics_opt.yml
|
||||
debug:
|
||||
task: tasks/builds/b2g_emulator_ics_debug.yml
|
||||
aries-nightly:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_aries_lightsaber_nightly_opt.yml
|
||||
debug:
|
||||
task: tasks/builds/b2g_aries_lightsaber_nightly_debug.yml
|
||||
aries-eng:
|
||||
platforms:
|
||||
- b2g
|
||||
types:
|
||||
opt:
|
||||
task: tasks/builds/b2g_aries_lightsaber_eng.yml
|
||||
|
||||
tests:
|
||||
cppunit:
|
||||
|
@ -25,8 +25,8 @@ task:
|
||||
# the board.
|
||||
- 'docker-worker:cache:tc-vcs'
|
||||
- 'docker-worker:image:{{#docker_image}}builder{{/docker_image}}'
|
||||
- 'queue:define-task:aws-provisioner/build-c4-2xlarge'
|
||||
- 'queue:create-task:aws-provisioner/build-c4-2xlarge'
|
||||
- 'queue:define-task:aws-provisioner-v1/build-c4-2xlarge'
|
||||
- 'queue:create-task:aws-provisioner-v1/build-c4-2xlarge'
|
||||
|
||||
|
||||
payload:
|
||||
|
@ -25,6 +25,9 @@ task:
|
||||
cd ./workspace/gecko/testing/taskcluster/scripts/phone-builder &&
|
||||
buildbot_step 'Build' ./build-lightsaber.sh $HOME/workspace
|
||||
extra:
|
||||
treeherderEnv:
|
||||
- production
|
||||
- staging
|
||||
treeherder:
|
||||
symbol: Be
|
||||
groupSymbol: Aries
|
||||
|
@ -18,6 +18,9 @@ task:
|
||||
buildbot_step 'Build' ./build-lightsaber-nightly.sh $HOME/workspace
|
||||
|
||||
extra:
|
||||
treeherderEnv:
|
||||
- production
|
||||
- staging
|
||||
treeherder:
|
||||
symbol: B
|
||||
groupSymbol: Aries
|
||||
|
@ -2,13 +2,16 @@ $inherits:
|
||||
from: 'tasks/builds/b2g_aries_lightsaber_nightly_base.yml'
|
||||
variables:
|
||||
build_name: 'aries'
|
||||
build_type: 'nightly-debug'
|
||||
build_type: 'debug'
|
||||
task:
|
||||
metadata:
|
||||
name: '[TC] B2G Aries Nightly (userdebug)'
|
||||
scopes:
|
||||
- 'docker-worker:cache:build-aries-lightsaber-nightly-debug'
|
||||
|
||||
extra:
|
||||
treeherder:
|
||||
collection:
|
||||
debug: true
|
||||
payload:
|
||||
cache:
|
||||
build-aries-lightsaber-nightly-debug: /home/worker/workspace
|
||||
|
@ -2,7 +2,7 @@ $inherits:
|
||||
from: 'tasks/builds/b2g_aries_lightsaber_nightly_base.yml'
|
||||
variables:
|
||||
build_name: 'aries'
|
||||
build_type: 'nightly-user'
|
||||
build_type: 'opt'
|
||||
task:
|
||||
metadata:
|
||||
name: '[TC] B2G Aries Nightly (user)'
|
||||
|
@ -13,7 +13,7 @@ task:
|
||||
|
||||
scopes:
|
||||
- 'docker-worker:image:{{#docker_image}}tester-device{{/docker_image}}'
|
||||
- 'queue:create-task:aws-provisioner/testdroid-device'
|
||||
- 'queue:create-task:aws-provisioner-v1/testdroid-device'
|
||||
- 'docker-worker:cache:tc-vcs'
|
||||
|
||||
payload:
|
||||
|
@ -13,8 +13,8 @@ task:
|
||||
|
||||
scopes:
|
||||
- 'docker-worker:image:{{#docker_image}}tester{{/docker_image}}'
|
||||
- 'queue:define-task:aws-provisioner/test-c4-2xlarge'
|
||||
- 'queue:create-task:aws-provisioner/test-c4-2xlarge'
|
||||
- 'queue:define-task:aws-provisioner-v1/test-c4-2xlarge'
|
||||
- 'queue:create-task:aws-provisioner-v1/test-c4-2xlarge'
|
||||
- 'docker-worker:cache:tc-vcs'
|
||||
- 'docker-worker:cache:linux-cache'
|
||||
- 'docker-worker:capability:device:loopbackVideo'
|
||||
|
Loading…
Reference in New Issue
Block a user