summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTyler Gunn <tgunn@google.com>2017-08-04 09:28:59 -0700
committerTyler Gunn <tgunn@google.com>2017-08-28 16:07:20 +0000
commitbcf23de07aed59ed34d0121a76d29b6ed9a14288 (patch)
tree4457266e6da5e7150257f46f8cbd65a4976d0999
parentdb86aa5bc50f8c6440dce1672864e29aaeba4a5d (diff)
downloadandroid_packages_services_Telecomm-bcf23de07aed59ed34d0121a76d29b6ed9a14288.tar.gz
android_packages_services_Telecomm-bcf23de07aed59ed34d0121a76d29b6ed9a14288.tar.bz2
android_packages_services_Telecomm-bcf23de07aed59ed34d0121a76d29b6ed9a14288.zip
Change getAgeMillis to use elapsed system time instead of wall-clock time.
Changing getAgeMillis to rely on SystemClock#elapsedRealtime() to determine the duration of a call. This ensures that changes to the device time zone, clock updates by the network and user initiated time changes to not impact the duration of calls in the call log. Test: Manual, unit Bug: 64068300 Merged-In: I62924dc7889c86a7457d05f8fbb20ab8189ece1a Change-Id: I62924dc7889c86a7457d05f8fbb20ab8189ece1a (cherry picked from commit 6c3a2dd68c9ac5584f48cf5f62fa01896fccdc7d)
-rw-r--r--src/com/android/server/telecom/Call.java92
-rw-r--r--src/com/android/server/telecom/CallsManager.java29
-rw-r--r--src/com/android/server/telecom/ClockProxy.java39
-rw-r--r--src/com/android/server/telecom/TelecomSystem.java7
-rw-r--r--src/com/android/server/telecom/components/TelecomService.java16
-rw-r--r--tests/src/com/android/server/telecom/tests/BasicCallTests.java29
-rw-r--r--tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java4
-rw-r--r--tests/src/com/android/server/telecom/tests/TelecomSystemTest.java26
8 files changed, 192 insertions, 50 deletions
diff --git a/src/com/android/server/telecom/Call.java b/src/com/android/server/telecom/Call.java
index 9ab52900..90c1fe81 100644
--- a/src/com/android/server/telecom/Call.java
+++ b/src/com/android/server/telecom/Call.java
@@ -27,6 +27,7 @@ import android.os.Looper;
import android.os.ParcelFileDescriptor;
import android.os.Parcelable;
import android.os.RemoteException;
+import android.os.SystemClock;
import android.os.Trace;
import android.provider.ContactsContract.Contacts;
import android.telecom.CallAudioState;
@@ -242,17 +243,38 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
private String mViaNumber = "";
/**
- * The time this call was created. Beyond logging and such, may also be used for bookkeeping
- * and specifically for marking certain call attempts as failed attempts.
+ * The wall clock time this call was created. Beyond logging and such, may also be used for
+ * bookkeeping and specifically for marking certain call attempts as failed attempts.
+ * Note: This timestamp should NOT be used for calculating call duration.
*/
- private long mCreationTimeMillis = System.currentTimeMillis();
+ private long mCreationTimeMillis;
/** The time this call was made active. */
private long mConnectTimeMillis = 0;
- /** The time this call was disconnected. */
+ /**
+ * The time, in millis, since boot when this call was connected. This should ONLY be used when
+ * calculating the duration of the call.
+ *
+ * The reason for this is that the {@link SystemClock#elapsedRealtime()} is based on the
+ * elapsed time since the device was booted. Changes to the system clock (e.g. due to NITZ
+ * time sync, time zone changes user initiated clock changes) would cause a duration calculated
+ * based on {@link #mConnectTimeMillis} to change based on the delta in the time.
+ * Using the {@link SystemClock#elapsedRealtime()} ensures that changes to the wall clock do
+ * not impact the call duration.
+ */
+ private long mConnectElapsedTimeMillis = 0;
+
+ /** The wall clock time this call was disconnected. */
private long mDisconnectTimeMillis = 0;
+ /**
+ * The elapsed time since boot when this call was disconnected. Recorded as the
+ * {@link SystemClock#elapsedRealtime()}. This ensures that the call duration is not impacted
+ * by changes in the wall time clock.
+ */
+ private long mDisconnectElapsedTimeMillis = 0;
+
/** The gateway information associated with this call. This stores the original call handle
* that the user is attempting to connect to via the gateway, the actual handle to dial in
* order to connect the call via the gateway, as well as the package name of the gateway
@@ -376,6 +398,7 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
private final ConnectionServiceRepository mRepository;
private final Context mContext;
private final CallsManager mCallsManager;
+ private final ClockProxy mClockProxy;
private final TelecomSystem.SyncRoot mLock;
private final String mId;
private String mConnectionId;
@@ -471,20 +494,19 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
/**
* Persists the specified parameters and initializes the new instance.
- *
- * @param context The context.
+ * @param context The context.
* @param repository The connection service repository.
* @param handle The handle to dial.
* @param gatewayInfo Gateway information to use for the call.
* @param connectionManagerPhoneAccountHandle Account to use for the service managing the call.
- * This account must be one that was registered with the
- * {@link PhoneAccount#CAPABILITY_CONNECTION_MANAGER} flag.
+* This account must be one that was registered with the
+* {@link PhoneAccount#CAPABILITY_CONNECTION_MANAGER} flag.
* @param targetPhoneAccountHandle Account information to use for the call. This account must be
- * one that was registered with the {@link PhoneAccount#CAPABILITY_CALL_PROVIDER} flag.
+* one that was registered with the {@link PhoneAccount#CAPABILITY_CALL_PROVIDER} flag.
* @param callDirection one of CALL_DIRECTION_INCOMING, CALL_DIRECTION_OUTGOING,
- * or CALL_DIRECTION_UNKNOWN.
+* or CALL_DIRECTION_UNKNOWN.
* @param shouldAttachToExistingConnection Set to true to attach the call to an existing
- * connection, regardless of whether it's incoming or outgoing.
+ * @param clockProxy
*/
public Call(
String callId,
@@ -501,7 +523,8 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
PhoneAccountHandle targetPhoneAccountHandle,
int callDirection,
boolean shouldAttachToExistingConnection,
- boolean isConference) {
+ boolean isConference,
+ ClockProxy clockProxy) {
mId = callId;
mConnectionId = callId;
mState = isConference ? CallState.ACTIVE : CallState.NEW;
@@ -522,26 +545,27 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
|| callDirection == CALL_DIRECTION_INCOMING;
maybeLoadCannedSmsResponses();
mAnalytics = new Analytics.CallInfo();
-
+ mClockProxy = clockProxy;
+ mCreationTimeMillis = mClockProxy.currentTimeMillis();
}
/**
* Persists the specified parameters and initializes the new instance.
- *
- * @param context The context.
+ * @param context The context.
* @param repository The connection service repository.
* @param handle The handle to dial.
* @param gatewayInfo Gateway information to use for the call.
* @param connectionManagerPhoneAccountHandle Account to use for the service managing the call.
- * This account must be one that was registered with the
- * {@link PhoneAccount#CAPABILITY_CONNECTION_MANAGER} flag.
+* This account must be one that was registered with the
+* {@link PhoneAccount#CAPABILITY_CONNECTION_MANAGER} flag.
* @param targetPhoneAccountHandle Account information to use for the call. This account must be
- * one that was registered with the {@link PhoneAccount#CAPABILITY_CALL_PROVIDER} flag.
+* one that was registered with the {@link PhoneAccount#CAPABILITY_CALL_PROVIDER} flag.
* @param callDirection one of CALL_DIRECTION_INCOMING, CALL_DIRECTION_OUTGOING,
- * or CALL_DIRECTION_UNKNOWN
+* or CALL_DIRECTION_UNKNOWN
* @param shouldAttachToExistingConnection Set to true to attach the call to an existing
- * connection, regardless of whether it's incoming or outgoing.
+* connection, regardless of whether it's incoming or outgoing.
* @param connectTimeMillis The connection time of the call.
+ * @param clockProxy
*/
Call(
String callId,
@@ -559,13 +583,16 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
int callDirection,
boolean shouldAttachToExistingConnection,
boolean isConference,
- long connectTimeMillis) {
+ long connectTimeMillis,
+ long connectElapsedTimeMillis,
+ ClockProxy clockProxy) {
this(callId, context, callsManager, lock, repository, contactsAsyncHelper,
callerInfoAsyncQueryFactory, phoneNumberUtilsAdapter, handle, gatewayInfo,
connectionManagerPhoneAccountHandle, targetPhoneAccountHandle, callDirection,
- shouldAttachToExistingConnection, isConference);
+ shouldAttachToExistingConnection, isConference, clockProxy);
mConnectTimeMillis = connectTimeMillis;
+ mConnectElapsedTimeMillis = connectElapsedTimeMillis;
mAnalytics.setCallStartTime(connectTimeMillis);
}
@@ -790,14 +817,17 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
// We check to see if mConnectTime is already set to prevent the
// call from resetting active time when it goes in and out of
// ACTIVE/ON_HOLD
- mConnectTimeMillis = System.currentTimeMillis();
+ mConnectTimeMillis = mClockProxy.currentTimeMillis();
+ mConnectElapsedTimeMillis = mClockProxy.elapsedRealtime();
mAnalytics.setCallStartTime(mConnectTimeMillis);
}
// We're clearly not disconnected, so reset the disconnected time.
mDisconnectTimeMillis = 0;
+ mDisconnectElapsedTimeMillis = 0;
} else if (mState == CallState.DISCONNECTED) {
- mDisconnectTimeMillis = System.currentTimeMillis();
+ mDisconnectTimeMillis = mClockProxy.currentTimeMillis();
+ mDisconnectElapsedTimeMillis = mClockProxy.elapsedRealtime();
mAnalytics.setCallEndTime(mDisconnectTimeMillis);
setLocallyDisconnecting(false);
fixParentAfterDisconnect();
@@ -1200,9 +1230,11 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
}
/**
+ * Note: This method relies on {@link #mConnectElapsedTimeMillis} and
+ * {@link #mDisconnectElapsedTimeMillis} which are independent of the wall clock (which could
+ * change due to clock changes).
* @return The "age" of this call object in milliseconds, which typically also represents the
- * period since this call was added to the set pending outgoing calls, see
- * mCreationTimeMillis.
+ * period since this call was added to the set pending outgoing calls.
*/
@VisibleForTesting
public long getAgeMillis() {
@@ -1211,16 +1243,16 @@ public class Call implements CreateConnectionResponse, EventManager.Loggable {
mDisconnectCause.getCode() == DisconnectCause.MISSED)) {
// Rejected and missed calls have no age. They're immortal!!
return 0;
- } else if (mConnectTimeMillis == 0) {
+ } else if (mConnectElapsedTimeMillis == 0) {
// Age is measured in the amount of time the call was active. A zero connect time
// indicates that we never went active, so return 0 for the age.
return 0;
- } else if (mDisconnectTimeMillis == 0) {
+ } else if (mDisconnectElapsedTimeMillis == 0) {
// We connected, but have not yet disconnected
- return System.currentTimeMillis() - mConnectTimeMillis;
+ return mClockProxy.elapsedRealtime() - mConnectElapsedTimeMillis;
}
- return mDisconnectTimeMillis - mConnectTimeMillis;
+ return mDisconnectElapsedTimeMillis - mConnectElapsedTimeMillis;
}
/**
diff --git a/src/com/android/server/telecom/CallsManager.java b/src/com/android/server/telecom/CallsManager.java
index c44e4fab..6cb08b2b 100644
--- a/src/com/android/server/telecom/CallsManager.java
+++ b/src/com/android/server/telecom/CallsManager.java
@@ -257,6 +257,7 @@ public class CallsManager extends Call.ListenerBase
private final DefaultDialerCache mDefaultDialerCache;
private final Timeouts.Adapter mTimeoutsAdapter;
private final PhoneNumberUtilsAdapter mPhoneNumberUtilsAdapter;
+ private final ClockProxy mClockProxy;
private final Set<Call> mLocallyDisconnectingCalls = new HashSet<>();
private final Set<Call> mPendingCallsToDisconnect = new HashSet<>();
/* Handler tied to thread in which CallManager was initialized. */
@@ -306,7 +307,8 @@ public class CallsManager extends Call.ListenerBase
AsyncRingtonePlayer asyncRingtonePlayer,
PhoneNumberUtilsAdapter phoneNumberUtilsAdapter,
EmergencyCallHelper emergencyCallHelper,
- InCallTonePlayer.ToneGeneratorFactory toneGeneratorFactory) {
+ InCallTonePlayer.ToneGeneratorFactory toneGeneratorFactory,
+ ClockProxy clockProxy) {
mContext = context;
mLock = lock;
mPhoneNumberUtilsAdapter = phoneNumberUtilsAdapter;
@@ -370,6 +372,7 @@ public class CallsManager extends Call.ListenerBase
mConnectionServiceRepository =
new ConnectionServiceRepository(mPhoneAccountRegistrar, mContext, mLock, this);
mInCallWakeLockController = inCallWakeLockControllerFactory.create(context, this);
+ mClockProxy = clockProxy;
mListeners.add(mInCallWakeLockController);
mListeners.add(statusBarNotifier);
@@ -833,8 +836,8 @@ public class CallsManager extends Call.ListenerBase
phoneAccountHandle,
Call.CALL_DIRECTION_INCOMING /* callDirection */,
false /* forceAttachToExistingConnection */,
- false /* isConference */
- );
+ false, /* isConference */
+ mClockProxy);
// Ensure new calls related to self-managed calls/connections are set as such. This will
// be overridden when the actual connection is returned in startCreateConnection, however
@@ -967,8 +970,8 @@ public class CallsManager extends Call.ListenerBase
// Use onCreateIncomingConnection in TelephonyConnectionService, so that we attach
// to the existing connection instead of trying to create a new one.
true /* forceAttachToExistingConnection */,
- false /* isConference */
- );
+ false, /* isConference */
+ mClockProxy);
call.initAnalytics();
setIntentExtrasAndStartTime(call, extras);
@@ -1047,8 +1050,8 @@ public class CallsManager extends Call.ListenerBase
null /* phoneAccountHandle */,
Call.CALL_DIRECTION_OUTGOING /* callDirection */,
false /* forceAttachToExistingConnection */,
- false /* isConference */
- );
+ false, /* isConference */
+ mClockProxy);
call.initAnalytics();
// Ensure new calls related to self-managed calls/connections are set as such. This
@@ -2023,6 +2026,10 @@ public class CallsManager extends Call.ListenerBase
parcelableConference.getConnectTimeMillis() ==
Conference.CONNECT_TIME_NOT_SPECIFIED ? 0 :
parcelableConference.getConnectTimeMillis();
+ long connectElapsedTime =
+ parcelableConference.getConnectElapsedTimeMillis() ==
+ Conference.CONNECT_TIME_NOT_SPECIFIED ? 0 :
+ parcelableConference.getConnectElapsedTimeMillis();
Call call = new Call(
callId,
@@ -2040,7 +2047,9 @@ public class CallsManager extends Call.ListenerBase
Call.CALL_DIRECTION_UNDEFINED /* callDirection */,
false /* forceAttachToExistingConnection */,
true /* isConference */,
- connectTime);
+ connectTime,
+ connectElapsedTime,
+ mClockProxy);
setCallState(call, Call.getStateFromConnectionState(parcelableConference.getState()),
"new conference call");
@@ -2707,7 +2716,9 @@ public class CallsManager extends Call.ListenerBase
Call.CALL_DIRECTION_UNDEFINED /* callDirection */,
false /* forceAttachToExistingConnection */,
isDowngradedConference /* isConference */,
- connection.getConnectTimeMillis() /* connectTimeMillis */);
+ connection.getConnectTimeMillis() /* connectTimeMillis */,
+ connection.getConnectElapsedTimeMillis(), /* connectElapsedTimeMillis */
+ mClockProxy);
call.initAnalytics();
call.getAnalytics().setCreatedFromExistingConnection(true);
diff --git a/src/com/android/server/telecom/ClockProxy.java b/src/com/android/server/telecom/ClockProxy.java
new file mode 100644
index 00000000..6f92f947
--- /dev/null
+++ b/src/com/android/server/telecom/ClockProxy.java
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.server.telecom;
+
+import android.os.SystemClock;
+
+/**
+ * Defines common clock functionality used in Telecom. Provided to make unit testing of clock
+ * operations testable.
+ */
+public interface ClockProxy {
+ /**
+ * Returns the current wall-clock time of the system, as typically returned by
+ * {@link System#currentTimeMillis()}.
+ * @return The current wall-clock time.
+ */
+ long currentTimeMillis();
+
+ /**
+ * Returns the elapsed time since boot of the system, as typically returned by
+ * {@link SystemClock#elapsedRealtime()}.
+ * @return the current elapsed real time.
+ */
+ long elapsedRealtime();
+}
diff --git a/src/com/android/server/telecom/TelecomSystem.java b/src/com/android/server/telecom/TelecomSystem.java
index b40381bb..31afbba6 100644
--- a/src/com/android/server/telecom/TelecomSystem.java
+++ b/src/com/android/server/telecom/TelecomSystem.java
@@ -22,7 +22,6 @@ import com.android.server.telecom.bluetooth.BluetoothRouteManager;
import com.android.server.telecom.components.UserCallIntentProcessor;
import com.android.server.telecom.components.UserCallIntentProcessorFactory;
import com.android.server.telecom.ui.IncomingCallNotifier;
-import com.android.server.telecom.ui.IncomingCallNotifier.IncomingCallNotifierFactory;
import com.android.server.telecom.ui.MissedCallNotifierImpl.MissedCallNotifierImplFactory;
import com.android.server.telecom.BluetoothPhoneServiceImpl.BluetoothPhoneServiceImplFactory;
import com.android.server.telecom.CallAudioManager.AudioServiceFactory;
@@ -190,7 +189,8 @@ public class TelecomSystem {
AsyncRingtonePlayer asyncRingtonePlayer,
PhoneNumberUtilsAdapter phoneNumberUtilsAdapter,
IncomingCallNotifier incomingCallNotifier,
- InCallTonePlayer.ToneGeneratorFactory toneGeneratorFactory) {
+ InCallTonePlayer.ToneGeneratorFactory toneGeneratorFactory,
+ ClockProxy clockProxy) {
mContext = context.getApplicationContext();
LogUtils.initLogging(mContext);
DefaultDialerManagerAdapter defaultDialerAdapter =
@@ -255,7 +255,8 @@ public class TelecomSystem {
asyncRingtonePlayer,
phoneNumberUtilsAdapter,
emergencyCallHelper,
- toneGeneratorFactory);
+ toneGeneratorFactory,
+ clockProxy);
mIncomingCallNotifier = incomingCallNotifier;
incomingCallNotifier.setCallsManagerProxy(new IncomingCallNotifier.CallsManagerProxy() {
diff --git a/src/com/android/server/telecom/components/TelecomService.java b/src/com/android/server/telecom/components/TelecomService.java
index d9d60b86..19dd404e 100644
--- a/src/com/android/server/telecom/components/TelecomService.java
+++ b/src/com/android/server/telecom/components/TelecomService.java
@@ -25,6 +25,7 @@ import android.media.ToneGenerator;
import android.os.IBinder;
import android.os.PowerManager;
import android.os.ServiceManager;
+import android.os.SystemClock;
import android.telecom.Log;
import com.android.internal.telephony.CallerInfoAsyncQuery;
@@ -33,6 +34,7 @@ import com.android.server.telecom.BluetoothAdapterProxy;
import com.android.server.telecom.BluetoothPhoneServiceImpl;
import com.android.server.telecom.CallerInfoAsyncQueryFactory;
import com.android.server.telecom.CallsManager;
+import com.android.server.telecom.ClockProxy;
import com.android.server.telecom.DefaultDialerCache;
import com.android.server.telecom.HeadsetMediaButton;
import com.android.server.telecom.HeadsetMediaButtonFactory;
@@ -161,8 +163,18 @@ public class TelecomService extends Service implements TelecomSystem.Component {
new AsyncRingtonePlayer(),
new PhoneNumberUtilsAdapterImpl(),
new IncomingCallNotifier(context),
- ToneGenerator::new
- ));
+ ToneGenerator::new,
+ new ClockProxy() {
+ @Override
+ public long currentTimeMillis() {
+ return System.currentTimeMillis();
+ }
+
+ @Override
+ public long elapsedRealtime() {
+ return SystemClock.elapsedRealtime();
+ }
+ }));
}
if (BluetoothAdapter.getDefaultAdapter() != null) {
context.startService(new Intent(context, BluetoothPhoneService.class));
diff --git a/tests/src/com/android/server/telecom/tests/BasicCallTests.java b/tests/src/com/android/server/telecom/tests/BasicCallTests.java
index ce774a78..905a15e6 100644
--- a/tests/src/com/android/server/telecom/tests/BasicCallTests.java
+++ b/tests/src/com/android/server/telecom/tests/BasicCallTests.java
@@ -82,11 +82,22 @@ public class BasicCallTests extends TelecomSystemTest {
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureX.getCall(ids.mCallId).getState());
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureY.getCall(ids.mCallId).getState());
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(ids.mConnectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureX.getCall(ids.mCallId).getState());
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureY.getCall(ids.mCallId).getState());
+ assertEquals(TEST_CONNECT_TIME,
+ mInCallServiceFixtureX.getCall(ids.mCallId).getConnectTimeMillis());
+ assertEquals(TEST_CONNECT_TIME,
+ mInCallServiceFixtureY.getCall(ids.mCallId).getConnectTimeMillis());
+ assertEquals(TEST_CREATE_TIME,
+ mInCallServiceFixtureX.getCall(ids.mCallId).getCreationTimeMillis());
+ assertEquals(TEST_CREATE_TIME,
+ mInCallServiceFixtureY.getCall(ids.mCallId).getCreationTimeMillis());
+
verifyNoBlockChecks();
}
@@ -95,6 +106,8 @@ public class BasicCallTests extends TelecomSystemTest {
IdPair ids = startAndMakeActiveOutgoingCall("650-555-1212",
mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(ids.mConnectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureX.getCall(ids.mCallId).getState());
@@ -219,6 +232,8 @@ public class BasicCallTests extends TelecomSystemTest {
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureX.getCall(ids.mCallId).getState());
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureY.getCall(ids.mCallId).getState());
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(ids.mConnectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureX.getCall(ids.mCallId).getState());
@@ -231,6 +246,8 @@ public class BasicCallTests extends TelecomSystemTest {
IdPair ids = startAndMakeActiveIncomingCall("650-555-1212",
mPhoneAccountA0.getAccountHandle(), mConnectionServiceFixtureA);
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(ids.mConnectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureX.getCall(ids.mCallId).getState());
@@ -290,6 +307,8 @@ public class BasicCallTests extends TelecomSystemTest {
IdPair ids = outgoingCallPhoneAccountSelected(mPhoneAccountA0.getAccountHandle(),
startingNumConnections, startingNumCalls, mConnectionServiceFixtureA);
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(ids.mConnectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED,
mInCallServiceFixtureX.getCall(ids.mCallId).getState());
@@ -341,6 +360,8 @@ public class BasicCallTests extends TelecomSystemTest {
@LargeTest
public void testIncomingCallCallerInfoLookupTimesOutIsAllowed() throws Exception {
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_CREATE_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_CREATE_ELAPSED_TIME);
Bundle extras = new Bundle();
extras.putParcelable(
TelecomManager.EXTRA_INCOMING_CALL_ADDRESS,
@@ -377,6 +398,8 @@ public class BasicCallTests extends TelecomSystemTest {
verify(mInCallServiceFixtureY.getTestDouble(), timeout(TEST_TIMEOUT))
.addCall(any(ParcelableCall.class));
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_CONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_CONNECT_ELAPSED_TIME);
disconnectCall(mInCallServiceFixtureX.mLatestCallId,
mConnectionServiceFixtureA.mLatestConnectionId);
}
@@ -736,9 +759,15 @@ public class BasicCallTests extends TelecomSystemTest {
}
private void disconnectCall(String callId, String connectionId) throws Exception {
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_DISCONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_DISCONNECT_ELAPSED_TIME);
mConnectionServiceFixtureA.sendSetDisconnected(connectionId, DisconnectCause.LOCAL);
assertEquals(Call.STATE_DISCONNECTED, mInCallServiceFixtureX.getCall(callId).getState());
assertEquals(Call.STATE_DISCONNECTED, mInCallServiceFixtureY.getCall(callId).getState());
+ assertEquals(TEST_CREATE_TIME,
+ mInCallServiceFixtureX.getCall(callId).getCreationTimeMillis());
+ assertEquals(TEST_CREATE_TIME,
+ mInCallServiceFixtureY.getCall(callId).getCreationTimeMillis());
}
/**
diff --git a/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java b/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
index e815b5cb..39f70c8c 100644
--- a/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
+++ b/tests/src/com/android/server/telecom/tests/ConnectionServiceFixture.java
@@ -50,7 +50,6 @@ import com.google.android.collect.Lists;
import java.lang.Override;
import java.util.ArrayList;
-import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
@@ -410,6 +409,7 @@ public class ConnectionServiceFixture implements TestFixture<IConnectionService>
IVideoProvider videoProvider;
int videoState;
long connectTimeMillis;
+ long connectElapsedTimeMillis;
StatusHints statusHints;
Bundle extras;
}
@@ -640,6 +640,7 @@ public class ConnectionServiceFixture implements TestFixture<IConnectionService>
c.videoProvider,
c.videoState,
c.connectTimeMillis,
+ c.connectElapsedTimeMillis,
c.statusHints,
c.extras);
}
@@ -660,6 +661,7 @@ public class ConnectionServiceFixture implements TestFixture<IConnectionService>
false, /* ringback requested */
false, /* voip audio mode */
0, /* Connect Time for conf call on this connection */
+ 0, /* Connect Real Time comes from conference call */
c.statusHints,
c.disconnectCause,
c.conferenceableConnectionIds,
diff --git a/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java b/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
index 205d7788..e51a9c75 100644
--- a/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
+++ b/tests/src/com/android/server/telecom/tests/TelecomSystemTest.java
@@ -65,11 +65,10 @@ import com.android.internal.telecom.IInCallAdapter;
import com.android.server.telecom.AsyncRingtonePlayer;
import com.android.server.telecom.BluetoothPhoneServiceImpl;
import com.android.server.telecom.CallAudioManager;
-import com.android.server.telecom.CallAudioRouteStateMachine;
-import com.android.server.telecom.CallerInfoAsyncQueryFactory;
import com.android.server.telecom.CallerInfoLookupHelper;
import com.android.server.telecom.CallsManager;
import com.android.server.telecom.CallsManagerListenerBase;
+import com.android.server.telecom.ClockProxy;
import com.android.server.telecom.DefaultDialerCache;
import com.android.server.telecom.HeadsetMediaButton;
import com.android.server.telecom.HeadsetMediaButtonFactory;
@@ -83,7 +82,6 @@ import com.android.server.telecom.ProximitySensorManager;
import com.android.server.telecom.ProximitySensorManagerFactory;
import com.android.server.telecom.TelecomSystem;
import com.android.server.telecom.Timeouts;
-import com.android.server.telecom.callfiltering.AsyncBlockCheckFilter;
import com.android.server.telecom.components.UserCallIntentProcessor;
import com.android.server.telecom.ui.IncomingCallNotifier;
import com.android.server.telecom.ui.MissedCallNotifierImpl.MissedCallNotifierImplFactory;
@@ -108,6 +106,16 @@ public class TelecomSystemTest extends TelecomTestCase {
static final int TEST_POLL_INTERVAL = 10; // milliseconds
static final int TEST_TIMEOUT = 1000; // milliseconds
+ // Purposely keep the connect time (which is wall clock) and elapsed time (which is time since
+ // boot) different to test that wall clock time operations and elapsed time operations perform
+ // as they individually should.
+ static final long TEST_CREATE_TIME = 100;
+ static final long TEST_CREATE_ELAPSED_TIME = 200;
+ static final long TEST_CONNECT_TIME = 1000;
+ static final long TEST_CONNECT_ELAPSED_TIME = 2000;
+ static final long TEST_DISCONNECT_TIME = 8000;
+ static final long TEST_DISCONNECT_ELAPSED_TIME = 4000;
+
public class HeadsetMediaButtonFactoryF implements HeadsetMediaButtonFactory {
@Override
public HeadsetMediaButton create(Context context, CallsManager callsManager,
@@ -194,6 +202,7 @@ public class TelecomSystemTest extends TelecomTestCase {
@Mock BluetoothPhoneServiceImpl mBluetoothPhoneServiceImpl;
@Mock AsyncRingtonePlayer mAsyncRingtonePlayer;
@Mock IncomingCallNotifier mIncomingCallNotifier;
+ @Mock ClockProxy mClockProxy;
final ComponentName mInCallServiceComponentNameX =
new ComponentName(
@@ -393,7 +402,9 @@ public class TelecomSystemTest extends TelecomTestCase {
when(mTimeoutsAdapter.getCallScreeningTimeoutMillis(any(ContentResolver.class)))
.thenReturn(TEST_TIMEOUT / 5L);
mIncomingCallNotifier = mock(IncomingCallNotifier.class);
-
+ mClockProxy = mock(ClockProxy.class);
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_CREATE_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_CREATE_ELAPSED_TIME);
mTelecomSystem = new TelecomSystem(
mComponentContextFixture.getTestDouble(),
new MissedCallNotifierImplFactory() {
@@ -426,7 +437,8 @@ public class TelecomSystemTest extends TelecomTestCase {
mAsyncRingtonePlayer,
mPhoneNumberUtilsAdapter,
mIncomingCallNotifier,
- (streamType, volume) -> mock(ToneGenerator.class));
+ (streamType, volume) -> mock(ToneGenerator.class),
+ mClockProxy);
mComponentContextFixture.setTelecomManager(new TelecomManager(
mComponentContextFixture.getTestDouble(),
@@ -891,6 +903,8 @@ public class TelecomSystemTest extends TelecomTestCase {
connectionServiceFixture.sendSetVideoState(ids.mConnectionId);
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_CONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_CONNECT_ELAPSED_TIME);
connectionServiceFixture.sendSetActive(ids.mConnectionId);
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureX.getCall(ids.mCallId).getState());
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureY.getCall(ids.mCallId).getState());
@@ -928,6 +942,8 @@ public class TelecomSystemTest extends TelecomTestCase {
.answerVideo(eq(ids.mConnectionId), eq(videoState), any());
}
+ when(mClockProxy.currentTimeMillis()).thenReturn(TEST_CONNECT_TIME);
+ when(mClockProxy.elapsedRealtime()).thenReturn(TEST_CONNECT_ELAPSED_TIME);
connectionServiceFixture.sendSetActive(ids.mConnectionId);
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureX.getCall(ids.mCallId).getState());
assertEquals(Call.STATE_ACTIVE, mInCallServiceFixtureY.getCall(ids.mCallId).getState());