mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-14 15:37:55 +00:00
341 lines
9.7 KiB
JavaScript
341 lines
9.7 KiB
JavaScript
/* Copyright 2012 Mozilla Foundation and Mozilla contributors
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
"use strict";
|
|
|
|
const {classes: Cc, interfaces: Ci, utils: Cu, results: Cr} = Components;
|
|
|
|
Cu.import("resource://gre/modules/DOMRequestHelper.jsm");
|
|
Cu.import("resource://gre/modules/Services.jsm");
|
|
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
|
|
|
/* global 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";
|
|
|
|
const NS_PREFBRANCH_PREFCHANGE_TOPIC_ID = "nsPref:changed";
|
|
|
|
const kPrefRilNumRadioInterfaces = "ril.numRadioInterfaces";
|
|
const kPrefRilDebuggingEnabled = "ril.debugging.enabled";
|
|
|
|
let DEBUG;
|
|
function debug(s) {
|
|
dump("-*- RILContentHelper: " + s + "\n");
|
|
}
|
|
|
|
const RILCONTENTHELPER_CID =
|
|
Components.ID("{472816e1-1fd6-4405-996c-806f9ea68174}");
|
|
|
|
const RIL_IPC_MSG_NAMES = [
|
|
"RIL:ReadIccContacts",
|
|
"RIL:UpdateIccContact",
|
|
];
|
|
|
|
/* global cpmm */
|
|
XPCOMUtils.defineLazyServiceGetter(this, "cpmm",
|
|
"@mozilla.org/childprocessmessagemanager;1",
|
|
"nsISyncMessageSender");
|
|
|
|
/* global UUIDGenerator */
|
|
XPCOMUtils.defineLazyServiceGetter(this, "UUIDGenerator",
|
|
"@mozilla.org/uuid-generator;1",
|
|
"nsIUUIDGenerator");
|
|
|
|
/* global gNumRadioInterfaces */
|
|
XPCOMUtils.defineLazyGetter(this, "gNumRadioInterfaces", function() {
|
|
let appInfo = Cc["@mozilla.org/xre/app-info;1"];
|
|
let isParentProcess = !appInfo || appInfo.getService(Ci.nsIXULRuntime)
|
|
.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT;
|
|
|
|
if (isParentProcess) {
|
|
let ril = { numRadioInterfaces: 0 };
|
|
try {
|
|
ril = Cc["@mozilla.org/ril;1"].getService(Ci.nsIRadioInterfaceLayer);
|
|
} catch(e) {}
|
|
return ril.numRadioInterfaces;
|
|
}
|
|
|
|
return Services.prefs.getIntPref(kPrefRilNumRadioInterfaces);
|
|
});
|
|
|
|
function RILContentHelper() {
|
|
this.updateDebugFlag();
|
|
|
|
this.numClients = gNumRadioInterfaces;
|
|
if (DEBUG) debug("Number of clients: " + this.numClients);
|
|
|
|
this.initDOMRequestHelper(/* aWindow */ null, RIL_IPC_MSG_NAMES);
|
|
this._windowsMap = [];
|
|
|
|
Services.obs.addObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID, false);
|
|
|
|
Services.prefs.addObserver(kPrefRilDebuggingEnabled, this, false);
|
|
}
|
|
|
|
RILContentHelper.prototype = {
|
|
__proto__: DOMRequestIpcHelper.prototype,
|
|
|
|
QueryInterface: XPCOMUtils.generateQI([Ci.nsIIccProvider,
|
|
Ci.nsIObserver,
|
|
Ci.nsISupportsWeakReference]),
|
|
classID: RILCONTENTHELPER_CID,
|
|
classInfo: XPCOMUtils.generateCI({classID: RILCONTENTHELPER_CID,
|
|
classDescription: "RILContentHelper",
|
|
interfaces: [Ci.nsIIccProvider]}),
|
|
|
|
updateDebugFlag: function() {
|
|
try {
|
|
DEBUG = RIL.DEBUG_CONTENT_HELPER ||
|
|
Services.prefs.getBoolPref(kPrefRilDebuggingEnabled);
|
|
} catch (e) {}
|
|
},
|
|
|
|
_windowsMap: null,
|
|
|
|
/**
|
|
* nsIIccProvider
|
|
*/
|
|
|
|
readContacts: function(clientId, window, contactType) {
|
|
if (window == null) {
|
|
throw Components.Exception("Can't get window object",
|
|
Cr.NS_ERROR_UNEXPECTED);
|
|
}
|
|
|
|
let request = Services.DOMRequest.createRequest(window);
|
|
let requestId = this.getRequestId(request);
|
|
this._windowsMap[requestId] = window;
|
|
|
|
cpmm.sendAsyncMessage("RIL:ReadIccContacts", {
|
|
clientId: clientId,
|
|
data: {
|
|
requestId: requestId,
|
|
contactType: contactType
|
|
}
|
|
});
|
|
return request;
|
|
},
|
|
|
|
updateContact: function(clientId, window, contactType, contact, pin2) {
|
|
if (window == null) {
|
|
throw Components.Exception("Can't get window object",
|
|
Cr.NS_ERROR_UNEXPECTED);
|
|
}
|
|
|
|
let request = Services.DOMRequest.createRequest(window);
|
|
let requestId = this.getRequestId(request);
|
|
this._windowsMap[requestId] = window;
|
|
|
|
// Parsing nsDOMContact to Icc Contact format
|
|
let iccContact = {};
|
|
|
|
if (Array.isArray(contact.name) && contact.name[0]) {
|
|
iccContact.alphaId = contact.name[0];
|
|
}
|
|
|
|
if (Array.isArray(contact.tel)) {
|
|
iccContact.number = contact.tel[0] && contact.tel[0].value;
|
|
let telArray = contact.tel.slice(1);
|
|
let length = telArray.length;
|
|
if (length > 0) {
|
|
iccContact.anr = [];
|
|
}
|
|
for (let i = 0; i < telArray.length; i++) {
|
|
iccContact.anr.push(telArray[i].value);
|
|
}
|
|
}
|
|
|
|
if (Array.isArray(contact.email) && contact.email[0]) {
|
|
iccContact.email = contact.email[0].value;
|
|
}
|
|
|
|
iccContact.contactId = contact.id;
|
|
|
|
cpmm.sendAsyncMessage("RIL:UpdateIccContact", {
|
|
clientId: clientId,
|
|
data: {
|
|
requestId: requestId,
|
|
contactType: contactType,
|
|
contact: iccContact,
|
|
pin2: pin2
|
|
}
|
|
});
|
|
|
|
return request;
|
|
},
|
|
|
|
// nsIObserver
|
|
|
|
observe: function(subject, topic, data) {
|
|
switch (topic) {
|
|
case NS_PREFBRANCH_PREFCHANGE_TOPIC_ID:
|
|
if (data == kPrefRilDebuggingEnabled) {
|
|
this.updateDebugFlag();
|
|
}
|
|
break;
|
|
|
|
case NS_XPCOM_SHUTDOWN_OBSERVER_ID:
|
|
this.destroyDOMRequestHelper();
|
|
Services.obs.removeObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID);
|
|
break;
|
|
}
|
|
},
|
|
|
|
// nsIMessageListener
|
|
|
|
fireRequestSuccess: function(requestId, result) {
|
|
let request = this.takeRequest(requestId);
|
|
if (!request) {
|
|
if (DEBUG) {
|
|
debug("not firing success for id: " + requestId +
|
|
", result: " + JSON.stringify(result));
|
|
}
|
|
return;
|
|
}
|
|
|
|
if (DEBUG) {
|
|
debug("fire request success, id: " + requestId +
|
|
", result: " + JSON.stringify(result));
|
|
}
|
|
Services.DOMRequest.fireSuccess(request, result);
|
|
},
|
|
|
|
dispatchFireRequestSuccess: function(requestId, result) {
|
|
let currentThread = Services.tm.currentThread;
|
|
|
|
currentThread.dispatch(this.fireRequestSuccess.bind(this, requestId, result),
|
|
Ci.nsIThread.DISPATCH_NORMAL);
|
|
},
|
|
|
|
fireRequestError: function(requestId, error) {
|
|
let request = this.takeRequest(requestId);
|
|
if (!request) {
|
|
if (DEBUG) {
|
|
debug("not firing error for id: " + requestId +
|
|
", error: " + JSON.stringify(error));
|
|
}
|
|
return;
|
|
}
|
|
|
|
if (DEBUG) {
|
|
debug("fire request error, id: " + requestId +
|
|
", result: " + JSON.stringify(error));
|
|
}
|
|
Services.DOMRequest.fireError(request, error);
|
|
},
|
|
|
|
dispatchFireRequestError: function(requestId, error) {
|
|
let currentThread = Services.tm.currentThread;
|
|
|
|
currentThread.dispatch(this.fireRequestError.bind(this, requestId, error),
|
|
Ci.nsIThread.DISPATCH_NORMAL);
|
|
},
|
|
|
|
fireRequestDetailedError: function(requestId, detailedError) {
|
|
let request = this.takeRequest(requestId);
|
|
if (!request) {
|
|
if (DEBUG) {
|
|
debug("not firing detailed error for id: " + requestId +
|
|
", detailedError: " + JSON.stringify(detailedError));
|
|
}
|
|
return;
|
|
}
|
|
|
|
Services.DOMRequest.fireDetailedError(request, detailedError);
|
|
},
|
|
|
|
receiveMessage: function(msg) {
|
|
let request;
|
|
if (DEBUG) {
|
|
debug("Received message '" + msg.name + "': " + JSON.stringify(msg.json));
|
|
}
|
|
|
|
let data = msg.json.data;
|
|
let clientId = msg.json.clientId;
|
|
switch (msg.name) {
|
|
case "RIL:ReadIccContacts":
|
|
this.handleReadIccContacts(data);
|
|
break;
|
|
case "RIL:UpdateIccContact":
|
|
this.handleUpdateIccContact(data);
|
|
break;
|
|
}
|
|
},
|
|
|
|
handleReadIccContacts: function(message) {
|
|
if (message.errorMsg) {
|
|
this.fireRequestError(message.requestId, message.errorMsg);
|
|
return;
|
|
}
|
|
|
|
let window = this._windowsMap[message.requestId];
|
|
delete this._windowsMap[message.requestId];
|
|
let contacts = message.contacts;
|
|
let result = new window.Array();
|
|
contacts.forEach(function(c) {
|
|
let prop = {name: [c.alphaId], tel: [{value: c.number}]};
|
|
|
|
if (c.email) {
|
|
prop.email = [{value: c.email}];
|
|
}
|
|
|
|
// ANR - Additional Number
|
|
let anrLen = c.anr ? c.anr.length : 0;
|
|
for (let i = 0; i < anrLen; i++) {
|
|
prop.tel.push({value: c.anr[i]});
|
|
}
|
|
|
|
let contact = new window.mozContact(prop);
|
|
contact.id = c.contactId;
|
|
result.push(contact);
|
|
});
|
|
|
|
this.fireRequestSuccess(message.requestId, result);
|
|
},
|
|
|
|
handleUpdateIccContact: function(message) {
|
|
if (message.errorMsg) {
|
|
this.fireRequestError(message.requestId, message.errorMsg);
|
|
return;
|
|
}
|
|
|
|
let window = this._windowsMap[message.requestId];
|
|
delete this._windowsMap[message.requestId];
|
|
let iccContact = message.contact;
|
|
let prop = {name: [iccContact.alphaId], tel: [{value: iccContact.number}]};
|
|
if (iccContact.email) {
|
|
prop.email = [{value: iccContact.email}];
|
|
}
|
|
|
|
// ANR - Additional Number
|
|
let anrLen = iccContact.anr ? iccContact.anr.length : 0;
|
|
for (let i = 0; i < anrLen; i++) {
|
|
prop.tel.push({value: iccContact.anr[i]});
|
|
}
|
|
|
|
let contact = new window.mozContact(prop);
|
|
contact.id = iccContact.contactId;
|
|
|
|
this.fireRequestSuccess(message.requestId, contact);
|
|
}
|
|
};
|
|
|
|
this.NSGetFactory = XPCOMUtils.generateNSGetFactory([RILContentHelper]);
|