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;
18 
19 import android.content.ContentResolver;
20 import android.provider.Settings;
21 import android.telecom.CallRedirectionService;
22 import java.util.concurrent.TimeUnit;
23 
24 /**
25  * A helper class which serves only to make it easier to lookup timeout values. This class should
26  * never be instantiated, and only accessed through the {@link #get(String, long)} method.
27  *
28  * These methods are safe to call from any thread, including the UI thread.
29  */
30 public final class Timeouts {
31     public static class Adapter {
Adapter()32         public Adapter() {
33         }
34 
getCallScreeningTimeoutMillis(ContentResolver cr)35         public long getCallScreeningTimeoutMillis(ContentResolver cr) {
36             return Timeouts.getCallScreeningTimeoutMillis(cr);
37         }
38 
getCallRemoveUnbindInCallServicesDelay(ContentResolver cr)39         public long getCallRemoveUnbindInCallServicesDelay(ContentResolver cr) {
40             return Timeouts.getCallRemoveUnbindInCallServicesDelay(cr);
41         }
42 
getRetryBluetoothConnectAudioBackoffMillis(ContentResolver cr)43         public long getRetryBluetoothConnectAudioBackoffMillis(ContentResolver cr) {
44             return Timeouts.getRetryBluetoothConnectAudioBackoffMillis(cr);
45         }
46 
getBluetoothPendingTimeoutMillis(ContentResolver cr)47         public long getBluetoothPendingTimeoutMillis(ContentResolver cr) {
48             return Timeouts.getBluetoothPendingTimeoutMillis(cr);
49         }
50 
getEmergencyCallbackWindowMillis(ContentResolver cr)51         public long getEmergencyCallbackWindowMillis(ContentResolver cr) {
52             return Timeouts.getEmergencyCallbackWindowMillis(cr);
53         }
54 
getUserDefinedCallRedirectionTimeoutMillis(ContentResolver cr)55         public long getUserDefinedCallRedirectionTimeoutMillis(ContentResolver cr) {
56             return Timeouts.getUserDefinedCallRedirectionTimeoutMillis(cr);
57         }
58 
getCarrierCallRedirectionTimeoutMillis(ContentResolver cr)59         public long getCarrierCallRedirectionTimeoutMillis(ContentResolver cr) {
60             return Timeouts.getCarrierCallRedirectionTimeoutMillis(cr);
61         }
62 
getPhoneAccountSuggestionServiceTimeout(ContentResolver cr)63         public long getPhoneAccountSuggestionServiceTimeout(ContentResolver cr) {
64             return Timeouts.getPhoneAccountSuggestionServiceTimeout(cr);
65         }
66 
getCallRecordingToneRepeatIntervalMillis(ContentResolver cr)67         public long getCallRecordingToneRepeatIntervalMillis(ContentResolver cr) {
68             return Timeouts.getCallRecordingToneRepeatIntervalMillis(cr);
69         }
70     }
71 
72     /** A prefix to use for all keys so to not clobber the global namespace. */
73     private static final String PREFIX = "telecom.";
74 
Timeouts()75     private Timeouts() {
76     }
77 
78     /**
79      * Returns the timeout value from Settings or the default value if it hasn't been changed. This
80      * method is safe to call from any thread, including the UI thread.
81      *
82      * @param contentResolver The content resolved.
83      * @param key             Settings key to retrieve.
84      * @param defaultValue    Default value, in milliseconds.
85      * @return The timeout value from Settings or the default value if it hasn't been changed.
86      */
get(ContentResolver contentResolver, String key, long defaultValue)87     private static long get(ContentResolver contentResolver, String key, long defaultValue) {
88         return Settings.Secure.getLong(contentResolver, PREFIX + key, defaultValue);
89     }
90 
91     /**
92      * Returns the amount of time to wait before disconnecting a call that was canceled via
93      * NEW_OUTGOING_CALL broadcast. This timeout allows apps which repost the call using a gateway
94      * to reuse the existing call, preventing the call from causing a start->end->start jank in the
95      * in-call UI.
96      */
getNewOutgoingCallCancelMillis(ContentResolver contentResolver)97     public static long getNewOutgoingCallCancelMillis(ContentResolver contentResolver) {
98         return get(contentResolver, "new_outgoing_call_cancel_ms", 500L);
99     }
100 
101     /**
102      * Returns the maximum amount of time to wait before disconnecting a call that was canceled via
103      * NEW_OUTGOING_CALL broadcast. This prevents malicious or poorly configured apps from
104      * forever tying up the Telecom stack.
105      */
getMaxNewOutgoingCallCancelMillis(ContentResolver contentResolver)106     public static long getMaxNewOutgoingCallCancelMillis(ContentResolver contentResolver) {
107         return get(contentResolver, "max_new_outgoing_call_cancel_ms", 10000L);
108     }
109 
110     /**
111      * Returns the amount of time to play each DTMF tone after post dial continue.
112      * This timeout allows the current tone to play for a certain amount of time before either being
113      * interrupted by the next tone or terminated.
114      */
getDelayBetweenDtmfTonesMillis(ContentResolver contentResolver)115     public static long getDelayBetweenDtmfTonesMillis(ContentResolver contentResolver) {
116         return get(contentResolver, "delay_between_dtmf_tones_ms", 300L);
117     }
118 
119     /**
120      * Returns the amount of time to wait for an emergency call to be placed before routing to
121      * a different call service. A value of 0 or less means no timeout should be used.
122      */
getEmergencyCallTimeoutMillis(ContentResolver contentResolver)123     public static long getEmergencyCallTimeoutMillis(ContentResolver contentResolver) {
124         return get(contentResolver, "emergency_call_timeout_millis", 25000L /* 25 seconds */);
125     }
126 
127     /**
128      * Returns the amount of time to wait for an emergency call to be placed before routing to
129      * a different call service. This timeout is used only when the radio is powered off (for
130      * example in airplane mode). A value of 0 or less means no timeout should be used.
131      */
getEmergencyCallTimeoutRadioOffMillis(ContentResolver contentResolver)132     public static long getEmergencyCallTimeoutRadioOffMillis(ContentResolver contentResolver) {
133         return get(contentResolver, "emergency_call_timeout_radio_off_millis",
134                 60000L /* 1 minute */);
135     }
136 
137     /**
138      * Returns the amount of delay before unbinding the in-call services after all the calls
139      * are removed.
140      */
getCallRemoveUnbindInCallServicesDelay(ContentResolver contentResolver)141     public static long getCallRemoveUnbindInCallServicesDelay(ContentResolver contentResolver) {
142         return get(contentResolver, "call_remove_unbind_in_call_services_delay",
143                 2000L /* 2 seconds */);
144     }
145 
146     /**
147      * Returns the amount of time for which bluetooth is considered connected after requesting
148      * connection. This compensates for the amount of time it takes for the audio route to
149      * actually change to bluetooth.
150      */
getBluetoothPendingTimeoutMillis(ContentResolver contentResolver)151     public static long getBluetoothPendingTimeoutMillis(ContentResolver contentResolver) {
152         return get(contentResolver, "bluetooth_pending_timeout_millis", 5000L);
153     }
154 
155     /**
156      * Returns the amount of time to wait before retrying the connectAudio call. This is
157      * necessary to account for the HeadsetStateMachine sometimes not being ready when we want to
158      * connect to bluetooth audio immediately after a device connects.
159      */
getRetryBluetoothConnectAudioBackoffMillis(ContentResolver contentResolver)160     public static long getRetryBluetoothConnectAudioBackoffMillis(ContentResolver contentResolver) {
161         return get(contentResolver, "retry_bluetooth_connect_audio_backoff_millis", 500L);
162     }
163 
164     /**
165      * Returns the amount of time to wait for the phone account suggestion service to reply.
166      */
getPhoneAccountSuggestionServiceTimeout(ContentResolver contentResolver)167     public static long getPhoneAccountSuggestionServiceTimeout(ContentResolver contentResolver) {
168         return get(contentResolver, "phone_account_suggestion_service_timeout",
169                 5000L /* 5 seconds */);
170     }
171 
172     /**
173      * Returns the amount of time to wait for the call screening service to allow or disallow a
174      * call.
175      */
getCallScreeningTimeoutMillis(ContentResolver contentResolver)176     public static long getCallScreeningTimeoutMillis(ContentResolver contentResolver) {
177         return get(contentResolver, "call_screening_timeout", 5000L /* 5 seconds */);
178     }
179 
180     /**
181      * Returns the amount of time after an emergency call that incoming calls should be treated
182      * as potential emergency callbacks.
183      */
getEmergencyCallbackWindowMillis(ContentResolver contentResolver)184     public static long getEmergencyCallbackWindowMillis(ContentResolver contentResolver) {
185         return get(contentResolver, "emergency_callback_window_millis",
186                 TimeUnit.MILLISECONDS.convert(5, TimeUnit.MINUTES));
187     }
188 
189     /**
190      * Returns the amount of time for an user-defined {@link CallRedirectionService}.
191      *
192      * @param contentResolver The content resolved.
193      */
getUserDefinedCallRedirectionTimeoutMillis(ContentResolver contentResolver)194     public static long getUserDefinedCallRedirectionTimeoutMillis(ContentResolver contentResolver) {
195         return get(contentResolver, "user_defined_call_redirection_timeout",
196                 5000L /* 5 seconds */);
197     }
198 
199     /**
200      * Returns the amount of time for a carrier {@link CallRedirectionService}.
201      *
202      * @param contentResolver The content resolved.
203      */
getCarrierCallRedirectionTimeoutMillis(ContentResolver contentResolver)204     public static long getCarrierCallRedirectionTimeoutMillis(ContentResolver contentResolver) {
205         return get(contentResolver, "carrier_call_redirection_timeout", 5000L /* 5 seconds */);
206     }
207 
208     /**
209      * Returns the number of milliseconds between two plays of the call recording tone.
210      */
getCallRecordingToneRepeatIntervalMillis(ContentResolver contentResolver)211     public static long getCallRecordingToneRepeatIntervalMillis(ContentResolver contentResolver) {
212         return get(contentResolver, "call_recording_tone_repeat_interval", 15000L /* 15 seconds */);
213     }
214 }
215