diff options
| author | Tianjie Xu <xunchang@google.com> | 2016-05-13 12:30:29 -0700 |
|---|---|---|
| committer | Tianjie Xu <xunchang@google.com> | 2016-05-24 13:00:30 -0700 |
| commit | dcd3644f224da72ec95c590394ed656915bba481 (patch) | |
| tree | 1659fa358d8357e7d0b4d0121cb870301fdbf329 /core/java | |
| parent | 0f6363e8b3b091508181ea6cef5f5f87a4f75016 (diff) | |
Report OTA time statistics
Read time and I/O for OTA update from last_install, and report the
statistics using MetricsLogger.histogram.
Bug: 28658632
Change-Id: I7fd06a82cbabd346d6d44f81ebad08f6baf4b8d0
Diffstat (limited to 'core/java')
| -rw-r--r-- | core/java/android/os/RecoverySystem.java | 62 | ||||
| -rw-r--r-- | core/java/com/android/server/BootReceiver.java | 2 |
2 files changed, 62 insertions, 2 deletions
diff --git a/core/java/android/os/RecoverySystem.java b/core/java/android/os/RecoverySystem.java index 403e06ca8553..4abbf0efc81d 100644 --- a/core/java/android/os/RecoverySystem.java +++ b/core/java/android/os/RecoverySystem.java @@ -25,8 +25,10 @@ import android.text.TextUtils; import android.util.Log; import java.io.ByteArrayInputStream; +import java.io.BufferedReader; import java.io.File; import java.io.FileNotFoundException; +import java.io.FileReader; import java.io.FileWriter; import java.io.IOException; import java.io.InputStream; @@ -45,6 +47,8 @@ import java.util.Locale; import java.util.zip.ZipEntry; import java.util.zip.ZipFile; +import com.android.internal.logging.MetricsLogger; + import sun.security.pkcs.PKCS7; import sun.security.pkcs.SignerInfo; @@ -69,6 +73,7 @@ public class RecoverySystem { /** Used to communicate with recovery. See bootable/recovery/recovery.cpp. */ private static final File RECOVERY_DIR = new File("/cache/recovery"); private static final File LOG_FILE = new File(RECOVERY_DIR, "log"); + private static final File LAST_INSTALL_FILE = new File(RECOVERY_DIR, "last_install"); private static final String LAST_PREFIX = "last_"; /** @@ -682,13 +687,64 @@ public class RecoverySystem { } } + // Read last_install; then report time for update and I/O to tron. + // Only report on the reboots immediately after an OTA update. + private static void parseLastInstallLog(Context context) { + try (BufferedReader in = new BufferedReader(new FileReader(LAST_INSTALL_FILE))) { + String line = null; + int bytesWritten = -1, bytesStashed = -1; + int timeTotal = -1; + while ((line = in.readLine()) != null) { + // Here is an example of lines in last_install: + // ... + // time_total: 101 + // bytes_written_vendor: 51074 + // bytes_stashed_vendor: 200 + int numIndex = line.indexOf(':'); + if (numIndex == -1 || numIndex + 1 >= line.length()) { + continue; + } + String numString = line.substring(numIndex + 1).trim(); + int parsedNum; + try { + parsedNum = Integer.parseInt(numString); + } catch (NumberFormatException ignored) { + Log.e(TAG, "Failed to parse numbers in " + line); + continue; + } + + if (line.startsWith("time")) { + timeTotal = parsedNum; + } else if (line.startsWith("bytes_written")) { + bytesWritten = (bytesWritten == -1) ? parsedNum : bytesWritten + parsedNum; + } else if (line.startsWith("bytes_stashed")) { + bytesStashed = (bytesStashed == -1) ? parsedNum : bytesStashed + parsedNum; + } + } + + // Don't report data to tron if corresponding entry isn't found in last_install. + if (timeTotal != -1) { + MetricsLogger.histogram(context, "ota_time_total", timeTotal); + } + if (bytesWritten != -1) { + MetricsLogger.histogram(context, "ota_bytes_written", bytesWritten); + } + if (bytesStashed != -1) { + MetricsLogger.histogram(context, "ota_bytes_stashed", bytesStashed); + } + + } catch (IOException ignored) { + Log.e(TAG, "Failed to read lines in last_install", ignored); + } + } + /** * Called after booting to process and remove recovery-related files. * @return the log file from recovery, or null if none was found. * * @hide */ - public static String handleAftermath() { + public static String handleAftermath(Context context) { // Record the tail of the LOG_FILE String log = null; try { @@ -699,6 +755,10 @@ public class RecoverySystem { Log.e(TAG, "Error reading recovery log", e); } + if (log != null) { + parseLastInstallLog(context); + } + // Only remove the OTA package if it's partially processed (uncrypt'd). boolean reservePackage = BLOCK_MAP_FILE.exists(); if (!reservePackage && UNCRYPT_PACKAGE_FILE.exists()) { diff --git a/core/java/com/android/server/BootReceiver.java b/core/java/com/android/server/BootReceiver.java index 6d6c1622e5c2..fbc51cdca6c2 100644 --- a/core/java/com/android/server/BootReceiver.java +++ b/core/java/com/android/server/BootReceiver.java @@ -127,7 +127,7 @@ public class BootReceiver extends BroadcastReceiver { .append("\n").toString(); final String bootReason = SystemProperties.get("ro.boot.bootreason", null); - String recovery = RecoverySystem.handleAftermath(); + String recovery = RecoverySystem.handleAftermath(ctx); if (recovery != null && db != null) { db.addText("SYSTEM_RECOVERY_LOG", headers + recovery); } |
