# Android 设备卡顿诊断报告(系统层+应用层综合优化版) **诊断时间:2026-04-18** **应用代码路径:F:\code\git_project\xcmg\xcmg** **系统代码路径:S:\znzc\034_xcmg\x9hp_xcmg\androd10_x9hp_ptg4.3p3\android10** --- ## 一、诊断数据汇总 ### 设备信息 | 项目 | 值 | |------|-----| | 设备型号 | x9 for arm64 (车载设备) | | Android 版本 | 10 (API 29) | | CPU | 8核 arm64, 1.6GHz | | 总内存 | 4,383 MB | | Swap | 1,753 MB | ### 系统状态诊断 | 指标 | 数值 | 状态 | 说明 | |------|------|------|------| | **Load Average** | **12.7** | **🔴 严重过载** | 8核CPU,正常应<8,当前超载1.6倍 | | 可用内存 | 584 MB (13%) | 🔴 紧张 | 低于安全阈值20% | | IRQ/SIRQ | 13% | 🔴 过高 | 中断处理负担重 | | surfaceflinger CPU | 18% | 🟡 偏高 | 图形合成压力大 | ### 高资源占用进程 | 进程 | CPU | 内存 | 问题 | |------|-----|------|------| | **com.yaxon.avm** | **89%** | 255MB | AVM全景监控CPU异常 | | **com.txzing.voiceassistant** | **76%** | 563MB | 语音助手CPU+内存双高 | | surfaceflinger | 18% | 51MB | 渲染合成压力 | --- ## 二、问题根因分析 ### 🔴 根因链 ``` ┌─────────────────────────────────────────────────────────────────┐ │ 卡顿根本原因链 │ ├─────────────────────────────────────────────────────────────────┤ │ │ │ [应用层问题] │ │ ├─ AVM无限激活重试 + Native密集调用 → 89% CPU │ │ ├─ TXZ语音助手WebSocket失败无限重试 → 76% CPU + 563MB │ │ └─ YX_Voice无重试限制 → 持续触发连接 │ │ │ │ ║ │ │ ║ 累计占用165%+ CPU │ │ ▼ │ │ [系统层压力] │ │ ├─ Load Average 12.7 → 任务队列过长 │ │ ├─ 内存可用13% → LMKD频繁杀进程 │ │ ├─ surfaceflinger无法及时合成 → 18% CPU │ │ └─ IRQ/SIRQ 13% → 硬件中断处理慢 │ │ │ │ ║ │ │ ▼ │ │ [渲染管线阻塞] │ │ ├─ Launcher主线程等待CPU → 88.89%卡顿帧 │ │ ├─ SystemUI主线程阻塞 → 302帧跳帧 │ │ └─ VSync丢失 → 渲染节奏紊乱 │ │ │ └─────────────────────────────────────────────────────────────────┘ ``` --- ## 三、系统层代码分析与优化 ### 3.1 ProcessList.java - OOM配置分析 **文件位置:** `frameworks/base/services/core/java/com/android/server/am/ProcessList.java` ```java // 第285-298行:OOM adj级别定义 private final int[] mOomAdj = new int[] { FOREGROUND_APP_ADJ, VISIBLE_APP_ADJ, PERCEPTIBLE_APP_ADJ, PERCEPTIBLE_LOW_APP_ADJ, CACHED_APP_MIN_ADJ, CACHED_APP_LMK_FIRST_ADJ }; // 第291-294行:低内存设备的minfree配置(KB) private final int[] mOomMinFreeLow = new int[] { 12288, 18432, 24576, 36864, 43008, 49152 // 12MB, 18MB, 24MB, 36MB, 42MB, 48MB }; // 第297-299行:高内存设备的minfree配置(KB) private final int[] mOomMinFreeHigh = new int[] { 73728, 92160, 110592, 129024, 147456, 184320 // 72MB, 90MB, 108MB, 126MB, 144MB, 180MB }; ``` **问题分析:** - 当前设备4.3GB内存,使用的是动态计算的minfree值 - 可用内存仅584MB,触发频繁的进程回收 **优化方案:** ```java // ===== 优化:调整OOM minfree阈值 ===== // 修改 ProcessList.java 第291-299行 // 针对4GB内存车载设备,适当提高阈值避免频繁杀进程 // 原值基于1GB设备设计,对于4GB设备过于激进 private final int[] mOomMinFreeHigh = new int[] { 122880, 153600, 184320, // 120MB, 150MB, 180MB (前台/可见/感知) 245760, 307200, 368640 // 240MB, 300MB, 360MB (缓存级别) }; // 提高约33%,减少频繁杀进程导致的卡顿 ``` --- ### 3.2 ActivityManagerConstants.java - 服务管理优化 **文件位置:** `frameworks/base/services/core/java/com/android/server/am/ActivityManagerConstants.java` ```java // 第81行:最大缓存进程数 private static final int DEFAULT_MAX_CACHED_PROCESSES = 8; // 第103行:服务最大不活跃时间 private static final long DEFAULT_MAX_SERVICE_INACTIVITY = 30*60*1000; // 30分钟 // 第107行:绑定服务崩溃最大重试 private static final int DEFAULT_BOUND_SERVICE_CRASH_MAX_RETRY = 16; ``` **问题分析:** - MAX_CACHED_PROCESSES=8 对于车载系统偏少 - 服务重试次数过多可能导致资源浪费 **优化方案:** ```java // ===== 优化1:增加缓存进程数 ===== // 车载系统有更多常驻服务,适当增加缓存容量 private static final int DEFAULT_MAX_CACHED_PROCESSES = 12; // 原8改为12 // ===== 优化2:减少服务崩溃重试次数 ===== // 避免崩溃服务反复重启占用资源 private static final int DEFAULT_BOUND_SERVICE_CRASH_MAX_RETRY = 5; // 原16改为5 ``` --- ### 3.3 lmkd.c - 低内存杀手配置优化 **文件位置:** `system/core/lmkd/lmkd.c` ```c // 第182-186行:PSI压力阈值配置 static struct psi_threshold psi_thresholds[VMPRESS_LEVEL_COUNT] = { { PSI_SOME, 70 }, // 70ms out of 1sec for partial stall { PSI_SOME, 100 }, // 100ms out of 1sec for partial stall { PSI_FULL, 70 }, // 70ms out of 1sec for complete stall }; ``` **问题分析:** - PSI阈值偏激进,触发过早导致频繁杀进程 **优化方案:** ```c // ===== 优化:调整PSI阈值减少过早触发 ===== // 修改 lmkd.c 第182-186行 static struct psi_threshold psi_thresholds[VMPRESS_LEVEL_COUNT] = { { PSI_SOME, 100 }, // 100ms(原70ms)- 放宽容忍度 { PSI_SOME, 150 }, // 150ms(原100ms) { PSI_FULL, 100 }, // 100ms(原70ms) }; // 减少内存压力误触发,避免频繁杀进程 ``` --- ### 3.4 SurfaceFlinger.cpp - 渲染管线优化 **文件位置:** `frameworks/native/services/surfaceflinger/SurfaceFlinger.cpp` 当前渲染合成占用18% CPU,问题在于: 1. CPU过载导致SurfaceFlinger无法及时获得调度 2. 多图层合成计算量大 **优化方案(Scheduler层面):** **文件位置:** `frameworks/native/services/surfaceflinger/Scheduler/Scheduler.cpp` ```cpp // ===== 优化:提高渲染线程优先级 ===== // 在 Scheduler.cpp 中添加优先级提升 // 第134-150行附近,创建EventThread时提高优先级 std::unique_ptr eventThread = makeEventThread(connectionName, mPrimaryDispSync.get(), phaseOffsetNs, offsetThresholdForNextVsync, std::move(interceptCallback)); // 提高渲染相关线程的调度优先级 // 在EventThread创建后设置: if (eventThread) { // 设置更高的调度优先级,确保渲染及时 eventThread->setSchedPriority(SCHED_PRIORITY_REALTIME); } ``` --- ### 3.5 系统属性配置优化 **建议添加的系统属性(build.prop或通过adb设置):** ```bash # ===== 内存管理优化 ===== # 提高LMKD阈值,减少过早触发 ro.lmk.psi_partial_stall_ms=150 ro.lmk.psi_complete_stall_ms=100 ro.lmk.low=100 ro.lmk.medium=200 ro.lmk.critical=500 # ===== 进程管理优化 ===== # 增加缓存进程数 ro.sys.fw.bg_apps_limit=12 ro.sys.fw.max_cached_processes=12 # ===== 渲染优化 ===== # 提高渲染线程优先级 debug.sf.set_idle_timer_ms=100 debug.sf.enable_gl_backpressure=1 # ===== CPU调度优化 ===== # 降低后台进程对CPU的影响 ro.sys.fw.bg_cpu_percent=10 ``` --- ## 四、应用层代码优化(结合之前分析) ### 4.1 YX_Avm模块优化 **文件位置:** `F:\code\git_project\xcmg\xcmg\YX_Avm\src\main\java\com\android\v4l2camera\V4L2CameraManager.java` ```java // ===== 优化1:添加激活超时机制 ===== // 修改 avmActivatedIfNeed() 方法(第166-181行) private static final long ACTIVATION_TIMEOUT_MS = 30000; // 30秒超时 private final ExecutorService mActivationExecutor = Executors.newSingleThreadExecutor(); public void avmActivatedIfNeed() { if (isAvmActivated) { Log.i(TAG, "avmActivatedIfNeed isAvmActivated -> true"); return; } if (mActivatedThread != null && mActivatedThread.isAlive()) { Log.i(TAG, "avmActivatedIfNeed mActivatedThread is alive"); return; } mActivatedThread = new Thread(() -> { Future future = mActivationExecutor.submit(() -> mV4L2CameraManager.activatedAvmModule()); try { future.get(ACTIVATION_TIMEOUT_MS, TimeUnit.MILLISECONDS); } catch (TimeoutException e) { Log.w(TAG, "AVM activation timeout, cancelling"); future.cancel(true); // 延迟重试,避免立即重试占用CPU mHandler.postDelayed(() -> avmActivatedIfNeed(), 60000); } catch (Exception e) { Log.e(TAG, "AVM activation error", e); } }); mActivatedThread.setName("T_AvmActivated"); mActivatedThread.start(); } // ===== 优化2:图像处理移至子线程 ===== // 修改 saveYuvImageToFrontPng() 等方法(第695-820行) private final ExecutorService mImageProcessExecutor = Executors.newFixedThreadPool(2); private void saveYuvImageToFrontPng(byte[] yuvData, int width, int height) { if (calibDirection != AvmConstant.CalibCameraView.AVM_CALIBRATION_FRONT) { return; } // 异步处理,避免阻塞回调线程 mImageProcessExecutor.execute(() -> { String filePath = AvmConstant.SDCARD_CALIBRATION_PATH; File file = new File(filePath); if (!file.exists()) file.mkdirs(); String temFile = file.getAbsolutePath() + File.separator + "front.jpg"; try { YuvImage image = new YuvImage(yuvData, ImageFormat.NV21, width, height, null); ByteArrayOutputStream baos = new ByteArrayOutputStream(); image.compressToJpeg(new Rect(0, 0, width, height), 100, baos); Bitmap bmp = BitmapFactory.decodeByteArray(baos.toByteArray(), 0, baos.toByteArray().length); FileOutputStream fos = new FileOutputStream(temFile); bmp.compress(Bitmap.CompressFormat.JPEG, 90, fos); // 降低质量减少CPU fos.close(); baos.close(); if (calibraResultCallBack != null) { mHandler.post(() -> calibraResultCallBack.onFrontCapture(temFile)); } } catch (Exception e) { Log.e(TAG, "saveYuvImageToFrontPng error", e); } }); } // ===== 优化3:添加ContentObserver防抖 ===== // 修改 AvmService.java 第160-217行 private ContentObserver mContentObserver = new ContentObserver(null) { private long mLastCallbackTime = 0; private static final long MIN_CALLBACK_INTERVAL = 200; // 200ms最小间隔 @Override public void onChange(boolean selfChange, Uri uri) { super.onChange(selfChange, uri); if (uri == null) return; // 防抖处理 long currentTime = System.currentTimeMillis(); if (currentTime - mLastCallbackTime < MIN_CALLBACK_INTERVAL) { Log.d(TAG, "onChange throttled: " + uri.toString()); return; } mLastCallbackTime = currentTime; // 原有的处理逻辑... } }; ``` --- ### 4.2 YX_Voice模块优化 **文件位置:** `F:\code\git_project\xcmg\xcmg\YX_Voice\src\main\java\com\yaxon\voice\service\VoiceService.java` ```java // ===== 优化:添加连接重试限制 ===== // 修改 VoiceService.java private int mConnectRetryCount = 0; private static final int MAX_CONNECT_RETRY = 3; private static final long[] RETRY_DELAY_MS = {5000, 15000, 60000}; // 5s, 15s, 60s private void initTxz() { try { // 检测网络可用性 if (!isNetworkAvailable()) { Log.w(TAG, "Network not available, delay connect"); scheduleReconnect(10000); return; } // ... 原有的初始化代码 } catch (Throwable e) { Log.e(TAG, "initTxz error", e); scheduleReconnect(RETRY_DELAY_MS[Math.min(mConnectRetryCount, RETRY_DELAY_MS.length - 1)]); } } @Override public void onDisconnected() { Log.d(TAG,"TXZ onDisconnected"); VoiceManager.getInstance().setVoiceBind(false); if (mConnectRetryCount < MAX_CONNECT_RETRY) { long delay = RETRY_DELAY_MS[mConnectRetryCount]; Log.d(TAG, "Schedule reconnect in " + delay + "ms, retry=" + (mConnectRetryCount + 1)); scheduleReconnect(delay); mConnectRetryCount++; } else { Log.w(TAG, "Max retry count reached (" + MAX_CONNECT_RETRY + "), stop reconnecting"); // 网络恢复后再重试 registerNetworkRecoveryListener(); } } @Override public void onConnected() { Log.d(TAG,"TXZ onConnected"); mConnectRetryCount = 0; // 连接成功重置计数 // ... 原有代码 } private void scheduleReconnect(long delayMs) { mHandler.removeCallbacks(mReconnectRunnable); mHandler.postDelayed(mReconnectRunnable, delayMs); } private final Runnable mReconnectRunnable = () -> { if (isNetworkAvailable()) { mConnectRetryCount = 0; initTxz(); } }; private boolean isNetworkAvailable() { ConnectivityManager cm = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE); NetworkInfo activeNetwork = cm.getActiveNetworkInfo(); return activeNetwork != null && activeNetwork.isConnectedOrConnecting(); } ``` --- ### 4.3 TXZ语音助手SDK优化需求 **需联系TXZ技术支持(同舟行科技)提出以下需求:** | 序号 | 问题描述 | 优化要求 | 优先级 | |------|----------|----------|--------| | 1 | WebSocket连接失败后无限重试 | 添加重试次数限制(最多3次) | **P0** | | 2 | 重试间隔固定约3秒 | 添加指数退避(5s→15s→60s) | **P0** | | 3 | 网络不可达时仍重试 | 检测网络状态,不可达时暂停 | **P0** | | 4 | 内存占用563MB过高 | 优化内存使用,减少缓存 | **P1** | | 5 | CPU占用76%异常 | 检查SDK内部循环/定时器 | **P0** | --- ## 五、综合优化方案实施清单 ### 优先级排序 | 优先级 | 层级 | 模块 | 优化内容 | 预期效果 | |--------|------|------|----------|----------| | **P0** | 应用 | TXZ SDK | 重试限制、指数退避 | 释放76% CPU | | **P0** | 应用 | YX_Avm | 激活超时、图像异步 | 降低CPU峰值 | | **P0** | 应用 | YX_Voice | 重试限制、网络检测 | 降低重试频率 | | **P1** | 系统 | lmkd.c | PSI阈值调整 | 减少频繁杀进程 | | **P1** | 系统 | ProcessList | minfree调整 | 增加缓存容量 | | **P1** | 系统 | ActivityManagerConstants | 缓存进程数 | 减少进程重建 | | **P2** | 系统 | Scheduler | 渲染优先级 | 提升UI响应 | | **P2** | 系统 | build.prop | 系统属性 | 全局优化 | --- ### 实施步骤 #### 步骤1:立即生效(无需重新编译系统) ```bash # 通过adb设置临时属性验证效果 adb shell "setprop ro.lmk.psi_partial_stall_ms 150" adb shell "setprop ro.lmk.psi_complete_stall_ms 100" adb shell "setprop ro.sys.fw.bg_apps_limit 12" # 强制停止问题应用 adb shell "am force-stop com.yaxon.avm" adb shell "am force-stop com.txzing.voiceassistant" ``` #### 步骤2:应用层修改(需要重新编译应用) 修改以下文件并重新编译: 1. `YX_Avm/.../V4L2CameraManager.java` 2. `YX_Avm/.../AvmService.java` 3. `YX_Voice/.../VoiceService.java` #### 步骤3:系统层修改(需要重新编译系统) 修改以下文件并重新编译系统镜像: 1. `system/core/lmkd/lmkd.c` - PSI阈值 2. `frameworks/base/services/core/java/com/android/server/am/ProcessList.java` - minfree 3. `frameworks/base/services/core/java/com/android/server/am/ActivityManagerConstants.java` - 缓存配置 4. `device/.../build.prop` - 系统属性 --- ## 六、代码修改文件清单 ### 应用层修改 | 文件路径 | 修改内容 | 状态 | |----------|----------|------| | `YX_Avm/src/.../V4L2CameraManager.java` | 激活超时、图像异步处理 | 待修改 | | `YX_Avm/src/.../AvmService.java` | ContentObserver防抖 | 待修改 | | `YX_Voice/src/.../VoiceService.java` | 连接重试限制、网络检测 | 待修改 | ### 系统层修改 | 文件路径 | 修改内容 | 状态 | |----------|----------|------| | `system/core/lmkd/lmkd.c` | PSI阈值调整 | 待修改 | | `frameworks/base/services/.../ProcessList.java` | minfree阈值调整 | 待修改 | | `frameworks/base/services/.../ActivityManagerConstants.java` | 缓存配置调整 | 待修改 | | `frameworks/native/services/surfaceflinger/Scheduler/Scheduler.cpp` | 渲染优先级 | 待修改 | | `device/.../system.prop` 或 `build.prop` | 系统属性配置 | 待修改 | --- ## 七、验证与监控 ### 优化效果验证命令 ```bash # 检查CPU负载 adb shell "top -n 1 | head -15" # 检查内存状态 adb shell "cat /proc/meminfo | grep -E 'MemTotal|MemAvailable'" # 检查进程杀次数 adb shell "cat /proc/vmstat | grep -i kill" # 检查渲染性能 adb shell "dumpsys gfxinfo com.yaxon.launcher" # 检查LMKD状态 adb shell "logcat -d | grep lmkd | tail -20" ``` ### 持续监控脚本 ```bash # 创建监控脚本 monitor.sh #!/bin/bash while true; do echo "=== $(date) ===" echo "CPU Load:" adb shell "top -n 1 | head -5" echo "Memory:" adb shell "cat /proc/meminfo | grep -E 'MemTotal|MemFree|MemAvailable'" echo "Janky frames:" adb shell "dumpsys gfxinfo com.yaxon.launcher | grep 'Janky frames'" sleep 10 done ``` --- ## 八、结论 ### 核心问题 | 层级 | 问题 | 占用 | 根因 | |------|------|------|------| | 应用层 | AVM | 89% CPU | 激活无超时、图像处理阻塞 | | 应用层 | TXZ语音助手 | 76% CPU | WebSocket失败无限重试 | | 系统层 | 内存紧张 | 13%可用 | PSI阈值激进、频繁杀进程 | | 系统层 | 渲染阻塞 | 18% CPU | surfaceflinger调度不及时 | ### 解决方向 1. **应用层优先**:修复AVM和TXZ的CPU异常占用(预期释放165%+ CPU) 2. **系统层配合**:调整内存管理策略,减少进程回收导致的二次卡顿 3. **渲染优化**:提高SurfaceFlinger调度优先级,保障UI流畅 --- **报告生成完毕** 诊断工具:Android Lag Analyzer v1.0 + 代码静态分析 生成时间:2026-04-18