Android Performance

Android Systrace Responsiveness in Action 3 - Extended Knowledge on Responsiv...

Word count: 1.7kReading time: 10 min
2021/09/13
loading

When discussing Android performance, Jank, Responsiveness, and ANR are usually grouped together because their causes are similar. They are simply categorized based on severity: Jank, Slow Response, and ANR. We can define “Broad Jank” to include all three. If a user reports that a phone or App is “stuttering,” they are likely referring to Broad Jank, and we must identify which specific issue is occurring.

If it’s stuttering during animation or list scrolling, we define it as Narrow Jank (referred to as Jank). If it’s slow app startup, slow screen wake-up, or slow scene switching, we define it as Slow Responsiveness (referred to as Slow). If it’s an ANR, it’s an Application Not Responding issue. Each situation requires different analysis and resolution methods.

Furthermore, within Apps or manufacturers, Jank, Responsiveness, and ANR have individual metrics like Frame Drop Rate, Startup Speed, and ANR Rate. Mastering the analysis and optimization of these issues is crucial for developers.

This is the third article in the Responsiveness series, focusing on extended knowledge when using Systrace to analyze app responsiveness, including startup speed testing, log interpretation, state analysis, and third-party startup libraries.

Table of Contents

If you are not familiar with the basic use of Systrace (Perfetto), please catch up on the Systrace Basics Series first. This article assumes you are already familiar with using Systrace (Perfetto).

Systrace Series Articles:

  1. Introduction to Systrace
  2. Systrace Basics - Prerequisites for Systrace
  3. Systrace Basics - Why 60 fps?
  4. Android Systrace Basics - SystemServer Explained
  5. Systrace Basics - SurfaceFlinger Explained
  6. Systrace Basics - Input Explained
  7. Systrace Basics - Vsync Explained
  8. Systrace Basics - Vsync-App: Detailed Explanation of Choreographer-Based Rendering Mechanism
  9. Systrace Basics - MainThread and RenderThread Explained
  10. Systrace Basics - Binder and Lock Contention Explained
  11. Systrace Basics - Triple Buffer Explained
  12. Systrace Basics - CPU Info Explained
  13. Systrace Smoothness in Action 1: Understanding Jank Principles
  14. Systrace Smoothness in Action 2: Case Analysis - MIUI Launcher Scroll Jank Analysis
  15. Systrace Smoothness in Action 3: FAQs During Jank Analysis
  16. Systrace Responsiveness in Action 1: Understanding Responsiveness Principles
  17. Systrace Responsiveness in Action 2: Responsiveness Analysis - Using App Startup as an Example
  18. Systrace Responsiveness in Action 3: Extended Knowledge on Responsiveness
  19. Systrace Thread CPU State Analysis Tips - Runnable
  20. Systrace Thread CPU State Analysis Tips - Running
  21. Systrace Thread CPU State Analysis Tips - Sleep and Uninterruptible Sleep

1. Interpretation of the Three Process States in Systrace

In Systrace, a process task typically exhibits three states: Sleep, Running, and Runnable. These are color-coded at the top of the task trace:

  1. Green: Running
  2. Blue: Runnable
  3. White: Sleep

1.1 Analyzing the Sleep State

White (Sleep) segments are either active or passive.

  1. Active Sleep (e.g., nativePoll): The app has no more messages to process and is sleeping while waiting for a new Message. This is normal and usually ignored (e.g., segments between frames).
  2. Passive Sleep: Triggered by user code sleep() or Binder communication with other processes. This is common and critical for performance analysis.

As shown below, long sleep periods during startup often correlate with Binder communication. Frequent Binder calls prolong response times.

Binder Sleep Trace

You can click the binder transaction marker at the bottom of the task to view details:

Binder Transaction Detail

If Binder info is missing but the task is woken by another thread, check the Wakeup info to find the dependency.

Wakeup Info Trace

Zooming into the Runnable marker from the previous image:

Waking Thread Detail

1.2 Analyzing the Running State

The Running state indicates the task is currently executing on a CPU core. If a Running segment is unexpectedly long, consider:

  1. Increased App logic/complexity.
  2. Core scheduling anomalies (e.g., running on the wrong core).

Running State Trace

Core Scheduling Map

On some Android devices, UI and Render threads are prioritized for Big Cores when the app is in the foreground.

1.3 Analyzing the Runnable State

A task must transition from Sleep to Runnable before entering the Running state:

State Transition Diagram

Systrace representation:

Runnable Transition Trace

Normally, a task enters Running almost immediately after becoming Runnable. In a congested system with saturated CPUs, tasks must wait in Runnable for an available core.

If startup shows heavy Runnable segments, check the overall system load.

2. Using TraceView for Responsiveness Analysis

“TraceView” refers to the CPU profiling visualization within the Android Studio Profiler.

AS CPU Profiler

2.1 Capturing TraceView During Startup

Use the following command to profile a cold start (replace package/activity names with your own):

1
adb shell am start -n com.aboback.wanandroidjetpack/.splash.SplashActivity --start-profiler /data/local/tmp/traceview.trace --sampling 1 && sleep 10 && adb shell am profile stop com.aboback.wanandroidjetpack && adb pull /data/local/tmp/traceview.trace .

Or execute steps individually:

1
2
3
4
5
6
7
8
9
10
# 1. Start App with 1ms sampling
adb shell am start -n com.aboback.wanandroidjetpack/.splash.SplashActivity --start-profiler /data/local/tmp/traceview.trace --sampling 1

# 2. End profiling after full load
adb shell am profile stop com.aboback.wanandroidjetpack

# 3. Pull the trace
adb pull /data/local/tmp/traceview.trace .

# 4. Open in Android Studio

2.2 Interpreting TraceView

Green markers denote App functions; yellow markers denote System functions.

Application.onCreate
Application onCreate TraceView

Activity.onCreate
Activity onCreate TraceView

doFrame
doFrame TraceView

WebView Initialization
WebView Init TraceView

2.3 Pros and Cons

TraceView uses high-frequency sampling, introducing significant performance overhead. Consequently, the execution times of individual methods are NOT accurate and should not be used as a real-time reference. Use it exclusively to visualize call stacks and pair it with Systrace for timing data.

3. Using SimplePerf for Startup Speed Analysis

SimplePerf captures both Java and Native stack traces.

To profile com.aboback.wanandroidjetpack (refer to SimplePerf Documentation):

1
python app_profiler.py -p com.aboback.wanandroidjetpack

Manually launch and then terminate the app:

1
2
3
4
5
6
$ python app_profiler.py -p com.aboback.wanandroidjetpack  
INFO:root:prepare profiling
INFO:root:start profiling1
INFO:root:run adb cmd: ['adb', 'shell', '/data/local/tmp/simpleperf', 'record', '-o', '/data/local/tmp/perf.data', '-e task-clock:u -f 1000 -g --duration 10', '--log', 'info', '--app', 'com.aboback.wanandroidjetpack']
simpleperf I environment.cpp:601] Waiting for process of app com.aboback.wanandroidjetpack
simpleperf I environment.cpp:593] Got process 32112 for package com.aboback.wanandroidjetpack

Generate the HTML report:

1
python report_html.py

Result:
SimplePerf Report Example

SimplePerf captures both Java and Native stacks. For advanced usage, see:

4. Locating Other Component Startups in Systrace

4.1 Service Startup

1
2
3
4
5
6
7
8
9
public final void scheduleCreateService(...) {
...
sendMessage(H.CREATE_SERVICE, s);
}

public final void scheduleBindService(...) {
...
sendMessage(H.BIND_SERVICE, s);
}

Service operations are sent as Messages to the H Handler. They don’t execute immediately but are processed in the order defined by the MessageQueue.

Service Message Trace

Execution typically follows the first frame (after the queue catches up). Subsequent messages represent custom App logic, Service starts, and BroadcastReceivers.

Service Process Trace

4.2 Custom Messages

Custom App Messages in Systrace:

Custom Message Trace

4.3 Service Startup Visualized

Service Trace Marker

4.4 BroadcastReceiver Execution

Receiver execution in Systrace:

Receiver Trace Marker

Dynamic registration (usually in lifecycle functions) executes where registered.

Receiver Registration Trace

4.5 ContentProvider Startup Timing

Provider Init Trace 1

Provider Init Trace 2

5. Can AppStartup Optimize Startup Speed?

Third-Party Library Initialization

Many libraries require Application context for initialization. Some libraries initialize “stealthily” using a ContentProvider. By defining a provider and calling initialization in its onCreate, the library ensures it’s ready without explicit developer action, as the system calls onCreate for all registered providers during App startup.

Facebook, Firebase, and WorkManager commonly use this trick.

Provider initialization timing:

Provider Init Flow

However, this leads to:

  1. Too many ContentProviders during startup.
  2. Loss of control over initialization timing for developers.
  3. Inability to manage library dependencies.

AppStartup Library

Google introduced AppStartup to address this:

  • Shared ContentProvider: Consolidates initialization into a single provider.
  • Explicit Sequence: Defines exact initialization order.
  • Lazy Loading: Optionally removes automatic initialization to manually trigger it later, optimizing startup speed.

Measurements show AppStartup doesn’t significantly speed up startup unless you have many (e.g., 50+) ContentProviders.

If an SDK’s provider slows you down, consider removing it from the merge and manually initializing it:

1
2
3
4
5
6
7
8
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
<meta-data android:name="com.example.ExampleLoggerInitializer"
tools:node="remove" />
</provider>

Summary

  1. Purpose: Solves “ContentProvider Bloat” from multiple libraries.
  2. Benefit: Minor. Usually $< 20$ms even with 20-30 libraries.
  3. Best Use Scenarios:
    • APK has excessive ContentProviders.
    • Individual Providers are heavy but not critical for startup (can be lazy-loaded).
    • Deep control over initialization order is required.

Action Items for App Developers:

  1. Check the merged manifest for ContentProvider count ( AS -> src\main\AndroidManifest.xml -> Merged Manifest tab).
  2. Measure initialization time for each.
  3. Identify lazy-loading candidates.
  4. Integrate AppStartup if needed.

6. Using IdleHandler in App Startup Scenarios

IdleHandler executes tasks when the MessageQueue is idle.

IdleHandler Timing in Systrace

Usage scenarios:

  1. Lazy Loading: Add an IdleHandler in Activity.onCreate to run non-critical tasks once the queue is clear.

    IdleHandler Lazy Load Example

  2. Accurate Startup Metrics: Call activity.reportFullyDrawn() once the first page list/content is stable.

    reportFullyDrawn Code Example

    Systrace reflects this:

    reportFullyDrawn Trace Marker

    This records a meaningful cold start time:

    Accurate Startup Metrics

Some system features also rely on FullyDrawn reports; they are highly recommended.

Series Articles

  1. Systrace Responsiveness in Action 1: Understanding Responsiveness Principles
  2. Systrace Responsiveness in Action 2: Responsiveness Analysis - Using App Startup as an Example
  3. Systrace Responsiveness in Action 3: Extended Knowledge on Responsiveness
  4. Link to Systrace Basics Series

References

  1. Analysis of Android App Startup Flow
  2. Investigation: Can App Startup Really Reduce Startup Time?
  3. Jetpack App Startup Explained
  4. App Startup Official Guide
  5. Complete Record of Android App Startup Optimization
  6. Android Application Profiling

About Me && Blog

Below is my personal intro and related links. I look forward to exchanging ideas with fellow professionals. “When three walk together, one can always be my teacher!”

  1. Blogger Intro: Includes personal WeChat and WeChat group links.
  2. Blog Content Navigation: A guide for my blog content.
  3. Curated Excellent Blog Articles - Android Performance Optimization Must-Knows: Welcome to recommend projects/articles.
  4. Android Performance Optimization Knowledge Planet: Welcome to join and thank you for your support~

One walks faster alone, but a group walks further together.

Scan WeChat QR Code

CATALOG
  1. 1. Table of Contents
  • 1. Interpretation of the Three Process States in Systrace
    1. 1. 1.1 Analyzing the Sleep State
    2. 2. 1.2 Analyzing the Running State
    3. 3. 1.3 Analyzing the Runnable State
  • 2. Using TraceView for Responsiveness Analysis
    1. 1. 2.1 Capturing TraceView During Startup
    2. 2. 2.2 Interpreting TraceView
    3. 3. 2.3 Pros and Cons
  • 3. Using SimplePerf for Startup Speed Analysis
  • 4. Locating Other Component Startups in Systrace
    1. 1. 4.1 Service Startup
    2. 2. 4.2 Custom Messages
    3. 3. 4.3 Service Startup Visualized
    4. 4. 4.4 BroadcastReceiver Execution
    5. 5. 4.5 ContentProvider Startup Timing
  • 5. Can AppStartup Optimize Startup Speed?
    1. 0.0.1. Third-Party Library Initialization
    2. 0.0.2. AppStartup Library
  • 0.1. Summary
    1. 0.1.1. Action Items for App Developers:
  • 6. Using IdleHandler in App Startup Scenarios
  • Series Articles
  • References
  • About Me && Blog