Merge "Fix the problem that AccessibilityNodeInfo maybe null and cause a crash."
diff --git a/apct-tests/perftests/core/OWNERS b/apct-tests/perftests/core/OWNERS
index 6abab6e..f8fe51c 100644
--- a/apct-tests/perftests/core/OWNERS
+++ b/apct-tests/perftests/core/OWNERS
@@ -12,3 +12,5 @@
per-file /apct-tests/perftests/core/src/android/content/om/* = felkachang@google.com
per-file /apct-tests/perftests/core/src/android/content/om/* = file:/core/java/android/content/om/OWNERS
+# Bug component: 44215
+per-file **Accessibility* = file:/core/java/android/view/accessibility/OWNERS
\ No newline at end of file
diff --git a/core/api/test-current.txt b/core/api/test-current.txt
index dc01662..6e61569 100644
--- a/core/api/test-current.txt
+++ b/core/api/test-current.txt
@@ -1697,6 +1697,10 @@
package android.os {
+ public class BatteryManager {
+ field public static final int BATTERY_PLUGGED_ANY = 15; // 0xf
+ }
+
public final class BatteryStatsManager {
method @RequiresPermission(android.Manifest.permission.DEVICE_POWER) public void resetBattery(boolean);
method @RequiresPermission(android.Manifest.permission.DEVICE_POWER) public void setBatteryLevel(int, boolean);
diff --git a/core/java/android/hardware/SensorAdditionalInfo.java b/core/java/android/hardware/SensorAdditionalInfo.java
index 12edc5e..59def9f 100644
--- a/core/java/android/hardware/SensorAdditionalInfo.java
+++ b/core/java/android/hardware/SensorAdditionalInfo.java
@@ -63,7 +63,7 @@
public final int[] intValues;
/**
- * Typical values of additional infomation type. The set of values is subject to extension in
+ * Typical values of additional information type. The set of values is subject to extension in
* newer versions and vendors have the freedom of define their own custom values.
*
* @hide
diff --git a/core/java/android/hardware/SensorManager.java b/core/java/android/hardware/SensorManager.java
index 6d8c4a9..f053976 100644
--- a/core/java/android/hardware/SensorManager.java
+++ b/core/java/android/hardware/SensorManager.java
@@ -872,9 +872,9 @@
/**
* Flushes the FIFO of all the sensors registered for this listener. If there are events
- * in the FIFO of the sensor, they are returned as if the maxReportLantecy of the FIFO has
+ * in the FIFO of the sensor, they are returned as if the maxReportLatency of the FIFO has
* expired. Events are returned in the usual way through the SensorEventListener.
- * This call doesn't affect the maxReportLantecy for this sensor. This call is asynchronous and
+ * This call doesn't affect the maxReportLatency for this sensor. This call is asynchronous and
* returns immediately.
* {@link android.hardware.SensorEventListener2#onFlushCompleted onFlushCompleted} is called
* after all the events in the batch at the time of calling this method have been delivered
@@ -902,7 +902,7 @@
* Create a sensor direct channel backed by shared memory wrapped in MemoryFile object.
*
* The resulting channel can be used for delivering sensor events to native code, other
- * processes, GPU/DSP or other co-processors without CPU intervention. This is the recommanded
+ * processes, GPU/DSP or other co-processors without CPU intervention. This is the recommended
* for high performance sensor applications that use high sensor rates (e.g. greater than 200Hz)
* and cares about sensor event latency.
*
@@ -924,7 +924,7 @@
* Create a sensor direct channel backed by shared memory wrapped in HardwareBuffer object.
*
* The resulting channel can be used for delivering sensor events to native code, other
- * processes, GPU/DSP or other co-processors without CPU intervention. This is the recommanded
+ * processes, GPU/DSP or other co-processors without CPU intervention. This is the recommended
* for high performance sensor applications that use high sensor rates (e.g. greater than 200Hz)
* and cares about sensor event latency.
*
@@ -1334,11 +1334,11 @@
* returned by {@link #getRotationMatrix}.
*
* @param X
- * defines the axis of the new cooridinate system that coincide with the X axis of the
+ * defines the axis of the new coordinate system that coincide with the X axis of the
* original coordinate system.
*
* @param Y
- * defines the axis of the new cooridinate system that coincide with the Y axis of the
+ * defines the axis of the new coordinate system that coincide with the Y axis of the
* original coordinate system.
*
* @param outR
@@ -1826,7 +1826,7 @@
* This method is used to inject raw sensor data into the HAL. Call {@link
* initDataInjection(boolean)} before this method to set the HAL in data injection mode. This
* method should be called only if a previous call to initDataInjection has been successful and
- * the HAL and SensorService are already opreating in data injection mode.
+ * the HAL and SensorService are already operating in data injection mode.
*
* @param sensor The sensor to inject.
* @param values Sensor values to inject. The length of this
diff --git a/core/java/android/hardware/SystemSensorManager.java b/core/java/android/hardware/SystemSensorManager.java
index 1c4898a..3d87fa3 100644
--- a/core/java/android/hardware/SystemSensorManager.java
+++ b/core/java/android/hardware/SystemSensorManager.java
@@ -453,7 +453,7 @@
public void onReceive(Context context, Intent intent) {
if (intent.getAction() == Intent.ACTION_DYNAMIC_SENSOR_CHANGED) {
if (DEBUG_DYNAMIC_SENSOR) {
- Log.i(TAG, "DYNS received DYNAMIC_SENSOR_CHANED broadcast");
+ Log.i(TAG, "DYNS received DYNAMIC_SENSOR_CHANGED broadcast");
}
// Dynamic sensors probably changed
mDynamicSensorListDirty = true;
@@ -498,7 +498,7 @@
protected void unregisterDynamicSensorCallbackImpl(
DynamicSensorCallback callback) {
if (DEBUG_DYNAMIC_SENSOR) {
- Log.i(TAG, "Removing dynamic sensor listerner");
+ Log.i(TAG, "Removing dynamic sensor listener");
}
mDynamicSensorCallbacks.remove(callback);
}
@@ -624,7 +624,7 @@
}
if (hardwareBuffer.getWidth() < MIN_DIRECT_CHANNEL_BUFFER_SIZE) {
throw new IllegalArgumentException(
- "Width if HaradwareBuffer must be greater than "
+ "Width if HardwareBuffer must be greater than "
+ MIN_DIRECT_CHANNEL_BUFFER_SIZE);
}
if ((hardwareBuffer.getUsage() & HardwareBuffer.USAGE_SENSOR_DIRECT_DATA) == 0) {
@@ -655,7 +655,7 @@
/*
* BaseEventQueue is the communication channel with the sensor service,
- * SensorEventQueue, TriggerEventQueue are subclases and there is one-to-one mapping between
+ * SensorEventQueue, TriggerEventQueue are subclasses and there is one-to-one mapping between
* the queues and the listeners. InjectEventQueue is also a sub-class which is a special case
* where data is being injected into the sensor HAL through the sensor service. It is not
* associated with any listener and there is one InjectEventQueue associated with a
diff --git a/core/java/android/os/BatteryManager.java b/core/java/android/os/BatteryManager.java
index 6bc0f6e..092923e 100644
--- a/core/java/android/os/BatteryManager.java
+++ b/core/java/android/os/BatteryManager.java
@@ -20,6 +20,7 @@
import android.annotation.RequiresPermission;
import android.annotation.SystemApi;
import android.annotation.SystemService;
+import android.annotation.TestApi;
import android.compat.annotation.UnsupportedAppUsage;
import android.content.Context;
import android.content.Intent;
@@ -232,6 +233,7 @@
OsProtoEnums.CHARGING_POLICY_ADAPTIVE_LONGLIFE; // = 4
/** @hide */
+ @TestApi
public static final int BATTERY_PLUGGED_ANY =
BATTERY_PLUGGED_AC | BATTERY_PLUGGED_USB | BATTERY_PLUGGED_WIRELESS
| BATTERY_PLUGGED_DOCK;
diff --git a/core/java/android/os/image/DynamicSystemClient.java b/core/java/android/os/image/DynamicSystemClient.java
index 7cdaecd..d5364df 100644
--- a/core/java/android/os/image/DynamicSystemClient.java
+++ b/core/java/android/os/image/DynamicSystemClient.java
@@ -209,6 +209,13 @@
public static final String ACTION_HIDE_NOTIFICATION =
"android.os.image.action.HIDE_NOTIFICATION";
+ /**
+ * Intent action: notify the service to post a status update when keyguard is dismissed.
+ * @hide
+ */
+ public static final String ACTION_NOTIFY_KEYGUARD_DISMISSED =
+ "android.os.image.action.NOTIFY_KEYGUARD_DISMISSED";
+
/*
* Intent Keys
*/
diff --git a/core/java/android/webkit/OWNERS b/core/java/android/webkit/OWNERS
index b33da57..e7fd7a5 100644
--- a/core/java/android/webkit/OWNERS
+++ b/core/java/android/webkit/OWNERS
@@ -1,4 +1,3 @@
-changwan@google.com
+# Bug component: 76427
ntfschr@google.com
-tobiasjs@google.com
torne@google.com
diff --git a/data/etc/com.android.networkstack.xml b/data/etc/com.android.networkstack.xml
index 06fec1c..003ca53 100644
--- a/data/etc/com.android.networkstack.xml
+++ b/data/etc/com.android.networkstack.xml
@@ -25,6 +25,7 @@
<permission name="android.permission.LOCAL_MAC_ADDRESS"/>
<permission name="android.permission.MANAGE_SUBSCRIPTION_PLANS"/>
<permission name="android.permission.MANAGE_USB"/>
+ <permission name="android.permission.MANAGE_USERS"/>
<permission name="android.permission.NETWORK_BYPASS_PRIVATE_DNS"/>
<permission name="android.permission.PACKET_KEEPALIVE_OFFLOAD"/>
<permission name="android.permission.READ_NETWORK_USAGE_HISTORY"/>
diff --git a/native/webview/OWNERS b/native/webview/OWNERS
index 580bb0f..7e27dc8 100644
--- a/native/webview/OWNERS
+++ b/native/webview/OWNERS
@@ -1,4 +1,4 @@
+# Bug component: 76427
boliu@google.com
-changwan@google.com
-tobiasjs@google.com
+ntfschr@google.com
torne@google.com
diff --git a/packages/DynamicSystemInstallationService/src/com/android/dynsystem/DynamicSystemInstallationService.java b/packages/DynamicSystemInstallationService/src/com/android/dynsystem/DynamicSystemInstallationService.java
index e78de49..3b56016 100644
--- a/packages/DynamicSystemInstallationService/src/com/android/dynsystem/DynamicSystemInstallationService.java
+++ b/packages/DynamicSystemInstallationService/src/com/android/dynsystem/DynamicSystemInstallationService.java
@@ -16,11 +16,10 @@
package com.android.dynsystem;
-import static android.os.AsyncTask.Status.FINISHED;
-import static android.os.AsyncTask.Status.PENDING;
import static android.os.AsyncTask.Status.RUNNING;
import static android.os.image.DynamicSystemClient.ACTION_HIDE_NOTIFICATION;
import static android.os.image.DynamicSystemClient.ACTION_NOTIFY_IF_IN_USE;
+import static android.os.image.DynamicSystemClient.ACTION_NOTIFY_KEYGUARD_DISMISSED;
import static android.os.image.DynamicSystemClient.ACTION_START_INSTALL;
import static android.os.image.DynamicSystemClient.CAUSE_ERROR_EXCEPTION;
import static android.os.image.DynamicSystemClient.CAUSE_ERROR_INVALID_URL;
@@ -234,6 +233,8 @@
executeNotifyIfInUseCommand();
} else if (ACTION_HIDE_NOTIFICATION.equals(action)) {
executeHideNotificationCommand();
+ } else if (ACTION_NOTIFY_KEYGUARD_DISMISSED.equals(action)) {
+ executeNotifyKeyguardDismissed();
}
return Service.START_NOT_STICKY;
@@ -477,6 +478,10 @@
}
}
+ private void executeNotifyKeyguardDismissed() {
+ postStatus(STATUS_NOT_STARTED, CAUSE_INSTALL_CANCELLED, null);
+ }
+
private void resetTaskAndStop() {
resetTaskAndStop(/* removeNotification= */ false);
}
diff --git a/packages/DynamicSystemInstallationService/src/com/android/dynsystem/VerificationActivity.java b/packages/DynamicSystemInstallationService/src/com/android/dynsystem/VerificationActivity.java
index b522729..7401691 100644
--- a/packages/DynamicSystemInstallationService/src/com/android/dynsystem/VerificationActivity.java
+++ b/packages/DynamicSystemInstallationService/src/com/android/dynsystem/VerificationActivity.java
@@ -16,6 +16,7 @@
package com.android.dynsystem;
+import static android.os.image.DynamicSystemClient.ACTION_NOTIFY_KEYGUARD_DISMISSED;
import static android.os.image.DynamicSystemClient.KEY_KEYGUARD_USE_DEFAULT_STRINGS;
import android.app.Activity;
@@ -83,11 +84,19 @@
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == REQUEST_CODE && resultCode == RESULT_OK) {
startInstallationService();
+ } else {
+ notifyKeyguardDismissed();
}
finish();
}
+ private void notifyKeyguardDismissed() {
+ Intent intent = new Intent(this, DynamicSystemInstallationService.class);
+ intent.setAction(ACTION_NOTIFY_KEYGUARD_DISMISSED);
+ startServiceAsUser(intent, UserHandle.SYSTEM);
+ }
+
private void startInstallationService() {
// retrieve data from calling intent
Intent callingIntent = getIntent();
diff --git a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java
index 5641237..9d547bf 100644
--- a/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/volume/VolumeDialogImpl.java
@@ -1889,14 +1889,14 @@
if (row.anim == null) {
row.anim = ObjectAnimator.ofInt(row.slider, "progress", progress, newProgress);
row.anim.setInterpolator(new DecelerateInterpolator());
+ row.anim.addListener(
+ getJankListener(row.view, TYPE_UPDATE, UPDATE_ANIMATION_DURATION));
} else {
row.anim.cancel();
row.anim.setIntValues(progress, newProgress);
}
row.animTargetProgress = newProgress;
row.anim.setDuration(UPDATE_ANIMATION_DURATION);
- row.anim.addListener(
- getJankListener(row.view, TYPE_UPDATE, UPDATE_ANIMATION_DURATION));
row.anim.start();
} else {
// update slider directly to clamped value
diff --git a/services/core/java/com/android/server/audio/AudioService.java b/services/core/java/com/android/server/audio/AudioService.java
index 66682cc..a54b59c 100644
--- a/services/core/java/com/android/server/audio/AudioService.java
+++ b/services/core/java/com/android/server/audio/AudioService.java
@@ -3409,16 +3409,15 @@
synchronized (mHdmiClientLock) {
if (mHdmiManager != null) {
// At most one of mHdmiPlaybackClient and mHdmiTvClient should be non-null
- HdmiClient fullVolumeHdmiClient = mHdmiPlaybackClient;
+ HdmiClient hdmiClient = mHdmiPlaybackClient;
if (mHdmiTvClient != null) {
- fullVolumeHdmiClient = mHdmiTvClient;
+ hdmiClient = mHdmiTvClient;
}
- if (fullVolumeHdmiClient != null
+ if (((mHdmiPlaybackClient != null && isFullVolumeDevice(device))
+ || (mHdmiTvClient != null && mHdmiSystemAudioSupported))
&& mHdmiCecVolumeControlEnabled
- && streamTypeAlias == AudioSystem.STREAM_MUSIC
- // vol change on a full volume device
- && isFullVolumeDevice(device)) {
+ && streamTypeAlias == AudioSystem.STREAM_MUSIC) {
int keyCode = KeyEvent.KEYCODE_UNKNOWN;
switch (direction) {
case AudioManager.ADJUST_RAISE:
@@ -3442,14 +3441,14 @@
try {
switch (keyEventMode) {
case AudioDeviceVolumeManager.ADJUST_MODE_NORMAL:
- fullVolumeHdmiClient.sendVolumeKeyEvent(keyCode, true);
- fullVolumeHdmiClient.sendVolumeKeyEvent(keyCode, false);
+ hdmiClient.sendVolumeKeyEvent(keyCode, true);
+ hdmiClient.sendVolumeKeyEvent(keyCode, false);
break;
case AudioDeviceVolumeManager.ADJUST_MODE_START:
- fullVolumeHdmiClient.sendVolumeKeyEvent(keyCode, true);
+ hdmiClient.sendVolumeKeyEvent(keyCode, true);
break;
case AudioDeviceVolumeManager.ADJUST_MODE_END:
- fullVolumeHdmiClient.sendVolumeKeyEvent(keyCode, false);
+ hdmiClient.sendVolumeKeyEvent(keyCode, false);
break;
default:
Log.e(TAG, "Invalid keyEventMode " + keyEventMode);
diff --git a/services/core/java/com/android/server/pm/permission/PermissionManagerServiceImpl.java b/services/core/java/com/android/server/pm/permission/PermissionManagerServiceImpl.java
index 554e269..b92e73c 100644
--- a/services/core/java/com/android/server/pm/permission/PermissionManagerServiceImpl.java
+++ b/services/core/java/com/android/server/pm/permission/PermissionManagerServiceImpl.java
@@ -2868,9 +2868,7 @@
} else if (!permissionPolicyInitialized
|| (!hardRestricted || restrictionExempt)) {
if ((origPermState != null && origPermState.isGranted())) {
- if (!uidState.grantPermission(bp)) {
- wasChanged = true;
- }
+ uidState.grantPermission(bp);
}
}
if (mIsLeanback && NOTIFICATION_PERMISSIONS.contains(permName)) {
diff --git a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
index f9e2eae..36b9765 100644
--- a/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
+++ b/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
@@ -36,6 +36,7 @@
import android.app.ActivityManager;
import android.app.AppGlobals;
import android.app.AppOpsManager;
+import android.app.ApplicationExitInfo;
import android.app.ILocalWallpaperColorConsumer;
import android.app.IWallpaperManager;
import android.app.IWallpaperManagerCallback;
@@ -189,6 +190,10 @@
private final Object mLock = new Object();
+ private static final double LMK_LOW_THRESHOLD_MEMORY_PERCENTAGE = 10;
+ private static final int LMK_RECONNECT_REBIND_RETRIES = 3;
+ private static final long LMK_RECONNECT_DELAY_MS = 5000;
+
/**
* Minimum time between crashes of a wallpaper service for us to consider
* restarting it vs. just reverting to the static wallpaper.
@@ -1208,6 +1213,7 @@
/** Time in milliseconds until we expect the wallpaper to reconnect (unless we're in the
* middle of an update). If exceeded, the wallpaper gets reset to the system default. */
private static final long WALLPAPER_RECONNECT_TIMEOUT_MS = 10000;
+ private int mLmkLimitRebindRetries = LMK_RECONNECT_REBIND_RETRIES;
final WallpaperInfo mInfo;
IWallpaperService mService;
@@ -1448,20 +1454,51 @@
&& mWallpaper.userId == mCurrentUserId
&& !Objects.equals(mDefaultWallpaperComponent, wpService)
&& !Objects.equals(mImageWallpaper, wpService)) {
- // There is a race condition which causes
- // {@link #mWallpaper.wallpaperUpdating} to be false even if it is
- // currently updating since the broadcast notifying us is async.
- // This race is overcome by the general rule that we only reset the
- // wallpaper if its service was shut down twice
- // during {@link #MIN_WALLPAPER_CRASH_TIME} millis.
- if (mWallpaper.lastDiedTime != 0
- && mWallpaper.lastDiedTime + MIN_WALLPAPER_CRASH_TIME
- > SystemClock.uptimeMillis()) {
- Slog.w(TAG, "Reverting to built-in wallpaper!");
- clearWallpaperLocked(true, FLAG_SYSTEM, mWallpaper.userId, null);
+ List<ApplicationExitInfo> reasonList =
+ mActivityManager.getHistoricalProcessExitReasons(
+ wpService.getPackageName(), 0, 1);
+ int exitReason = ApplicationExitInfo.REASON_UNKNOWN;
+ if (reasonList != null && !reasonList.isEmpty()) {
+ ApplicationExitInfo info = reasonList.get(0);
+ exitReason = info.getReason();
+ }
+ Slog.d(TAG, "exitReason: " + exitReason);
+ // If exit reason is LOW_MEMORY_KILLER
+ // delay the mTryToRebindRunnable for 10s
+ if (exitReason == ApplicationExitInfo.REASON_LOW_MEMORY) {
+ if (isRunningOnLowMemory()) {
+ Slog.i(TAG, "Rebind is delayed due to lmk");
+ mContext.getMainThreadHandler().postDelayed(mTryToRebindRunnable,
+ LMK_RECONNECT_DELAY_MS);
+ mLmkLimitRebindRetries = LMK_RECONNECT_REBIND_RETRIES;
+ } else {
+ if (mLmkLimitRebindRetries <= 0) {
+ Slog.w(TAG, "Reverting to built-in wallpaper due to lmk!");
+ clearWallpaperLocked(true, FLAG_SYSTEM, mWallpaper.userId,
+ null);
+ mLmkLimitRebindRetries = LMK_RECONNECT_REBIND_RETRIES;
+ return;
+ }
+ mLmkLimitRebindRetries--;
+ mContext.getMainThreadHandler().postDelayed(mTryToRebindRunnable,
+ LMK_RECONNECT_DELAY_MS);
+ }
} else {
- mWallpaper.lastDiedTime = SystemClock.uptimeMillis();
- tryToRebind();
+ // There is a race condition which causes
+ // {@link #mWallpaper.wallpaperUpdating} to be false even if it is
+ // currently updating since the broadcast notifying us is async.
+ // This race is overcome by the general rule that we only reset the
+ // wallpaper if its service was shut down twice
+ // during {@link #MIN_WALLPAPER_CRASH_TIME} millis.
+ if (mWallpaper.lastDiedTime != 0
+ && mWallpaper.lastDiedTime + MIN_WALLPAPER_CRASH_TIME
+ > SystemClock.uptimeMillis()) {
+ Slog.w(TAG, "Reverting to built-in wallpaper!");
+ clearWallpaperLocked(true, FLAG_SYSTEM, mWallpaper.userId, null);
+ } else {
+ mWallpaper.lastDiedTime = SystemClock.uptimeMillis();
+ tryToRebind();
+ }
}
}
} else {
@@ -1472,6 +1509,14 @@
}
};
+ private boolean isRunningOnLowMemory() {
+ ActivityManager.MemoryInfo memoryInfo = new ActivityManager.MemoryInfo();
+ mActivityManager.getMemoryInfo(memoryInfo);
+ double availableMBsInPercentage = memoryInfo.availMem / (double)memoryInfo.totalMem *
+ 100.0;
+ return availableMBsInPercentage < LMK_LOW_THRESHOLD_MEMORY_PERCENTAGE;
+ }
+
/**
* Called by a live wallpaper if its colors have changed.
* @param primaryColors representation of wallpaper primary colors
diff --git a/services/core/java/com/android/server/webkit/OWNERS b/services/core/java/com/android/server/webkit/OWNERS
index 00e540a..e7fd7a5 100644
--- a/services/core/java/com/android/server/webkit/OWNERS
+++ b/services/core/java/com/android/server/webkit/OWNERS
@@ -1,3 +1,3 @@
-changwan@google.com
-tobiasjs@google.com
+# Bug component: 76427
+ntfschr@google.com
torne@google.com
diff --git a/services/tests/servicestests/src/com/android/server/accessibility/magnification/WindowMagnificationManagerTest.java b/services/tests/servicestests/src/com/android/server/accessibility/magnification/WindowMagnificationManagerTest.java
index 25ad2be..edb4eca 100644
--- a/services/tests/servicestests/src/com/android/server/accessibility/magnification/WindowMagnificationManagerTest.java
+++ b/services/tests/servicestests/src/com/android/server/accessibility/magnification/WindowMagnificationManagerTest.java
@@ -66,6 +66,7 @@
import com.android.server.statusbar.StatusBarManagerInternal;
import org.junit.Before;
+import org.junit.Ignore;
import org.junit.Test;
import org.mockito.Mock;
import org.mockito.Mockito;
@@ -294,6 +295,7 @@
MagnificationScaleProvider.MAX_SCALE);
}
+ @Ignore("b/278816260: We could refer to b/182561174#comment4 for solution.")
@Test
public void logTrackingTypingFocus_processScroll_logDuration() {
WindowMagnificationManager spyWindowMagnificationManager = spy(mWindowMagnificationManager);
diff --git a/services/tests/servicestests/src/com/android/server/webkit/OWNERS b/services/tests/servicestests/src/com/android/server/webkit/OWNERS
index 00e540a..e7fd7a5 100644
--- a/services/tests/servicestests/src/com/android/server/webkit/OWNERS
+++ b/services/tests/servicestests/src/com/android/server/webkit/OWNERS
@@ -1,3 +1,3 @@
-changwan@google.com
-tobiasjs@google.com
+# Bug component: 76427
+ntfschr@google.com
torne@google.com