Bug 999334 - Redesign pending outgoing call mechanism. r=hsinyi
authorSzu-Yu Chen [:aknow] <szchen@mozilla.com>
Fri, 25 Apr 2014 14:59:40 +0800
changeset 180615 6234b7cdf8ce9c27ebff1a25f46dce1d4d6967f5
parent 180614 f2cf7149ebc6934fd46b941e1bef44d8e431c80e
child 180616 a436956eb6302b4f81e99097386174836b505640
push id272
push userpvanderbeken@mozilla.com
push dateMon, 05 May 2014 16:31:18 +0000
reviewershsinyi
bugs999334
milestone31.0a1
Bug 999334 - Redesign pending outgoing call mechanism. r=hsinyi
dom/system/gonk/ril_worker.js
--- a/dom/system/gonk/ril_worker.js
+++ b/dom/system/gonk/ril_worker.js
@@ -1493,16 +1493,21 @@ RilObject.prototype = {
       options.featureStr = options.number;
       this.sendCdmaFlashCommand(options);
     } else {
       this.sendDialRequest(options);
     }
   },
 
   sendDialRequest: function(options) {
+    // Always succeed.
+    options.success = true;
+    this.sendChromeMessage(options);
+    this._createPendingOutgoingCall(options);
+
     let Buf = this.context.Buf;
     Buf.newParcel(options.request, options);
     Buf.writeString(options.number);
     Buf.writeInt32(options.clirMode || 0);
     Buf.writeInt32(options.uusInfo || 0);
     // TODO Why do we need this extra 0? It was put it in to make this
     // match the format of the binary message.
     Buf.writeInt32(0);
@@ -1536,16 +1541,17 @@ RilObject.prototype = {
   hangUp: function(options) {
     let call = this.currentCalls[options.callIndex];
     if (!call) {
       return;
     }
 
     let callIndex = call.callIndex;
     if (callIndex === OUTGOING_PLACEHOLDER_CALL_INDEX) {
+      if (DEBUG) this.context.debug("Hang up pending outgoing call.");
       this._removeVoiceCall(call, GECKO_CALL_ERROR_NORMAL_CALL_CLEARING);
       return;
     }
 
     if (call.state === CALL_STATE_HOLDING) {
       this.sendHangUpBackgroundRequest(callIndex);
     } else {
       this.sendHangUpRequest(callIndex);
@@ -3841,37 +3847,37 @@ RilObject.prototype = {
         this.currentConference.cache[currentCall.callIndex] = newCall;
         currentCall.state = newCall.state;
         currentCall.isMpty = newCall.isMpty;
         conferenceChanged = true;
       }
     }
 
     if (pendingOutgoingCall) {
-      // We don't get a successful call for pendingOutgoingCall.
       if (!newCalls || Object.keys(newCalls).length === 0) {
-        if (DEBUG) this.context.debug("No result for pending outgoing call.");
-        pendingOutgoingCall.failCause = GECKO_CALL_ERROR_UNSPECIFIED;
-        this._handleDisconnectedCall(pendingOutgoingCall);
-      }
-
-      delete this.currentCalls[OUTGOING_PLACEHOLDER_CALL_INDEX];
+        // We don't get a successful call for pendingOutgoingCall.
+        this._removePendingOutgoingCall(GECKO_CALL_ERROR_UNSPECIFIED);
+      } else {
+        // Only remove it from currentCalls map. Will use the new call to
+        // replace the placeholder.
+        delete this.currentCalls[OUTGOING_PLACEHOLDER_CALL_INDEX];
+      }
     }
 
     // Go through any remaining calls that are new to us.
     for each (let newCall in newCalls) {
       if (newCall.isVoice) {
         if (newCall.isMpty) {
           conferenceChanged = true;
         }
         if (!pendingOutgoingCall &&
             (newCall.state === CALL_STATE_DIALING ||
              newCall.state === CALL_STATE_ALERTING)) {
           // Receive a new outgoing call which is already hung up by user.
-          if (DEBUG) this.context.debug("Hang up pending outgoing call");
+          if (DEBUG) this.context.debug("Pending outgoing call is hung up by user.");
           this.sendHangUpRequest(newCall.callIndex);
         } else {
           this._addNewVoiceCall(newCall);
         }
       }
     }
 
     if (clearConferenceRequest) {
@@ -3928,16 +3934,35 @@ RilObject.prototype = {
         this.getFailCauseCode((function(call, failCause) {
           call.failCause = failCause;
           this._handleDisconnectedCall(call);
         }).bind(this, removedCall));
       }
     }
   },
 
+  _createPendingOutgoingCall: function(options) {
+    if (DEBUG) this.context.debug("Create a pending outgoing call.");
+    this._addNewVoiceCall({
+      number: options.number,
+      state: CALL_STATE_DIALING,
+      callIndex: OUTGOING_PLACEHOLDER_CALL_INDEX
+    });
+  },
+
+  _removePendingOutgoingCall: function(failCause) {
+    let call = this.currentCalls[OUTGOING_PLACEHOLDER_CALL_INDEX];
+    if (!call) {
+      return;
+    }
+
+    if (DEBUG) this.context.debug("Remove pending outgoing call.");
+    this._removeVoiceCall(pendingOutgoingCall, failCause);
+  },
+
   _ensureConference: function() {
     let oldState = this.currentConference.state;
     let remaining = Object.keys(this.currentConference.participants);
 
     if (remaining.length == 1) {
       // Remove that if only does one remain in a conference call.
       let call = this.currentCalls[remaining[0]];
       call.isConference = false;
@@ -5324,34 +5349,24 @@ RilObject.prototype[REQUEST_GET_CURRENT_
       };
     }
 
     calls[call.callIndex] = call;
   }
   this._processCalls(calls);
 };
 RilObject.prototype[REQUEST_DIAL] = function REQUEST_DIAL(length, options) {
-  options.success = (options.rilRequestError === 0);
-  if (options.success) {
-    this.sendChromeMessage(options);
-
-    // Create a pending outgoing call.
-    if (DEBUG) this.context.debug("Create a pending outgoing call.");
-    this._addNewVoiceCall({
-      number: options.number,
-      state: CALL_STATE_DIALING,
-      callIndex: OUTGOING_PLACEHOLDER_CALL_INDEX
-    });
-  } else {
-    this.getFailCauseCode((function(options, failCause) {
-      options.errorMsg = failCause;
-      this.sendChromeMessage(options);
-    }).bind(this, options));
-  }
-};
+  // We already return a successful response before. Don't respond it again!
+  if (options.rilRequestError) {
+    this.getFailCauseCode((function(failCause) {
+      this._removePendingOutgoingCall(failCause);
+    }).bind(this));
+  }
+};
+RilObject.prototype[REQUEST_DIAL_EMERGENCY_CALL] = RilObject.prototype[REQUEST_DIAL];
 RilObject.prototype[REQUEST_GET_IMSI] = function REQUEST_GET_IMSI(length, options) {
   if (options.rilRequestError) {
     return;
   }
 
   this.iccInfoPrivate.imsi = this.context.Buf.readString();
   if (DEBUG) {
     this.context.debug("IMSI: " + this.iccInfoPrivate.imsi);