Merge "Add a flag to enable/disable/configure LatencyTracker"
This commit is contained in:
committed by
Android (Google) Code Review
commit
64ef4de9ba
@@ -14591,6 +14591,19 @@ public final class Settings {
|
||||
*/
|
||||
public static final String MAXIMUM_OBSCURING_OPACITY_FOR_TOUCH =
|
||||
"maximum_obscuring_opacity_for_touch";
|
||||
|
||||
/**
|
||||
* LatencyTracker settings.
|
||||
*
|
||||
* The following strings are supported as keys:
|
||||
* <pre>
|
||||
* enabled (boolean)
|
||||
* sampling_interval (int)
|
||||
* </pre>
|
||||
*
|
||||
* @hide
|
||||
*/
|
||||
public static final String LATENCY_TRACKER = "latency_tracker";
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -15,14 +15,22 @@
|
||||
package com.android.internal.util;
|
||||
|
||||
import android.content.Context;
|
||||
import android.database.ContentObserver;
|
||||
import android.net.Uri;
|
||||
import android.os.Build;
|
||||
import android.os.SystemClock;
|
||||
import android.os.Trace;
|
||||
import android.os.UserHandle;
|
||||
import android.provider.Settings;
|
||||
import android.util.EventLog;
|
||||
import android.util.KeyValueListParser;
|
||||
import android.util.Log;
|
||||
import android.util.SparseLongArray;
|
||||
|
||||
import com.android.internal.logging.EventLogTags;
|
||||
import com.android.internal.os.BackgroundThread;
|
||||
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
|
||||
/**
|
||||
* Class to track various latencies in SystemUI. It then writes the latency to statsd and also
|
||||
@@ -34,6 +42,12 @@ import com.android.internal.logging.EventLogTags;
|
||||
*/
|
||||
public class LatencyTracker {
|
||||
private static final String TAG = "LatencyTracker";
|
||||
private static final String SETTINGS_ENABLED_KEY = "enabled";
|
||||
private static final String SETTINGS_SAMPLING_INTERVAL_KEY = "sampling_interval";
|
||||
/** Default to being enabled on debug builds. */
|
||||
private static final boolean DEFAULT_ENABLED = Build.IS_DEBUGGABLE;
|
||||
/** Default to collecting data for 1/5 of all actions (randomly sampled). */
|
||||
private static final int DEFAULT_SAMPLING_INTERVAL = 5;
|
||||
|
||||
/**
|
||||
* Time it takes until the first frame of the notification panel to be displayed while expanding
|
||||
@@ -76,7 +90,7 @@ public class LatencyTracker {
|
||||
*/
|
||||
public static final int ACTION_FACE_WAKE_AND_UNLOCK = 7;
|
||||
|
||||
private static final String[] NAMES = new String[] {
|
||||
private static final String[] NAMES = new String[]{
|
||||
"expand panel",
|
||||
"toggle recents",
|
||||
"fingerprint wake-and-unlock",
|
||||
@@ -84,9 +98,9 @@ public class LatencyTracker {
|
||||
"check credential unlocked",
|
||||
"turn on screen",
|
||||
"rotate the screen",
|
||||
"face wake-and-unlock" };
|
||||
"face wake-and-unlock"};
|
||||
|
||||
private static final int[] STATSD_ACTION = new int[] {
|
||||
private static final int[] STATSD_ACTION = new int[]{
|
||||
FrameworkStatsLog.UIACTION_LATENCY_REPORTED__ACTION__ACTION_EXPAND_PANEL,
|
||||
FrameworkStatsLog.UIACTION_LATENCY_REPORTED__ACTION__ACTION_TOGGLE_RECENTS,
|
||||
FrameworkStatsLog.UIACTION_LATENCY_REPORTED__ACTION__ACTION_FINGERPRINT_WAKE_AND_UNLOCK,
|
||||
@@ -100,20 +114,59 @@ public class LatencyTracker {
|
||||
private static LatencyTracker sLatencyTracker;
|
||||
|
||||
private final SparseLongArray mStartRtc = new SparseLongArray();
|
||||
private final Context mContext;
|
||||
private volatile int mSamplingInterval;
|
||||
private volatile boolean mEnabled;
|
||||
|
||||
public static LatencyTracker getInstance(Context context) {
|
||||
if (sLatencyTracker == null) {
|
||||
sLatencyTracker = new LatencyTracker();
|
||||
synchronized (LatencyTracker.class) {
|
||||
if (sLatencyTracker == null) {
|
||||
sLatencyTracker = new LatencyTracker(context);
|
||||
}
|
||||
}
|
||||
}
|
||||
return sLatencyTracker;
|
||||
}
|
||||
|
||||
public LatencyTracker(Context context) {
|
||||
mContext = context;
|
||||
mEnabled = DEFAULT_ENABLED;
|
||||
mSamplingInterval = DEFAULT_SAMPLING_INTERVAL;
|
||||
|
||||
// Post initialization to the background in case we're running on the main thread.
|
||||
BackgroundThread.getHandler().post(this::registerSettingsObserver);
|
||||
BackgroundThread.getHandler().post(this::readSettings);
|
||||
}
|
||||
|
||||
private void registerSettingsObserver() {
|
||||
Uri settingsUri = Settings.Global.getUriFor(Settings.Global.LATENCY_TRACKER);
|
||||
mContext.getContentResolver().registerContentObserver(
|
||||
settingsUri, false, new SettingsObserver(this), UserHandle.myUserId());
|
||||
}
|
||||
|
||||
private void readSettings() {
|
||||
KeyValueListParser parser = new KeyValueListParser(',');
|
||||
String settingsValue = Settings.Global.getString(mContext.getContentResolver(),
|
||||
Settings.Global.LATENCY_TRACKER);
|
||||
|
||||
try {
|
||||
parser.setString(settingsValue);
|
||||
mSamplingInterval = parser.getInt(SETTINGS_SAMPLING_INTERVAL_KEY,
|
||||
DEFAULT_SAMPLING_INTERVAL);
|
||||
mEnabled = parser.getBoolean(SETTINGS_ENABLED_KEY, DEFAULT_ENABLED);
|
||||
} catch (IllegalArgumentException e) {
|
||||
Log.e(TAG, "Incorrect settings format", e);
|
||||
mEnabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
public static boolean isEnabled(Context ctx) {
|
||||
return getInstance(ctx).isEnabled();
|
||||
}
|
||||
|
||||
public boolean isEnabled() {
|
||||
return Build.IS_DEBUGGABLE;
|
||||
return mEnabled;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -145,19 +198,48 @@ public class LatencyTracker {
|
||||
}
|
||||
mStartRtc.delete(action);
|
||||
Trace.asyncTraceEnd(Trace.TRACE_TAG_APP, NAMES[action], 0);
|
||||
logAction(action, (int)(endRtc - startRtc));
|
||||
logAction(action, (int) (endRtc - startRtc));
|
||||
}
|
||||
|
||||
/**
|
||||
* Logs an action that has started and ended. This needs to be called from the main thread.
|
||||
*
|
||||
* @param action The action to end. One of the ACTION_* values.
|
||||
* @param duration The duration of the action in ms.
|
||||
* @param action The action to end. One of the ACTION_* values.
|
||||
* @param duration The duration of the action in ms.
|
||||
*/
|
||||
public static void logAction(int action, int duration) {
|
||||
public void logAction(int action, int duration) {
|
||||
boolean shouldSample = ThreadLocalRandom.current().nextInt() % mSamplingInterval == 0;
|
||||
logActionDeprecated(action, duration, shouldSample);
|
||||
}
|
||||
|
||||
/**
|
||||
* Logs an action that has started and ended. This needs to be called from the main thread.
|
||||
*
|
||||
* @param action The action to end. One of the ACTION_* values.
|
||||
* @param duration The duration of the action in ms.
|
||||
* @param writeToStatsLog Whether to write the measured latency to FrameworkStatsLog.
|
||||
*/
|
||||
public static void logActionDeprecated(int action, int duration, boolean writeToStatsLog) {
|
||||
Log.i(TAG, "action=" + action + " latency=" + duration);
|
||||
EventLog.writeEvent(EventLogTags.SYSUI_LATENCY, action, duration);
|
||||
FrameworkStatsLog.write(
|
||||
FrameworkStatsLog.UI_ACTION_LATENCY_REPORTED, STATSD_ACTION[action], duration);
|
||||
|
||||
if (writeToStatsLog) {
|
||||
FrameworkStatsLog.write(
|
||||
FrameworkStatsLog.UI_ACTION_LATENCY_REPORTED, STATSD_ACTION[action], duration);
|
||||
}
|
||||
}
|
||||
|
||||
private static class SettingsObserver extends ContentObserver {
|
||||
private final LatencyTracker mThisTracker;
|
||||
|
||||
SettingsObserver(LatencyTracker thisTracker) {
|
||||
super(BackgroundThread.getHandler());
|
||||
mThisTracker = thisTracker;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onChange(boolean selfChange, Uri uri, int userId) {
|
||||
mThisTracker.readSettings();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -314,6 +314,7 @@ public class SettingsBackupTest {
|
||||
Settings.Global.KERNEL_CPU_THREAD_READER,
|
||||
Settings.Global.LANG_ID_UPDATE_CONTENT_URL,
|
||||
Settings.Global.LANG_ID_UPDATE_METADATA_URL,
|
||||
Settings.Global.LATENCY_TRACKER,
|
||||
Settings.Global.LOCATION_BACKGROUND_THROTTLE_INTERVAL_MS,
|
||||
Settings.Global.LOCATION_BACKGROUND_THROTTLE_PROXIMITY_ALERT_INTERVAL_MS,
|
||||
Settings.Global.LOCATION_BACKGROUND_THROTTLE_PACKAGE_WHITELIST,
|
||||
|
||||
@@ -28,7 +28,18 @@ public class LatencyTrackerCompat {
|
||||
return LatencyTracker.isEnabled(context);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see LatencyTracker
|
||||
* @deprecated Please use {@link LatencyTrackerCompat#logToggleRecents(Context, int)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void logToggleRecents(int duration) {
|
||||
LatencyTracker.logAction(LatencyTracker.ACTION_TOGGLE_RECENTS, duration);
|
||||
LatencyTracker.logActionDeprecated(LatencyTracker.ACTION_TOGGLE_RECENTS, duration, false);
|
||||
}
|
||||
|
||||
/** @see LatencyTracker */
|
||||
public static void logToggleRecents(Context context, int duration) {
|
||||
LatencyTracker.getInstance(context).logAction(LatencyTracker.ACTION_TOGGLE_RECENTS,
|
||||
duration);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user