• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 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.components;
18 
19 import android.app.Service;
20 import android.app.role.RoleManager;
21 import android.content.Context;
22 import android.content.Intent;
23 import android.media.IAudioService;
24 import android.media.ToneGenerator;
25 import android.os.IBinder;
26 import android.os.PowerManager;
27 import android.os.ServiceManager;
28 import android.os.SystemClock;
29 import android.provider.BlockedNumberContract;
30 import android.telecom.Log;
31 
32 import android.telecom.CallerInfoAsyncQuery;
33 import android.view.accessibility.AccessibilityManager;
34 
35 import com.android.internal.telecom.IInternalServiceRetriever;
36 import com.android.internal.telecom.ITelecomLoader;
37 import com.android.internal.telecom.ITelecomService;
38 import com.android.server.telecom.AsyncRingtonePlayer;
39 import com.android.server.telecom.CallAudioModeStateMachine;
40 import com.android.server.telecom.CallAudioRouteStateMachine;
41 import com.android.server.telecom.CallerInfoAsyncQueryFactory;
42 import com.android.server.telecom.CallsManager;
43 import com.android.server.telecom.ClockProxy;
44 import com.android.server.telecom.ConnectionServiceFocusManager;
45 import com.android.server.telecom.ContactsAsyncHelper;
46 import com.android.server.telecom.DefaultDialerCache;
47 import com.android.server.telecom.DeviceIdleControllerAdapter;
48 import com.android.server.telecom.HeadsetMediaButton;
49 import com.android.server.telecom.HeadsetMediaButtonFactory;
50 import com.android.server.telecom.InCallWakeLockControllerFactory;
51 import com.android.server.telecom.CallAudioManager;
52 import com.android.server.telecom.InternalServiceRetrieverAdapter;
53 import com.android.server.telecom.PhoneAccountRegistrar;
54 import com.android.server.telecom.PhoneNumberUtilsAdapterImpl;
55 import com.android.server.telecom.ProximitySensorManagerFactory;
56 import com.android.server.telecom.InCallWakeLockController;
57 import com.android.server.telecom.ProximitySensorManager;
58 import com.android.server.telecom.Ringer;
59 import com.android.server.telecom.RoleManagerAdapterImpl;
60 import com.android.server.telecom.TelecomSystem;
61 import com.android.server.telecom.TelecomWakeLock;
62 import com.android.server.telecom.Timeouts;
63 import com.android.server.telecom.callfiltering.BlockedNumbersAdapter;
64 import com.android.server.telecom.settings.BlockedNumbersUtil;
65 import com.android.server.telecom.ui.IncomingCallNotifier;
66 import com.android.server.telecom.ui.MissedCallNotifierImpl;
67 import com.android.server.telecom.ui.NotificationChannelManager;
68 
69 import java.util.concurrent.Executors;
70 
71 /**
72  * Implementation of the ITelecom interface.
73  */
74 public class TelecomService extends Service implements TelecomSystem.Component {
75 
76     @Override
onBind(Intent intent)77     public IBinder onBind(Intent intent) {
78         Log.d(this, "onBind");
79         return new ITelecomLoader.Stub() {
80             @Override
81             public ITelecomService createTelecomService(IInternalServiceRetriever retriever) {
82                 InternalServiceRetrieverAdapter adapter =
83                         new InternalServiceRetrieverAdapter(retriever);
84                 initializeTelecomSystem(TelecomService.this, adapter);
85                 synchronized (getTelecomSystem().getLock()) {
86                     return getTelecomSystem().getTelecomServiceImpl().getBinder();
87                 }
88             }
89         };
90     }
91 
92     /**
93      * This method is to be called by components (Activitys, Services, ...) to initialize the
94      * Telecom singleton. It should only be called on the main thread. As such, it is atomic
95      * and needs no synchronization -- it will either perform its initialization, after which
96      * the {@link TelecomSystem#getInstance()} will be initialized, or some other invocation of
97      * this method on the main thread will have happened strictly prior to it, and this method
98      * will be a benign no-op.
99      *
100      * @param context
101      */
102     static void initializeTelecomSystem(Context context,
103             InternalServiceRetrieverAdapter internalServiceRetriever) {
104         if (TelecomSystem.getInstance() == null) {
105             NotificationChannelManager notificationChannelManager =
106                     new NotificationChannelManager();
107             notificationChannelManager.createChannels(context);
108 
109             TelecomSystem.setInstance(
110                     new TelecomSystem(
111                             context,
112                             new MissedCallNotifierImpl.MissedCallNotifierImplFactory() {
113                                 @Override
114                                 public MissedCallNotifierImpl makeMissedCallNotifierImpl(
115                                         Context context,
116                                         PhoneAccountRegistrar phoneAccountRegistrar,
117                                         DefaultDialerCache defaultDialerCache,
118                                         DeviceIdleControllerAdapter idleControllerAdapter) {
119                                     return new MissedCallNotifierImpl(context,
120                                             phoneAccountRegistrar, defaultDialerCache,
121                                             idleControllerAdapter);
122                                 }
123                             },
124                             new CallerInfoAsyncQueryFactory() {
125                                 @Override
126                                 public CallerInfoAsyncQuery startQuery(
127                                         int token,
128                                         Context context,
129                                         String number,
130                                         CallerInfoAsyncQuery.OnQueryCompleteListener listener,
131                                         Object cookie) {
132                                     Log.i(TelecomSystem.getInstance(),
133                                             "CallerInfoAsyncQuery.startQuery number=%s cookie=%s",
134                                             Log.pii(number), cookie);
135                                     return CallerInfoAsyncQuery.startQuery(
136                                             token, context, number, listener, cookie);
137                                 }
138                             },
139                             new HeadsetMediaButtonFactory() {
140                                 @Override
141                                 public HeadsetMediaButton create(
142                                         Context context,
143                                         CallsManager callsManager,
144                                         TelecomSystem.SyncRoot lock) {
145                                     return new HeadsetMediaButton(context, callsManager, lock);
146                                 }
147                             },
148                             new ProximitySensorManagerFactory() {
149                                 @Override
150                                 public ProximitySensorManager create(
151                                         Context context,
152                                         CallsManager callsManager) {
153                                     return new ProximitySensorManager(
154                                             new TelecomWakeLock(
155                                                     context,
156                                                     PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK,
157                                                     ProximitySensorManager.class.getSimpleName()),
158                                             callsManager);
159                                 }
160                             },
161                             new InCallWakeLockControllerFactory() {
162                                 @Override
163                                 public InCallWakeLockController create(Context context,
164                                         CallsManager callsManager) {
165                                     return new InCallWakeLockController(
166                                             new TelecomWakeLock(context,
167                                                     PowerManager.FULL_WAKE_LOCK,
168                                                     InCallWakeLockController.class.getSimpleName()),
169                                             callsManager);
170                                 }
171                             },
172                             new CallAudioManager.AudioServiceFactory() {
173                                 @Override
174                                 public IAudioService getAudioService() {
175                                     return IAudioService.Stub.asInterface(
176                                             ServiceManager.getService(Context.AUDIO_SERVICE));
177                                 }
178                             },
179                             ConnectionServiceFocusManager::new,
180                             new Timeouts.Adapter(),
181                             new AsyncRingtonePlayer(),
182                             new PhoneNumberUtilsAdapterImpl(),
183                             new IncomingCallNotifier(context),
184                             ToneGenerator::new,
185                             new CallAudioRouteStateMachine.Factory(),
186                             new CallAudioModeStateMachine.Factory(),
187                             new ClockProxy() {
188                                 @Override
189                                 public long currentTimeMillis() {
190                                     return System.currentTimeMillis();
191                                 }
192 
193                                 @Override
194                                 public long elapsedRealtime() {
195                                     return SystemClock.elapsedRealtime();
196                                 }
197                             },
198                             new RoleManagerAdapterImpl(context,
199                                     (RoleManager) context.getSystemService(Context.ROLE_SERVICE)),
200                             new ContactsAsyncHelper.Factory(),
201                             internalServiceRetriever.getDeviceIdleController(),
202                             new Ringer.AccessibilityManagerAdapter() {
203                                 @Override
204                                 public boolean startFlashNotificationSequence(
205                                         @androidx.annotation.NonNull Context context, int reason) {
206                                     return context.getSystemService(AccessibilityManager.class)
207                                             .startFlashNotificationSequence(context, reason);
208                                 }
209 
210                                 @Override
211                                 public boolean stopFlashNotificationSequence(
212                                         @androidx.annotation.NonNull Context context) {
213                                     return context.getSystemService(AccessibilityManager.class)
214                                             .stopFlashNotificationSequence(context);
215                                 }
216                             },
217                             Executors.newCachedThreadPool(),
218                             Executors.newSingleThreadExecutor(),
219                             new BlockedNumbersAdapter() {
220                                 @Override
221                                 public boolean shouldShowEmergencyCallNotification(Context
222                                         context) {
223                                     return BlockedNumberContract.SystemContract
224                                             .shouldShowEmergencyCallNotification(context);
225                                 }
226 
227                                 @Override
228                                 public void updateEmergencyCallNotification(Context context,
229                                         boolean showNotification) {
230                                     BlockedNumbersUtil.updateEmergencyCallNotification(context,
231                                             showNotification);
232                                 }
233                             }));
234         }
235     }
236 
237     @Override
238     public TelecomSystem getTelecomSystem() {
239         return TelecomSystem.getInstance();
240     }
241 }
242