• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2022 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.server.telecom.voip;
18 
19 import static android.Manifest.permission.CALL_PRIVILEGED;
20 import static android.telecom.CallAttributes.CALL_CAPABILITIES_KEY;
21 import static android.telecom.CallAttributes.DISPLAY_NAME_KEY;
22 import static android.telecom.CallException.CODE_CALL_NOT_PERMITTED_AT_PRESENT_TIME;
23 
24 import android.content.Context;
25 import android.content.Intent;
26 import android.content.pm.PackageManager;
27 import android.os.Bundle;
28 import android.telecom.CallAttributes;
29 import android.telecom.TelecomManager;
30 import android.util.Log;
31 
32 import com.android.server.telecom.Call;
33 import com.android.server.telecom.CallsManager;
34 import com.android.server.telecom.LoggedHandlerExecutor;
35 
36 import java.util.concurrent.CompletableFuture;
37 import java.util.concurrent.CompletionStage;
38 
39 public class OutgoingCallTransaction extends VoipCallTransaction {
40 
41     private static final String TAG = OutgoingCallTransaction.class.getSimpleName();
42     private final String mCallId;
43     private final Context mContext;
44     private final String mCallingPackage;
45     private final CallAttributes mCallAttributes;
46     private final CallsManager mCallsManager;
47     private final Bundle mExtras;
48 
OutgoingCallTransaction(String callId, Context context, CallAttributes callAttributes, CallsManager callsManager, Bundle extras)49     public OutgoingCallTransaction(String callId, Context context, CallAttributes callAttributes,
50             CallsManager callsManager, Bundle extras) {
51         super(callsManager.getLock());
52         mCallId = callId;
53         mContext = context;
54         mCallAttributes = callAttributes;
55         mCallsManager = callsManager;
56         mExtras = extras;
57         mCallingPackage = mContext.getOpPackageName();
58     }
59 
OutgoingCallTransaction(String callId, Context context, CallAttributes callAttributes, CallsManager callsManager)60     public OutgoingCallTransaction(String callId, Context context, CallAttributes callAttributes,
61             CallsManager callsManager) {
62         this(callId, context, callAttributes, callsManager, new Bundle());
63     }
64 
65     @Override
processTransaction(Void v)66     public CompletionStage<VoipCallTransactionResult> processTransaction(Void v) {
67         Log.d(TAG, "processTransaction");
68 
69         final boolean hasCallPrivilegedPermission = mContext.checkCallingPermission(
70                 CALL_PRIVILEGED) == PackageManager.PERMISSION_GRANTED;
71 
72         final Intent intent = new Intent(hasCallPrivilegedPermission ?
73                 Intent.ACTION_CALL_PRIVILEGED : Intent.ACTION_CALL, mCallAttributes.getAddress());
74 
75         if (mCallsManager.isOutgoingCallPermitted(mCallAttributes.getPhoneAccountHandle())) {
76             Log.d(TAG, "processTransaction: outgoing call permitted");
77 
78             CompletableFuture<Call> callFuture =
79                     mCallsManager.startOutgoingCall(mCallAttributes.getAddress(),
80                             mCallAttributes.getPhoneAccountHandle(),
81                             generateExtras(mCallAttributes),
82                             mCallAttributes.getPhoneAccountHandle().getUserHandle(),
83                             intent,
84                             mCallingPackage);
85 
86             if (callFuture == null) {
87                 return CompletableFuture.completedFuture(
88                         new VoipCallTransactionResult(
89                                 CODE_CALL_NOT_PERMITTED_AT_PRESENT_TIME,
90                                 "incoming call not permitted at the current time"));
91             }
92             CompletionStage<VoipCallTransactionResult> result = callFuture.thenComposeAsync(
93                     (call) -> {
94 
95                         Log.d(TAG, "processTransaction: completing future");
96 
97                         if (call == null) {
98                             Log.d(TAG, "processTransaction: call is null");
99                             return CompletableFuture.completedFuture(
100                                     new VoipCallTransactionResult(
101                                             CODE_CALL_NOT_PERMITTED_AT_PRESENT_TIME,
102                                             "call could not be created at this time"));
103                         } else {
104                             Log.d(TAG, "processTransaction: call done. id=" + call.getId());
105                         }
106 
107                         return CompletableFuture.completedFuture(
108                                 new VoipCallTransactionResult(
109                                         VoipCallTransactionResult.RESULT_SUCCEED,
110                                         call, null));
111                     }
112                     , new LoggedHandlerExecutor(mHandler, "OCT.pT", null));
113 
114             return result;
115         } else {
116             return CompletableFuture.completedFuture(
117                     new VoipCallTransactionResult(
118                             CODE_CALL_NOT_PERMITTED_AT_PRESENT_TIME,
119                             "incoming call not permitted at the current time"));
120 
121         }
122     }
123 
generateExtras(CallAttributes callAttributes)124     private Bundle generateExtras(CallAttributes callAttributes) {
125         mExtras.setDefusable(true);
126         mExtras.putString(TelecomManager.TRANSACTION_CALL_ID_KEY, mCallId);
127         mExtras.putInt(CALL_CAPABILITIES_KEY, callAttributes.getCallCapabilities());
128         mExtras.putInt(TelecomManager.EXTRA_START_CALL_WITH_VIDEO_STATE,
129                 callAttributes.getCallType());
130         mExtras.putCharSequence(DISPLAY_NAME_KEY, callAttributes.getDisplayName());
131         return mExtras;
132     }
133 }
134