Merge "Remove listener alarms when remote binder dies"

This commit is contained in:
TreeHugger Robot
2020-01-14 01:31:38 +00:00
committed by Android (Google) Code Review
2 changed files with 43 additions and 2 deletions

View File

@@ -208,6 +208,7 @@ class AlarmManagerService extends SystemService {
AppWakeupHistory mAppWakeupHistory;
ClockReceiver mClockReceiver;
final DeliveryTracker mDeliveryTracker = new DeliveryTracker();
IBinder.DeathRecipient mListenerDeathRecipient;
Intent mTimeTickIntent;
IAlarmListener mTimeTickTrigger;
PendingIntent mDateChangeSender;
@@ -1447,6 +1448,18 @@ class AlarmManagerService extends SystemService {
public void onStart() {
mInjector.init();
mListenerDeathRecipient = new IBinder.DeathRecipient() {
@Override
public void binderDied() {
}
@Override
public void binderDied(IBinder who) {
final IAlarmListener listener = IAlarmListener.Stub.asInterface(who);
removeImpl(null, listener);
}
};
synchronized (mLock) {
mHandler = new AlarmHandler();
mConstants = new Constants(mHandler);
@@ -1653,6 +1666,15 @@ class AlarmManagerService extends SystemService {
return;
}
if (directReceiver != null) {
try {
directReceiver.asBinder().linkToDeath(mListenerDeathRecipient, 0);
} catch (RemoteException e) {
Slog.w(TAG, "Dropping unreachable alarm listener " + listenerTag);
return;
}
}
// Sanity check the window length. This will catch people mistakenly
// trying to pass an end-of-window timestamp rather than a duration.
if (windowLength > AlarmManager.INTERVAL_HALF_DAY) {

View File

@@ -345,8 +345,8 @@ public class AlarmManagerServiceTest {
}
/**
* Lowers quotas to make testing feasible.
* Careful while calling as this will replace any existing settings for the calling test.
* Lowers quotas to make testing feasible. Careful while calling as this will replace any
* existing settings for the calling test.
*/
private void setTestableQuotas() {
final StringBuilder constantsBuilder = new StringBuilder();
@@ -981,6 +981,25 @@ public class AlarmManagerServiceTest {
assertEquals(0, mService.mAlarmsPerUid.get(TEST_CALLING_UID));
}
@Test
public void alarmCountOnListenerBinderDied() {
final int numAlarms = 10;
final IAlarmListener[] listeners = new IAlarmListener[numAlarms];
for (int i = 0; i < numAlarms; i++) {
listeners[i] = new IAlarmListener.Stub() {
@Override
public void doAlarm(IAlarmCompleteListener callback) throws RemoteException {
}
};
setTestAlarmWithListener(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + i, listeners[i]);
}
assertEquals(numAlarms, mService.mAlarmsPerUid.get(TEST_CALLING_UID));
for (int i = 0; i < numAlarms; i++) {
mService.mListenerDeathRecipient.binderDied(listeners[i].asBinder());
assertEquals(numAlarms - i - 1, mService.mAlarmsPerUid.get(TEST_CALLING_UID));
}
}
@After
public void tearDown() {
if (mMockingSession != null) {