ConnectionServiceWrapper.java revision b78b27693afbe9736f0a54ec473328955251f885
163aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon/*
263aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * Copyright 2014, The Android Open Source Project
363aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon *
463aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * Licensed under the Apache License, Version 2.0 (the "License");
563aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * you may not use this file except in compliance with the License.
663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * You may obtain a copy of the License at
763aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon *
863aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon *     http://www.apache.org/licenses/LICENSE-2.0
963aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon *
1063aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * Unless required by applicable law or agreed to in writing, software
1163aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * distributed under the License is distributed on an "AS IS" BASIS,
1263aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1363aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * See the License for the specific language governing permissions and
1463aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon * limitations under the License.
1563aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon */
1663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon
1763aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordonpackage com.android.telecomm;
1863aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon
199d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepalimport android.app.PendingIntent;
205924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordonimport android.content.ComponentName;
21e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepalimport android.net.Uri;
22a05805b839edea9b9fe3bd4a0fbaf310c2a32838Evan Charltonimport android.os.Bundle;
233d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordonimport android.os.Handler;
2463aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordonimport android.os.IBinder;
253d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordonimport android.os.Message;
2663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordonimport android.os.RemoteException;
276aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepalimport android.telecomm.CallAudioState;
28a3cb9e34db5952f0852c1a3230870cc6e378f246Ihab Awadimport android.telecomm.ConnectionRequest;
29f2f14efaf1ac2cd1e78d29b9d7213696746f1f17Santos Cordonimport android.telecomm.ConnectionService;
30c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepalimport android.telecomm.GatewayInfo;
3172890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordonimport android.telecomm.ParcelableConnection;
32b78b27693afbe9736f0a54ec473328955251f885Ihab Awadimport android.telecomm.PhoneAccount;
33b78b27693afbe9736f0a54ec473328955251f885Ihab Awadimport android.telecomm.PhoneAccountHandle;
3435faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepalimport android.telecomm.StatusHints;
35a3cb9e34db5952f0852c1a3230870cc6e378f246Ihab Awadimport android.telephony.DisconnectCause;
36a439e1b6d6201dedecfc40b67c9347a8c563b9c1Sailesh Nepal
373d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordonimport com.android.internal.os.SomeArgs;
38c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepalimport com.android.internal.telecomm.IConnectionService;
39c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepalimport com.android.internal.telecomm.IConnectionServiceAdapter;
403bcf935b25470e94c8c6855862434d15b785c54aAndrew Leeimport com.android.internal.telecomm.IVideoCallProvider;
415924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordonimport com.android.internal.telecomm.RemoteServiceCallback;
420e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepalimport com.google.common.base.Preconditions;
433d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
44b78b27693afbe9736f0a54ec473328955251f885Ihab Awadimport java.io.IOException;
455924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordonimport java.util.ArrayList;
465924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordonimport java.util.Collection;
47b78b27693afbe9736f0a54ec473328955251f885Ihab Awadimport java.util.Collections;
48682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordonimport java.util.HashMap;
49a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordonimport java.util.HashSet;
508f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordonimport java.util.List;
51682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordonimport java.util.Map;
523d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordonimport java.util.Set;
5363aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon
5463aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon/**
55c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal * Wrapper for {@link IConnectionService}s, handles binding to {@link IConnectionService} and keeps
56c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal * track of when the object can safely be unbound. Other classes should not use
57c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal * {@link IConnectionService} directly and instead should use this class to invoke methods of
58c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal * {@link IConnectionService}.
5963aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon */
60c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepalfinal class ConnectionServiceWrapper extends ServiceBinder<IConnectionService> {
61664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_HANDLE_CREATE_CONNECTION_SUCCESSFUL = 1;
62664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_HANDLE_CREATE_CONNECTION_FAILED = 2;
63664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_HANDLE_CREATE_CONNECTION_CANCELLED = 3;
64664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_ACTIVE = 4;
65664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_RINGING = 5;
66664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_DIALING = 6;
67664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_DISCONNECTED = 7;
68664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_ON_HOLD = 8;
69664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_REQUESTING_RINGBACK = 9;
70664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_CALL_CAPABILITIES = 10;
71664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_IS_CONFERENCED = 11;
72664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_ADD_CONFERENCE_CALL = 12;
73664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_REMOVE_CALL = 13;
74664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_ON_POST_DIAL_WAIT = 14;
75664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_QUERY_REMOTE_CALL_SERVICES = 15;
76664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_CALL_VIDEO_PROVIDER = 16;
77664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_AUDIO_MODE_IS_VOIP = 17;
78664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_STATUS_HINTS = 18;
79664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_HANDLE = 19;
80664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private static final int MSG_SET_CALLER_DISPLAY_NAME = 20;
810a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn    private static final int MSG_SET_VIDEO_STATE = 21;
829d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal    private static final int MSG_START_ACTIVITY_FROM_IN_CALL = 22;
83c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal
84c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private final Handler mHandler = new Handler() {
85c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        @Override
86c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        public void handleMessage(Message msg) {
87c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            Call call;
88c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            switch (msg.what) {
89664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                case MSG_HANDLE_CREATE_CONNECTION_SUCCESSFUL: {
9072890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                    SomeArgs args = (SomeArgs) msg.obj;
9172890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                    try {
9272890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                        ConnectionRequest request = (ConnectionRequest) args.arg1;
9372890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                        if (mPendingResponses.containsKey(request.getCallId())) {
9472890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                            ParcelableConnection connection = (ParcelableConnection) args.arg2;
9572890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                            mPendingResponses.remove(request.getCallId()).
9672890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                                    handleCreateConnectionSuccessful(request, connection);
9772890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                        }
9872890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                    } finally {
9972890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                        args.recycle();
100682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon                    }
101c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
102c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
103664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                case MSG_HANDLE_CREATE_CONNECTION_FAILED: {
104c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
105c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    try {
106a49c6431a8859d0ea2af788d123e1b35123e9502Sailesh Nepal                        ConnectionRequest request = (ConnectionRequest) args.arg1;
107c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        int statusCode = args.argi1;
108c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        String statusMsg = (String) args.arg2;
109fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                        removeCall(
110fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                                mCallIdMapper.getCall(request.getCallId()),
111fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                                statusCode,
112fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                                statusMsg);
113c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } finally {
114c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        args.recycle();
1155a73b03be0a2a929cf9974578445b90f773937b4Sailesh Nepal                    }
116c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
117c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
118664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                case MSG_HANDLE_CREATE_CONNECTION_CANCELLED: {
119c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    ConnectionRequest request = (ConnectionRequest) msg.obj;
120664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                    if (mPendingResponses.containsKey(request.getCallId())) {
121664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                        mPendingResponses.remove(
122664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                                request.getCallId()).handleCreateConnectionCancelled();
123c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
124664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                        //Log.w(this, "handleCreateConnectionCancelled, unknown call: %s", callId);
125c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    }
126c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
127c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
128c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_ACTIVE:
129c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
130c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (call != null) {
131c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        mCallsManager.markCallAsActive(call);
132c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
133c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(this, "setActive, unknown call id: %s", msg.obj);
134c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    }
135c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
136c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_RINGING:
137c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
138c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (call != null) {
139c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        mCallsManager.markCallAsRinging(call);
140c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
141c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(this, "setRinging, unknown call id: %s", msg.obj);
142c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    }
143c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
144c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_DIALING:
145c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
146c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (call != null) {
147c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        mCallsManager.markCallAsDialing(call);
148c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
149c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(this, "setDialing, unknown call id: %s", msg.obj);
1503d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon                    }
151c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
152c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_DISCONNECTED: {
153c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
154c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    try {
155c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
156c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        String disconnectMessage = (String) args.arg2;
157c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        int disconnectCause = args.argi1;
1583d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon                        if (call != null) {
159c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            mCallsManager.markCallAsDisconnected(call, disconnectCause,
160c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                    disconnectMessage);
1613d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon                        } else {
162c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            //Log.w(this, "setDisconnected, unknown call id: %s", args.arg1);
1633d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon                        }
164c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } finally {
165c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        args.recycle();
166352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton                    }
167c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
168c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
169c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_ON_HOLD:
170c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
171c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (call != null) {
172c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        mCallsManager.markCallAsOnHold(call);
173c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
174c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(this, "setOnHold, unknown call id: %s", msg.obj);
175a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    }
176c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
177c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_REQUESTING_RINGBACK: {
1789d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
1799d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    if (call != null) {
1809d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        call.setRequestingRingback(msg.arg1 == 1);
1819d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    } else {
1829d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        //Log.w(this, "setRingback, unknown call id: %s", args.arg1);
183a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    }
184c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
185c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
186e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                case MSG_SET_CALL_CAPABILITIES: {
187c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
188c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (call != null) {
189e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                        call.setCallCapabilities(msg.arg1);
190c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
191c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(ConnectionServiceWrapper.this,
192e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                        //      "setCallCapabilities, unknown call id: %s", msg.obj);
193c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    }
194c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
195c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
196c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_IS_CONFERENCED: {
197c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
198c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    try {
199c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        Call childCall = mCallIdMapper.getCall(args.arg1);
200c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        if (childCall != null) {
201c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            String conferenceCallId = (String) args.arg2;
202c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            if (conferenceCallId == null) {
203c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                childCall.setParentCall(null);
204c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            } else {
205c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                Call conferenceCall = mCallIdMapper.getCall(conferenceCallId);
206c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                if (conferenceCall != null &&
207c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                        !mPendingConferenceCalls.contains(conferenceCall)) {
208c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                    childCall.setParentCall(conferenceCall);
209a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                                } else {
210c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                    //Log.w(this, "setIsConferenced, unknown conference id %s",
211c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                                    //        conferenceCallId);
212a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                                }
213a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                            }
214c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        } else {
215c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            //Log.w(this, "setIsConferenced, unknown call id: %s", args.arg1);
216a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                        }
217c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } finally {
218c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        args.recycle();
219a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    }
220c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
221c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
222c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_ADD_CONFERENCE_CALL: {
223c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    Call conferenceCall = mCallIdMapper.getCall(msg.obj);
224c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    if (mPendingConferenceCalls.remove(conferenceCall)) {
225c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        Log.v(this, "confirming conf call %s", conferenceCall);
226c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        conferenceCall.confirmConference();
227c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } else {
228c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        //Log.w(this, "addConference, unknown call id: %s", callId);
229a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    }
230c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
231c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
232c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_REMOVE_CALL:
233c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
234c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_ON_POST_DIAL_WAIT: {
235c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
236c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    try {
237c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
238c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        if (call != null) {
239c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            String remaining = (String) args.arg2;
240c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            call.onPostDialWait(remaining);
241c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        } else {
242c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            //Log.w(this, "onPostDialWait, unknown call id: %s", args.arg1);
243c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        }
244c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } finally {
245c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        args.recycle();
246e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee                    }
247c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
248c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
249c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_QUERY_REMOTE_CALL_SERVICES: {
250664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                    queryRemoteConnectionServices((RemoteServiceCallback) msg.obj);
251c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
252c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
253c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                case MSG_SET_CALL_VIDEO_PROVIDER: {
254c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
255c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    try {
256c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
2573bcf935b25470e94c8c6855862434d15b785c54aAndrew Lee                        IVideoCallProvider videoCallProvider = (IVideoCallProvider) args.arg2;
258c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        if (call != null) {
2593bcf935b25470e94c8c6855862434d15b785c54aAndrew Lee                            call.setVideoCallProvider(videoCallProvider);
260e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee                        }
261c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    } finally {
262c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        args.recycle();
2635924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon                    }
264c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    break;
265c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
2667e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal                case MSG_SET_AUDIO_MODE_IS_VOIP: {
267e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                    call = mCallIdMapper.getCall(msg.obj);
268e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                    if (call != null) {
269e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                        call.setAudioModeIsVoip(msg.arg1 == 1);
2707e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal                    }
2717e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal                    break;
2727e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal                }
27335faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                case MSG_SET_STATUS_HINTS: {
27435faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
27535faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                    try {
27635faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
27735faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                        StatusHints statusHints = (StatusHints) args.arg2;
27835faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                        if (call != null) {
27935faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                            call.setStatusHints(statusHints);
28035faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                        }
28135faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                    } finally {
28235faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                        args.recycle();
28335faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                    }
28435faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                    break;
28535faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal                }
286e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                case MSG_SET_HANDLE: {
287e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
288e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    try {
289e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
290e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        if (call != null) {
291e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                            call.setHandle((Uri) args.arg2, args.argi1);
292e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        }
293e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    } finally {
294e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        args.recycle();
295e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    }
296e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    break;
297e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                }
298e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                case MSG_SET_CALLER_DISPLAY_NAME: {
299e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
300e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    try {
301e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
302e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        if (call != null) {
303e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                            call.setCallerDisplayName((String) args.arg2, args.argi1);
304e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        }
305e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    } finally {
306e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                        args.recycle();
307e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    }
308e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                    break;
309e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                }
3100a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                case MSG_SET_VIDEO_STATE: {
3110a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                    call = mCallIdMapper.getCall(msg.obj);
3120a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                    if (call != null) {
3130a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                        call.setVideoState(msg.arg1);
3140a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                    }
3157e0df31a6037c4d2d5c37a9c10e9b7a0d723382bTyler Gunn                    break;
3160a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn                }
3179d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                case MSG_START_ACTIVITY_FROM_IN_CALL: {
3189d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    SomeArgs args = (SomeArgs) msg.obj;
3199d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    try {
3209d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        call = mCallIdMapper.getCall(args.arg1);
3219d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        if (call != null) {
3229d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                            call.startActivityFromInCall((PendingIntent) args.arg2);
3239d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        }
3249d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    } finally {
3259d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                        args.recycle();
3269d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    }
3279d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    break;
3289d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                }
3293d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            }
330c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        }
331c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    };
332c195e3613af47a49e76821d3f24c05adb71cf920Santos Cordon
333c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private final class Adapter extends IConnectionServiceAdapter.Stub {
3343d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
33572890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon        public void handleCreateConnectionSuccessful(
33672890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon                ConnectionRequest request, ParcelableConnection connection) {
33772890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon
338664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            logIncoming("handleCreateConnectionSuccessful %s", request);
339c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            mCallIdMapper.checkValidCallId(request.getCallId());
34072890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon            SomeArgs args = SomeArgs.obtain();
34172890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon            args.arg1 = request;
34272890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon            args.arg2 = connection;
34372890ce844f92f45c56f3cccd1f2fd03ff12c3c2Santos Cordon            mHandler.obtainMessage(MSG_HANDLE_CREATE_CONNECTION_SUCCESSFUL, args).sendToTarget();
3443d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
3453d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
3463d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
347664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        public void handleCreateConnectionFailed(
348664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                ConnectionRequest request, int errorCode, String errorMsg) {
349664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            logIncoming("handleCreateConnectionFailed %s %d %s", request, errorCode, errorMsg);
350a3cb9e34db5952f0852c1a3230870cc6e378f246Ihab Awad            mCallIdMapper.checkValidCallId(request.getCallId());
3513d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            SomeArgs args = SomeArgs.obtain();
352c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            args.arg1 = request;
353a3cb9e34db5952f0852c1a3230870cc6e378f246Ihab Awad            args.argi1 = errorCode;
354a3cb9e34db5952f0852c1a3230870cc6e378f246Ihab Awad            args.arg2 = errorMsg;
355664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            mHandler.obtainMessage(MSG_HANDLE_CREATE_CONNECTION_FAILED, args).sendToTarget();
3563d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
3573d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
3583d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
359664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        public void handleCreateConnectionCancelled(ConnectionRequest request) {
360664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            logIncoming("handleCreateConnectionCancelled %s", request);
361c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            mCallIdMapper.checkValidCallId(request.getCallId());
362664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            mHandler.obtainMessage(MSG_HANDLE_CREATE_CONNECTION_CANCELLED, request).sendToTarget();
3635a73b03be0a2a929cf9974578445b90f773937b4Sailesh Nepal        }
3645a73b03be0a2a929cf9974578445b90f773937b4Sailesh Nepal
3655a73b03be0a2a929cf9974578445b90f773937b4Sailesh Nepal        @Override
3663d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        public void setActive(String callId) {
36755a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setActive %s", callId);
3683d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mCallIdMapper.checkValidCallId(callId);
3693d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mHandler.obtainMessage(MSG_SET_ACTIVE, callId).sendToTarget();
3703d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
3713d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
3723d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
3733d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        public void setRinging(String callId) {
37455a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setRinging %s", callId);
3753d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mCallIdMapper.checkValidCallId(callId);
3763d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mHandler.obtainMessage(MSG_SET_RINGING, callId).sendToTarget();
3773d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
3783d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
3793d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
3803bcf935b25470e94c8c6855862434d15b785c54aAndrew Lee        public void setVideoCallProvider(String callId, IVideoCallProvider videoCallProvider) {
3813bcf935b25470e94c8c6855862434d15b785c54aAndrew Lee            logIncoming("setVideoCallProvider %s", callId);
382e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee            mCallIdMapper.checkValidCallId(callId);
383e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee            SomeArgs args = SomeArgs.obtain();
384e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee            args.arg1 = callId;
3853bcf935b25470e94c8c6855862434d15b785c54aAndrew Lee            args.arg2 = videoCallProvider;
386e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee            mHandler.obtainMessage(MSG_SET_CALL_VIDEO_PROVIDER, args).sendToTarget();
387e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee        }
388e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee
389e9a776560dfe6f000cfc0dc1ea36c0f37d937f53Andrew Lee        @Override
3903d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        public void setDialing(String callId) {
39155a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setDialing %s", callId);
3923d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mCallIdMapper.checkValidCallId(callId);
3933d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mHandler.obtainMessage(MSG_SET_DIALING, callId).sendToTarget();
3943d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
3953d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
3963d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
3973d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        public void setDisconnected(
3983d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon                String callId, int disconnectCause, String disconnectMessage) {
39955a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setDisconnected %s %d %s", callId, disconnectCause, disconnectMessage);
4003d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mCallIdMapper.checkValidCallId(callId);
4013d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            SomeArgs args = SomeArgs.obtain();
4023d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            args.arg1 = callId;
4033d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            args.arg2 = disconnectMessage;
4043d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            args.argi1 = disconnectCause;
4053d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mHandler.obtainMessage(MSG_SET_DISCONNECTED, args).sendToTarget();
4063d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
4073d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
4083d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        @Override
4093d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        public void setOnHold(String callId) {
41055a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setOnHold %s", callId);
4113d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mCallIdMapper.checkValidCallId(callId);
4123d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            mHandler.obtainMessage(MSG_SET_ON_HOLD, callId).sendToTarget();
4133d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon        }
41450a57136b3aa876c8311b58e1e11720a337fe1ccIhab Awad
41550a57136b3aa876c8311b58e1e11720a337fe1ccIhab Awad        @Override
41650a57136b3aa876c8311b58e1e11720a337fe1ccIhab Awad        public void setRequestingRingback(String callId, boolean ringback) {
41755a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setRequestingRingback %s %b", callId, ringback);
41850a57136b3aa876c8311b58e1e11720a337fe1ccIhab Awad            mCallIdMapper.checkValidCallId(callId);
4199d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            mHandler.obtainMessage(MSG_SET_REQUESTING_RINGBACK, ringback ? 1 : 0, 0, callId)
4209d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal                    .sendToTarget();
42150a57136b3aa876c8311b58e1e11720a337fe1ccIhab Awad        }
4228f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon
4238f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        @Override
4248f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        public void removeCall(String callId) {
42555a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("removeCall %s", callId);
4268f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        }
4278f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon
4288f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        @Override
429e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal        public void setCallCapabilities(String callId, int callCapabilities) {
430e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal            logIncoming("setCallCapabilities %s %d", callId, callCapabilities);
431e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal            mHandler.obtainMessage(MSG_SET_CALL_CAPABILITIES, callCapabilities, 0, callId)
432a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    .sendToTarget();
4338f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        }
4348f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon
4358f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        @Override
436a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        public void setIsConferenced(String callId, String conferenceCallId) {
43755a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("setIsConferenced %s %s", callId, conferenceCallId);
438a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            SomeArgs args = SomeArgs.obtain();
439a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            args.arg1 = callId;
440a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            args.arg2 = conferenceCallId;
441a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            mHandler.obtainMessage(MSG_SET_IS_CONFERENCED, args).sendToTarget();
442a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        }
443a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon
444a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        @Override
445c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        public void addConferenceCall(String callId) {
446c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            logIncoming("addConferenceCall %s", callId);
447a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            mCallIdMapper.checkValidCallId(callId);
448c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            mHandler.obtainMessage(MSG_ADD_CONFERENCE_CALL, callId).sendToTarget();
4498f3282c49bd4e8e6de59be4bdaefc726d99a3273Santos Cordon        }
450352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton
451352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton        @Override
452352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton        public void onPostDialWait(String callId, String remaining) throws RemoteException {
45355a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad            logIncoming("onPostDialWait %s %s", callId, remaining);
454352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            mCallIdMapper.checkValidCallId(callId);
455352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            SomeArgs args = SomeArgs.obtain();
456352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            args.arg1 = callId;
457352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            args.arg2 = remaining;
458352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            mHandler.obtainMessage(MSG_ON_POST_DIAL_WAIT, args).sendToTarget();
459352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton        }
4606098d2c392f8698f8f4885da6edf6c5b8d7e4cb9Sailesh Nepal
4615924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon        @Override
4625924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon        public void queryRemoteConnectionServices(RemoteServiceCallback callback) {
4635924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon            logIncoming("queryRemoteCSs");
4645924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon            mHandler.obtainMessage(MSG_QUERY_REMOTE_CALL_SERVICES, callback).sendToTarget();
4655924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon        }
466e19cc005ddbff5313d6f7288587630b2410d005cTyler Gunn
467e19cc005ddbff5313d6f7288587630b2410d005cTyler Gunn        @Override
4680a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn        public void setVideoState(String callId, int videoState) {
4690a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn            logIncoming("setVideoState %s %d", callId, videoState);
4700a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn            mCallIdMapper.checkValidCallId(callId);
4710a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn            mHandler.obtainMessage(MSG_SET_VIDEO_STATE, videoState, 0, callId).sendToTarget();
4720a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn        }
4730a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn
4740a388fc566576513f54610c4427fb30feb88ab02Tyler Gunn        @Override
4757e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal        public void setAudioModeIsVoip(String callId, boolean isVoip) {
4767fa33cae6397f0952271a2d08c24d836b182dd41Sailesh Nepal            logIncoming("setAudioModeIsVoip %s %b", callId, isVoip);
4777e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal            mCallIdMapper.checkValidCallId(callId);
478e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal            mHandler.obtainMessage(MSG_SET_AUDIO_MODE_IS_VOIP, isVoip ? 1 : 0, 0,
479e20bc974ffc24d852d09e153a280b51e0329299cSailesh Nepal                    callId).sendToTarget();
4807e66957928c5c23a1028c8e2a2d7cf359cbfa44eSailesh Nepal        }
48135faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal
48235faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal        @Override
48335faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal        public void setStatusHints(String callId, StatusHints statusHints) {
48435faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            logIncoming("setStatusHints %s %s", callId, statusHints);
48535faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            mCallIdMapper.checkValidCallId(callId);
48635faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            SomeArgs args = SomeArgs.obtain();
48735faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            args.arg1 = callId;
48835faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            args.arg2 = statusHints;
48935faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal            mHandler.obtainMessage(MSG_SET_STATUS_HINTS, args).sendToTarget();
49035faf8cf29dc0f4a73935478e0fba957df9619d6Sailesh Nepal        }
491e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal
492e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        @Override
493e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        public void setHandle(String callId, Uri handle, int presentation) {
494e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            logIncoming("setHandle %s %s %d", callId, handle, presentation);
495e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            mCallIdMapper.checkValidCallId(callId);
496e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            SomeArgs args = SomeArgs.obtain();
497e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.arg1 = callId;
498e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.arg2 = handle;
499e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.argi1 = presentation;
500e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            mHandler.obtainMessage(MSG_SET_HANDLE, args).sendToTarget();
501e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        }
502e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal
503e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        @Override
504e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        public void setCallerDisplayName(
505e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                String callId, String callerDisplayName, int presentation) {
506e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            logIncoming("setCallerDisplayName %s %s %d", callId, callerDisplayName, presentation);
507e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            mCallIdMapper.checkValidCallId(callId);
508e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            SomeArgs args = SomeArgs.obtain();
509e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.arg1 = callId;
510e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.arg2 = callerDisplayName;
511e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            args.argi1 = presentation;
512e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            mHandler.obtainMessage(MSG_SET_CALLER_DISPLAY_NAME, args).sendToTarget();
513e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        }
5149d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal
5159d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal        @Override
5169d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal        public void startActivityFromInCall(String callId, PendingIntent intent) {
5179d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            logIncoming("startActivityFromInCall %s %s", callId, intent);
5189d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            mCallIdMapper.checkValidCallId(callId);
5199d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            SomeArgs args = SomeArgs.obtain();
5209d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            args.arg1 = callId;
5219d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            args.arg2 = intent;
5229d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal            mHandler.obtainMessage(MSG_START_ACTIVITY_FROM_IN_CALL, args).sendToTarget();
5239d58de5df05d0358fc8ae57ab7e9a0c45337c602Sailesh Nepal        }
5243d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    }
5253d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
5263d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    private final Adapter mAdapter = new Adapter();
5273d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    private final CallsManager mCallsManager = CallsManager.getInstance();
528a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    private final Set<Call> mPendingConferenceCalls = new HashSet<>();
529c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private final CallIdMapper mCallIdMapper = new CallIdMapper("ConnectionService");
530664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    private final Map<String, CreateConnectionResponse> mPendingResponses = new HashMap<>();
531c195e3613af47a49e76821d3f24c05adb71cf920Santos Cordon
5326192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad    private Binder mBinder = new Binder();
533c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private IConnectionService mServiceInterface;
534905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal    private final ConnectionServiceRepository mConnectionServiceRepository;
5356192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad
53663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon    /**
537905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal     * Creates a connection service.
538c195e3613af47a49e76821d3f24c05adb71cf920Santos Cordon     *
539905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal     * @param componentName The component name of the service with which to bind.
540905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal     * @param connectionServiceRepository Connection service repository.
541b78b27693afbe9736f0a54ec473328955251f885Ihab Awad     * @param phoneAccountRegistrar Phone account registrar
54263aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon     */
543c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    ConnectionServiceWrapper(
544b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            ComponentName componentName,
545b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            ConnectionServiceRepository connectionServiceRepository,
546b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            PhoneAccountRegistrar phoneAccountRegistrar) {
547f2f14efaf1ac2cd1e78d29b9d7213696746f1f17Santos Cordon        super(ConnectionService.SERVICE_INTERFACE, componentName);
548905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal        mConnectionServiceRepository = connectionServiceRepository;
549b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        phoneAccountRegistrar.addListener(new PhoneAccountRegistrar.Listener() {
550b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            // TODO -- Upon changes to PhoneAccountRegistrar, need to re-wire connections
551b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            // To do this, we must proxy remote ConnectionService objects
552b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        });
553c195e3613af47a49e76821d3f24c05adb71cf920Santos Cordon    }
554c195e3613af47a49e76821d3f24c05adb71cf920Santos Cordon
555c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** See {@link IConnectionService#addConnectionServiceAdapter}. */
556c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private void addConnectionServiceAdapter(IConnectionServiceAdapter adapter) {
557c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        if (isServiceValid("addConnectionServiceAdapter")) {
55861d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            try {
5593fe8b727b04cb677bc757f030c802cd4e6234db7Sailesh Nepal                logOutgoing("addConnectionServiceAdapter %s", adapter);
560c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                mServiceInterface.addConnectionServiceAdapter(adapter);
56161d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            } catch (RemoteException e) {
56263aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon            }
56363aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon        }
56463aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon    }
56563aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon
5666192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad    /**
567664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal     * Creates a new connection for a new outgoing call or to attach to an existing incoming call.
5686192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad     */
569664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal    void createConnection(final Call call, final CreateConnectionResponse response) {
570664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        Log.d(this, "createConnection(%s) via %s.", call, getComponentName());
5716192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad        BindCallback callback = new BindCallback() {
5723d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            @Override
5733d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            public void onSuccess() {
574682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon                String callId = mCallIdMapper.getCallId(call);
575664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                mPendingResponses.put(callId, response);
576682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon
577c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                GatewayInfo gatewayInfo = call.getGatewayInfo();
578c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                Bundle extras = call.getExtras();
579c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                if (gatewayInfo != null && gatewayInfo.getGatewayProviderPackageName() != null &&
580c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                        gatewayInfo.getOriginalHandle() != null) {
581c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    extras = (Bundle) extras.clone();
582c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    extras.putString(
583c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            NewOutgoingCallIntentBroadcaster.EXTRA_GATEWAY_PROVIDER_PACKAGE,
584c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            gatewayInfo.getGatewayProviderPackageName());
585c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                    extras.putParcelable(
586c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            NewOutgoingCallIntentBroadcaster.EXTRA_GATEWAY_ORIGINAL_URI,
587c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                            gatewayInfo.getOriginalHandle());
588c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                }
589c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal
590682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon                try {
591b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    mServiceInterface.createConnection(
592b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                            call.getConnectionManagerPhoneAccount(),
593b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                            new ConnectionRequest(
594b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    call.getTargetPhoneAccount(),
595b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    callId,
596b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    call.getHandle(),
597b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    call.getHandlePresentation(),
598b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    extras,
599b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                                    call.getVideoState()),
600b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                            call.isIncoming());
601682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon                } catch (RemoteException e) {
602664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                    Log.e(this, e, "Failure to createConnection -- %s", getComponentName());
603664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                    mPendingResponses.remove(callId).handleCreateConnectionFailed(
604fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                            DisconnectCause.OUTGOING_FAILURE, e.toString());
6056192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad                }
60663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon            }
6073d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
6083d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            @Override
6093d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon            public void onFailure() {
610905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal                Log.e(this, new Exception(), "Failure to call %s", getComponentName());
611fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon                response.handleCreateConnectionFailed(DisconnectCause.OUTGOING_FAILURE, null);
6126192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad            }
6136192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad        };
6146192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad
6156192561b1f56d7c4e6c650e178e07ba61ad02667Ben Gilad        mBinder.bind(callback);
61663aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon    }
61763aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon
618c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#abort(String) */
619e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void abort(Call call) {
620682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon        // Clear out any pending outgoing call data
621682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon        String callId = mCallIdMapper.getCallId(call);
622682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon
623c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        // If still bound, tell the connection service to abort.
62428e8ad601cbef0abab1cd6aec8c5a3bc881839c2Ben Gilad        if (isServiceValid("abort")) {
62528e8ad601cbef0abab1cd6aec8c5a3bc881839c2Ben Gilad            try {
62655a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("abort %s", callId);
627682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon                mServiceInterface.abort(callId);
62828e8ad601cbef0abab1cd6aec8c5a3bc881839c2Ben Gilad            } catch (RemoteException e) {
62961d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            }
63061d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon        }
631682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon
632fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon        removeCall(call, DisconnectCause.LOCAL, null);
63361d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon    }
63461d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon
635c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#hold(String) */
636e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void hold(Call call) {
637cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee        if (isServiceValid("hold")) {
638cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            try {
63955a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("hold %s", mCallIdMapper.getCallId(call));
640e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.hold(mCallIdMapper.getCallId(call));
641cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            } catch (RemoteException e) {
642cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            }
643cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee        }
644cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee    }
645cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee
646c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#unhold(String) */
647e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void unhold(Call call) {
648cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee        if (isServiceValid("unhold")) {
649cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            try {
65055a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("unhold %s", mCallIdMapper.getCallId(call));
651e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.unhold(mCallIdMapper.getCallId(call));
652cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            } catch (RemoteException e) {
653cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee            }
654cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee        }
655cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee    }
656cdf3ebd3ea6505668304b7e0a39df354ebbb52fbYorke Lee
657c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#onAudioStateChanged(String,CallAudioState) */
658e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void onAudioStateChanged(Call activeCall, CallAudioState audioState) {
6596aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal        if (isServiceValid("onAudioStateChanged")) {
6606aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal            try {
66155a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("onAudioStateChanged %s %s",
66255a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                        mCallIdMapper.getCallId(activeCall), audioState);
663e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.onAudioStateChanged(mCallIdMapper.getCallId(activeCall),
664e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                        audioState);
6656aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal            } catch (RemoteException e) {
6666aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal            }
6676aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal        }
6686aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal    }
6696aca10a0efa2771ccdef5920f4276f0db4a7ee1fSailesh Nepal
670c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#disconnect(String) */
671e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void disconnect(Call call) {
67261d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon        if (isServiceValid("disconnect")) {
67361d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            try {
67455a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("disconnect %s", mCallIdMapper.getCallId(call));
675e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.disconnect(mCallIdMapper.getCallId(call));
67661d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            } catch (RemoteException e) {
67761d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            }
67861d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon        }
67961d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon    }
68061d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon
681b78b27693afbe9736f0a54ec473328955251f885Ihab Awad    /** @see ConnectionService#answer(String,int) */
68238931d0ad60f00a9f50c90cef446166731f0b871Andrew Lee    void answer(Call call, int videoState) {
68361d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon        if (isServiceValid("answer")) {
68461d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            try {
68538931d0ad60f00a9f50c90cef446166731f0b871Andrew Lee                logOutgoing("answer %s %d", mCallIdMapper.getCallId(call), videoState);
68638931d0ad60f00a9f50c90cef446166731f0b871Andrew Lee                mServiceInterface.answer(mCallIdMapper.getCallId(call), videoState);
68761d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            } catch (RemoteException e) {
68863aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon            }
68963aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon        }
69063aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon    }
6915c12c6e00101d16d2db776839a027c62c109dea8Santos Cordon
692c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#reject(String) */
693e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void reject(Call call) {
69461d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon        if (isServiceValid("reject")) {
69561d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            try {
69655a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("reject %s", mCallIdMapper.getCallId(call));
697e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.reject(mCallIdMapper.getCallId(call));
69861d0f70cf45036f9cdeb41b96538f792b7c9764bSantos Cordon            } catch (RemoteException e) {
69974549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            }
70074549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad        }
70174549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad    }
70274549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad
703c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#playDtmfTone(String,char) */
704e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void playDtmfTone(Call call, char digit) {
70574549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad        if (isServiceValid("playDtmfTone")) {
70674549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            try {
70755a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("playDtmfTone %s %c", mCallIdMapper.getCallId(call), digit);
708e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.playDtmfTone(mCallIdMapper.getCallId(call), digit);
70974549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            } catch (RemoteException e) {
71074549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            }
71174549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad        }
71274549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad    }
71374549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad
714c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    /** @see ConnectionService#stopDtmfTone(String) */
715e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void stopDtmfTone(Call call) {
71674549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad        if (isServiceValid("stopDtmfTone")) {
71774549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            try {
71855a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("stopDtmfTone %s", mCallIdMapper.getCallId(call));
719e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal                mServiceInterface.stopDtmfTone(mCallIdMapper.getCallId(call));
72074549ec95acf0d2ddbe4feca91c6febdf8008074Ihab Awad            } catch (RemoteException e) {
7217917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon            }
7227917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon        }
7237917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon    }
7247917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon
725e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void addCall(Call call) {
726a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        if (mCallIdMapper.getCallId(call) == null) {
727a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            mCallIdMapper.addCall(call);
728a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        }
7297917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon    }
7307917d38176b6cc432314433d36d7bb46a09f5afcSantos Cordon
7310e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal    /**
732c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal     * Associates newCall with this connection service by replacing callToReplace.
7330e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal     */
7340e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal    void replaceCall(Call newCall, Call callToReplace) {
735c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        Preconditions.checkState(callToReplace.getConnectionService() == this);
7360e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal        mCallIdMapper.replaceCall(newCall, callToReplace);
7370e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal    }
7380e5410a58043ce059884fdc8811a280655e5a920Sailesh Nepal
739e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal    void removeCall(Call call) {
740fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon        removeCall(call, DisconnectCause.ERROR_UNSPECIFIED, null);
741fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon    }
742fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon
743fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon    void removeCall(Call call, int disconnectCause, String disconnectMessage) {
744664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        CreateConnectionResponse response = mPendingResponses.remove(mCallIdMapper.getCallId(call));
745664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        if (response != null) {
746fd6ca447a45c47aeb3956964103770475c655a26Santos Cordon            response.handleCreateConnectionFailed(disconnectCause, disconnectMessage);
747682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon        }
748682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon
749e59bb195972d65a71618af4fe13f1ad982253e16Sailesh Nepal        mCallIdMapper.removeCall(call);
750adee12dd6b3e85ce3ae419329226c9aa72c184fcYorke Lee    }
751adee12dd6b3e85ce3ae419329226c9aa72c184fcYorke Lee
752352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton    void onPostDialContinue(Call call, boolean proceed) {
753352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton        if (isServiceValid("onPostDialContinue")) {
754352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            try {
75555a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("onPostDialContinue %s %b", mCallIdMapper.getCallId(call), proceed);
756352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton                mServiceInterface.onPostDialContinue(mCallIdMapper.getCallId(call), proceed);
757352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            } catch (RemoteException ignored) {
758352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton            }
759352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton        }
760352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton    }
761352105c5d33ac94e5ad0cb5ac2e9268731423e65Evan Charlton
76277da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal    void onPhoneAccountClicked(Call call) {
76377da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal        if (isServiceValid("onPhoneAccountClicked")) {
76477da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal            try {
76577da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal                logOutgoing("onPhoneAccountClicked %s", mCallIdMapper.getCallId(call));
76677da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal                mServiceInterface.onPhoneAccountClicked(mCallIdMapper.getCallId(call));
76777da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal            } catch (RemoteException ignored) {
76877da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal            }
76977da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal        }
77077da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal    }
77177da19ea28b8753d439660b4352c1bf914f63a92Sailesh Nepal
772a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    void conference(final Call conferenceCall, Call call) {
773a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        if (isServiceValid("conference")) {
774a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            try {
775c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal                conferenceCall.setConnectionService(this);
776a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                mPendingConferenceCalls.add(conferenceCall);
777a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                mHandler.postDelayed(new Runnable() {
778a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    @Override public void run() {
779a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                        if (mPendingConferenceCalls.remove(conferenceCall)) {
780a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                            conferenceCall.expireConference();
781a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                            Log.i(this, "Conference call expired: %s", conferenceCall);
782a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                        }
783a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                    }
784a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                }, Timeouts.getConferenceCallExpireMillis());
785a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon
78655a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("conference %s %s",
78755a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                        mCallIdMapper.getCallId(conferenceCall),
78855a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                        mCallIdMapper.getCallId(call));
789a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                mServiceInterface.conference(
790a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                        mCallIdMapper.getCallId(conferenceCall),
791a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                        mCallIdMapper.getCallId(call));
792a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            } catch (RemoteException ignored) {
793a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            }
794a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        }
795a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    }
796a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon
797a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    void splitFromConference(Call call) {
798a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        if (isServiceValid("splitFromConference")) {
799a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            try {
80055a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad                logOutgoing("splitFromConference %s", mCallIdMapper.getCallId(call));
801a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon                mServiceInterface.splitFromConference(mCallIdMapper.getCallId(call));
802a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            } catch (RemoteException ignored) {
803a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon            }
804a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        }
805a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    }
806a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon
807e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal    void swapWithBackgroundCall(Call call) {
808e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        if (isServiceValid("swapWithBackgroundCall")) {
809e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            try {
810e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                logOutgoing("swapWithBackgroundCall %s", mCallIdMapper.getCallId(call));
811e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal                mServiceInterface.swapWithBackgroundCall(mCallIdMapper.getCallId(call));
812e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            } catch (RemoteException ignored) {
813e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal            }
814e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal        }
815e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal    }
816e8ecb98d5341395e073d02c065143ae3ac76ef71Sailesh Nepal
8175c12c6e00101d16d2db776839a027c62c109dea8Santos Cordon    /** {@inheritDoc} */
8183d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    @Override
8193d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    protected void setServiceInterface(IBinder binder) {
8204b2c119562bf29b05c7dc139c77f5893d3d70d2cSantos Cordon        if (binder == null) {
821c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            // We have lost our service connection. Notify the world that this service is done.
8224b2c119562bf29b05c7dc139c77f5893d3d70d2cSantos Cordon            // We must notify the adapter before CallsManager. The adapter will force any pending
823c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            // outgoing calls to try the next service. This needs to happen before CallsManager
824c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            // tries to clean up any calls still associated with this service.
825c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            handleConnectionServiceDeath();
826c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            CallsManager.getInstance().handleConnectionServiceDeath(this);
8274b2c119562bf29b05c7dc139c77f5893d3d70d2cSantos Cordon            mServiceInterface = null;
8284b2c119562bf29b05c7dc139c77f5893d3d70d2cSantos Cordon        } else {
829c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            mServiceInterface = IConnectionService.Stub.asInterface(binder);
830c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal            addConnectionServiceAdapter(mAdapter);
8314b2c119562bf29b05c7dc139c77f5893d3d70d2cSantos Cordon        }
8325c12c6e00101d16d2db776839a027c62c109dea8Santos Cordon    }
8333d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon
8343d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon    /**
835c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal     * Called when the associated connection service dies.
8363d3b4059d7b1fc5a03c4b049b1d436f28ecf84ecSantos Cordon     */
837c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal    private void handleConnectionServiceDeath() {
838664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal        if (!mPendingResponses.isEmpty()) {
839664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            CreateConnectionResponse[] responses = mPendingResponses.values().toArray(
840664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                    new CreateConnectionResponse[mPendingResponses.values().size()]);
841664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            mPendingResponses.clear();
842664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal            for (int i = 0; i < responses.length; i++) {
843664837f9a8a98f98876417a0bfff64834e8032faSailesh Nepal                responses[i].handleCreateConnectionFailed(DisconnectCause.ERROR_UNSPECIFIED, null);
844682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon            }
845682fe6ba2fe99e209d72a051539697a755b994c0Santos Cordon        }
846a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon        mCallIdMapper.clear();
847a161070ea054f91a5b2d5b4e3413381134d548b8Santos Cordon    }
84855a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad
84955a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad    private void logIncoming(String msg, Object... params) {
850c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        Log.d(this, "ConnectionService -> Telecomm: " + msg, params);
85155a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad    }
85255a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad
85355a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad    private void logOutgoing(String msg, Object... params) {
854c92c436d84de46bb85100df9138378d9ffe0f2f2Sailesh Nepal        Log.d(this, "Telecomm -> ConnectionService: " + msg, params);
85555a3428c6b62e5a84d21f890418cfa9a8494780eIhab Awad    }
8565924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon
8575924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon    private void queryRemoteConnectionServices(final RemoteServiceCallback callback) {
858b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        PhoneAccountRegistrar registrar = TelecommApp.getInstance().getPhoneAccountRegistrar();
859b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
860b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        // Only give remote connection services to this connection service if it is listed as
861b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        // the connection manager.
862b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        PhoneAccountHandle simCallManager = registrar.getSimCallManager();
863b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        if (simCallManager == null ||
864b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                !simCallManager.getComponentName().equals(getComponentName())) {
865b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            noRemoteServices(callback);
866b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            return;
867b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        }
868b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
869b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        // Make a list of ConnectionServices that are listed as being associated with SIM accounts
870b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        final Set<ConnectionServiceWrapper> simServices = new HashSet<>();
871b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        for (PhoneAccountHandle handle : registrar.getEnabledPhoneAccounts()) {
872b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            PhoneAccount account = registrar.getPhoneAccount(handle);
873b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            if ((account.getCapabilities() & PhoneAccount.CAPABILITY_SIM_SUBSCRIPTION) != 0) {
874b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                ConnectionServiceWrapper service =
875b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                        mConnectionServiceRepository.getService(handle.getComponentName());
876b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                if (service != null) {
877b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    simServices.add(service);
878b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                }
879b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            }
880b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        }
8815924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon
882b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        final List<ComponentName> simServiceComponentNames = new ArrayList<>();
883b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        final List<IBinder> simServiceBinders = new ArrayList<>();
8845924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon
885b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        Log.v(this, "queryRemoteConnectionServices, simServices = %s", simServices);
886b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
887b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        for (ConnectionServiceWrapper simService : simServices) {
888b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            if (simService == this) {
889b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                // Only happens in the unlikely case that a SIM service is also a SIM call manager
890b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                continue;
8915924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon            }
892b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
893b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            final ConnectionServiceWrapper currentSimService = simService;
894b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
895b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            currentSimService.mBinder.bind(new BindCallback() {
896b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                @Override
897b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                public void onSuccess() {
898b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    Log.d(this, "Adding simService %s", currentSimService.getComponentName());
899b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    simServiceComponentNames.add(currentSimService.getComponentName());
900b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    simServiceBinders.add(currentSimService.mServiceInterface.asBinder());
901b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    maybeComplete();
902b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                }
903b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
904b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                @Override
905b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                public void onFailure() {
906b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    Log.d(this, "Failed simService %s", currentSimService.getComponentName());
907b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    // We know maybeComplete() will always be a no-op from now on, so go ahead and
908b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    // signal failure of the entire request
909b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    noRemoteServices(callback);
910b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                }
911b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
912b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                private void maybeComplete() {
913b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    if (simServiceComponentNames.size() == simServices.size()) {
914b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                        setRemoteServices(callback, simServiceComponentNames, simServiceBinders);
915b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    }
916b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                }
917b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            });
918b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        }
919b78b27693afbe9736f0a54ec473328955251f885Ihab Awad    }
920b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
921b78b27693afbe9736f0a54ec473328955251f885Ihab Awad    private void setRemoteServices(
922b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            RemoteServiceCallback callback,
923b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            List<ComponentName> componentNames,
924b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            List<IBinder> binders) {
925b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        try {
926b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            callback.onResult(componentNames, binders);
927b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        } catch (RemoteException e) {
928b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            Log.e(this, e, "Contacting ConnectionService %s",
929b78b27693afbe9736f0a54ec473328955251f885Ihab Awad                    ConnectionServiceWrapper.this.getComponentName());
930b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        }
931b78b27693afbe9736f0a54ec473328955251f885Ihab Awad    }
932b78b27693afbe9736f0a54ec473328955251f885Ihab Awad
933b78b27693afbe9736f0a54ec473328955251f885Ihab Awad    private void noRemoteServices(RemoteServiceCallback callback) {
934b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        try {
935b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            callback.onResult(Collections.EMPTY_LIST, Collections.EMPTY_LIST);
936b78b27693afbe9736f0a54ec473328955251f885Ihab Awad        } catch (RemoteException e) {
937b78b27693afbe9736f0a54ec473328955251f885Ihab Awad            Log.e(this, e, "Contacting ConnectionService %s", this.getComponentName());
938905dfba7883666f45a0c6958d8bc6c19d68972d9Sailesh Nepal        }
9395924beafe09bf3fb710ec1bafd59113a12b45adaSantos Cordon    }
94063aeb16a14a94dd44345f6200c7c002e780a15ffSantos Cordon}
941