Claw 分析 Perfetto Trace

Perfetto Trace 分析报告

Trace 文件 : trace_file.perfetto-trace
分析时间 : 2026-05-12 12:13
分析工具: trace_processor_shell


1. 执行摘要

指标 结果 评级
掉帧率 18.31% 🔴 严重
锁竞争次数 11 次 🟡 中等
主线程长阻塞 816 次 (>5ms) 🔴 严重
最大单帧耗时 87.8ms 🔴 严重

2. 帧渲染分析

指标 数值
总帧数 590
掉帧数 108
掉帧率 18.31%
平均帧耗时 9.88ms
最大帧耗时 87.8ms

60fps 标准下,帧耗时超过 16.67ms 即视为掉帧。当前掉帧率 18.31%,用户体验会有明显卡顿感。


3. 锁竞争分析

3.1 总体分布

指标 数值
锁竞争次数 11 次
总等待时间 6.67ms
平均等待 0.61ms
最大等待 6.34ms

3.2 严重锁竞争详情(Top 5)

等待时间 持有者 阻塞位置
6.34ms Binder:585_5 PowerManagerService.acquireWakeLockInternal
0.13ms InputDispatcher Message.recycleUnchecked
0.10ms Binder:585_5 MessageQueue.enqueueMessage
0.04ms Binder:585_5 MessageQueue.enqueueMessage
0.03ms RenderThread MessageQueue.nativeWake

3.3 主线程锁竞争

等待时间 持有者 阻塞位置
0.13ms InputDispatcher Message.recycleUnchecked
0.03ms RenderThread MessageQueue.nativeWake
0.01ms RenderThread MessageQueue.enqueueMessage
0.005ms Binder:585_5 WindowManagerService.addWindow
0.001ms InputDispatcher MessageQueue.enqueueMessage

关键发现: 主线程多次被 RenderThread 和系统 Binder 线程阻塞,主要发生在 MessageQueue 操作上。


4. 主线程耗时分析(Top 10)

操作 次数 平均耗时 最大耗时 总耗时
animator 15 101.16ms 134.78ms 1517.41ms
traversal 77 11.41ms 69.99ms 878.69ms
draw 75 11.00ms 69.95ms 825.05ms
animator:scaleX 1 350.60ms 350.60ms 350.60ms
animator:scaleY 1 350.56ms 350.56ms 350.56ms
binder reply 51 5.97ms 21.12ms 304.64ms
HIDL::IComposerClient::executeCommands 49 6.08ms 21.09ms 298.07ms
rcCompose encode 40 6.61ms 20.49ms 264.28ms

关键发现:

  • animator:scaleX/Y 单次耗时 350ms+,严重阻塞主线程
  • animator 操作平均 101ms,远超 16.67ms 帧预算

5. ANR 风险分析

指标 数值
长阻塞次数 (>5ms) 816 次
最短阻塞 5.09ms
平均阻塞 18.25ms
最大阻塞 350.60ms

风险等级 : 🔴 高

存在大量主线程阻塞事件,最大阻塞达 350ms,接近 ANR 阈值(5秒)。


6. CPU 调度分析(Runnable 等待 Top 5)

线程 等待次数 平均等待 最大等待 总等待
AudioOut_D 1313 0.12ms 14.18ms 153.28ms
HwBinder:347_3 1338 0.11ms 11.25ms 145.84ms
RenderThread 875 0.14ms 12.68ms 122.72ms
surfaceflinger 1381 0.08ms 30.48ms 113.32ms
kworker/1:2 117 0.91ms 51.49ms 106.07ms

7. 根因总结

主要问题

  1. 动画性能问题 (最严重)

    • animator:scaleX/Y 单次执行 350ms+
    • 属性动画在主线程执行耗时操作
  2. 掉帧严重

    • 掉帧率 18.31%,远超健康标准 (<5%)
    • 最大单帧 87.8ms,是标准 16.67ms 的 5 倍
  3. 主线程阻塞

    • 816 次长阻塞事件
    • 被 RenderThread 和 Binder 线程频繁阻塞
  4. 锁竞争

    • MessageQueue 锁竞争频繁
    • PowerManagerService 锁单次阻塞 6.34ms

8. 优化建议

立即执行

markdown 复制代码
1. 动画优化
   ├── 使用 ObjectAnimator.setDuration() 控制时长
   ├── 复杂动画使用 RenderThread (硬件加速)
   └── 避免在动画回调中执行耗时操作

2. 减少主线程阻塞
   ├── 将 scaleX/scaleY 动画移到子线程计算
   ├── 使用 Choreographer.postFrameCallback 替代频繁 post
   └── 减少 Binder 同步调用,改用异步

中期优化

markdown 复制代码
3. 布局优化
   ├── 减少 View 层级,降低 traversal 耗时
   ├── 使用 ConstraintLayout 替代嵌套布局
   └── 避免在 onDraw 中创建对象

4. 锁优化
   ├── 减少跨线程 MessageQueue 操作
   ├── 使用 HandlerThread 隔离耗时消息
   └── 避免在动画期间触发 WakeLock 申请

9. 关键 SQL 查询

sql 复制代码
-- 查询掉帧详情
SELECT * FROM actual_frame_timeline_slice 
WHERE dur > 16666666 ORDER BY dur DESC;

-- 查询主线程长阻塞
SELECT * FROM __intrinsic_slice s
JOIN thread t ON s.track_id = t.utid
WHERE t.is_main_thread = 1 AND s.dur > 50000000;

-- 查询锁竞争
SELECT * FROM __intrinsic_slice 
WHERE name LIKE '%monitor contention%' ORDER BY dur DESC;

报告生成: Perfetto Trace Processor

相关推荐
小成很成9 小时前
mysql 8.0.21 升级 mysql 8.0.45(经过生产环境验证)
android·mysql·adb
虎王物联13 小时前
PHP实现MQTT消息处理:物联网设备数据接收与指令下发
android·物联网·php
我命由我1234513 小时前
Android 开发 - 获取当前设备屏幕的旋转角度
android·java·java-ee·android studio·android jetpack·android-studio·android runtime
程序员-Benothing15 小时前
MySQL 索引下推是什么?——深入理解 ICP 原理与实践
android·数据库·mysql
怀化纱厂球迷15 小时前
百度地图--android接入百度地图导航
android
AFinalStone16 小时前
Android 7系统无障碍服务(四)AccessibilityEvent 的产生与投递
android·无障碍服务
智购科技无人售货机工厂16 小时前
2026自动售货机热敏打印模块集成:从串口驱动到小票自动裁切的工程实践~YH
android·stm32·单片机·嵌入式硬件·系统架构
A133455517 小时前
苹果安卓手机播放器推荐:2026无广告4K怎么选
android·智能手机
hunterandroid18 小时前
ContentProvider 跨进程数据共享实战
android·前端