模块编译调试方法

(此处举例framework、installd、SystemUI等模块的编译调试,其他类似)

1. Framework模块编译

Android系统代码的framework目录内,一共有3个模块单独编译:framework、services、framework-res.apk。

注意:偶尔会有改了代码但没检测到,编译结束后产物并未更新的情况,所以可以考虑先剪切掉原先的产物或者检查产物更新时间确保已经重新编译。

步骤

  1. 完成根目录下 source build/envsetup.sh 命令、lunch qssi-userdebug-mars 命令(准备好编译环境、选择好编译分支,才可以开始编译)。
  2. 整编命令如 bash build.sh -j32 dist --qssi_only 2>&1 | tee buildlog.log
1.1 修改frameworks/base/core/res下的内容
  • 在执行 source build/envsetup.sh 命令的版本源代码根目录执行 make framework-res -j32
  • 产物位于 out/target/product/qssi/system/framework 下面(如 framework-res.apk 之类),push到手机的 /system/framework/ 下面重启即可。
1.2 修改framework/base/services下的内容
  • 在执行 source build/envsetup.sh 命令的版本源代码根目录执行 make services -j32
  • 产物位于 out/target/product/qssi/system/framework 下面,拿出来push到手机的 /system/framework/ 下面重启即可。
1.3 修改framework/base/core下的内容
  • 在执行 source build/envsetup.sh 命令的版本源代码根目录执行 make framework-minus-apex -j32
  • 产物位于 out/target/product/qssi/system/framework 下面,拿出来push到手机的 /system/framework/ 下面重启即可。
  • 问题处理:如果卡在开机过程里(常在小于Android13版本中发生),而且不是自己原因导致而是一些AndroidRuntime错误导致的signal 6的内存错误,可尝试在push framework.jaradb shell rm -rf system/framework/oat system/framework/arm system/framework/arm64 再重启。
1.4 其他目录下的代码修改
  • 在framework/base下的其他很多目录下的代码修改也可以被编译到,但需要自行确认:
    • 故意改错去编译。
    • 搜Android.bp文件内容看看framework-minus-apex library的srcs是否包含了被修改的文件。
1.5 作SDK
  • 如果是要make出jar包给apk调用而不是push到系统里调试,那要拿此目录的jar包:out/target/common/obj/JAVA_LIBRARIES/framework-minus-apex_intermediates/classes.jar
  • 版本改动注意:在Android11之前修改了framework相关代码,只需 make framework 就可以编译出 framework.jar。在Android11,这个编译命令不起作用了,根据framework/base/目录下Android.bp中的提示,编译命令需要改为 make framework-minus-apex

2. 修改frameworks/native/cmds/abcd的任意模块代码

  • 通过 make abcd -j32 编译,比如 make installd -j16 make atrace -j16 等。
  • 产物位于 out/target/product/qssi/system/bin 下面,拿出来push到手机的 /system/bin/ 下面重启即可。

3. 修改packages/modules/abcd的代码

  • 通过找被修改文件属于的同/上级目录的Android.bp文件中哪个模块内编译,在此模块library中找到apex_available标签,即标识该library可以被name为xxxx的apex包进去,通过 make xxxx -j32 编译。
  • 产物位于 out/target/product/qssi/system/apex/ 下面,拿出来push到手机的 /system/apex/ 下面重启即可。
  • 示例:修改了 /packages/modules/Wifi/framework/java/android/net/wifi/WifiManager.java,那么在 /packages/modules/Wifi/framework/Android.bp 中找到 apex_available: ["com.android.wifi", "test_com.android.wifi"],就知道 make com.android.wifi -j16 可以编译到被修改文件。

4. 改动SystemUI、Settings等模块的代码

  • 可以通过 make SystemUImake Settings 来进行编译,产物在 /system/app/system/priv-app 下面,将结果apk直接install,然后重启此应用相关服务,如直接重启手机,或者如SystemUI在install后 adb shell am restart 也可以。
  • 注意:不要push已经存在的apk到手机,重启系统不会扫描,新的apk不会重新安装,测试效果将还是原先的效果,除非此系统apk可以先删掉重启再push再重启。

5. 通用编译模块的方法

  • 如修改位于 framework/native/services 下的文件,可以通过在同级或上级目录中的Android.bp文件内容中查找修改的文件名字或具体目录,来找到所属sources,再逐级向上找到被编译进哪个“name”的目标产物xxx中,再 make xxx -j32 对其编译。
  • 如果xxx编译出的产物是中间产物或手机中没有的无法替换的产物可以再向上查找更大name的目标产物xxxx(如:cc_library_shared、cc_library、java_library、apex_available等)进行编译或直接push进system/lib和system/lib64重启。

6. 编译system.img

  • 当你确定修改的内容能在编译system.img时带入,可以使用 make systemimage -j16 编译。通过进入fastboot模式后刷system.img进行生效。

编译调试注意点

  1. 编译最好把已经生成的先删掉,不然有可能文件不更新(push前check下文件的生成时间)。
  2. 编译终端最后提示的生成路径不一定是唯一生成路径,同级目录、对称lib或lib64目录里可能都有你需要的生成物。library要把生成的库文件在system/lib和system/lib64下都做相应的push。
  3. 如果是push替换库文件,最好留一个原本的备份避免push了开不了机器。
  4. 编译调试的时候如果是自己陌生的模块,建议每次都加行特殊log以确认自己的修改已经生效。

二、使用ninja替代make进行快速编译

为什么要使用ninja?

通常使用make编译会有两个阶段:

  1. 先分析Android.bp,将所有需要参与编译的文件的路径都记录下,writing build rules并打包到 out/soong/combined-.ninja 中。(普遍耗时15-20min)
  2. 然后ninja工具通过第一步生成的文件,编译要编译的模块。(不同模块速度不同,比如services模块只需要大约20s)

优点:直接使用ninja就可以省去第一部分耗时,尤其在反复编译时调试效率提高。

注意点

  1. 进行ninja之前必须要先make一次(当然要想make必须先根目录source和lunch一次),以生成路径文件;如果你的修改增删了模块中文件的名字路径,就必须重新make生成路径文件。

ninja的获取

cd到android系统源码的根目录下,执行
cp prebuilts/build-tools/linux-x86/bin/ninja out/host/linux-x86/bin/
cp prebuilts/build-tools/linux-x86/bin/ninja /usr/local/bin/
cp prebuilts/build-tools/linux-x86/bin/ninja /usr/bin/
ln -sf out/combined-***.ninja build.ninja

ninja文件内容

#!/bin/bash
ninja(){ninja_bin="$ANDROID_BUILD_TOP/prebuilts/build-tools/linux-x86/bin/ninja"ninja_build_file="$ANDROID_BUILD_TOP/out/combined-$TARGET_PRODUCT.ninja"if [ ! -f $ninja_build_file ]thenecho "can't find ninja buildfile $ninja_build_file"exit -1fiif [ ! -f $ninja_bin ]thenecho "can't find ninja binary $ninja_bin"exit -1fi$ninja_bin -f $ninja_build_file $1}
#usage:ninja<modulename>
ninja $*

ninja的执行

如果执行ninja进行快速编译时,遇到如下错误:

ninja: error while loading shared libraries: libjemalloc5.so: cannot open shared object file: No such file or directory

使用如下解决方法:

sudo cp prebuilts/build-tools/linux-x86/lib64/libjemalloc5.so /usr/lib

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/diannao/94201.shtml
繁体地址,请注明出处:http://hk.pswp.cn/diannao/94201.shtml
英文地址,请注明出处:http://en.pswp.cn/diannao/94201.shtml

如若内容造成侵权/违法违规/事实不符,请联系英文站点网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【硬件-笔试面试题】硬件/电子工程师,笔试面试题-51,(知识点:stm32,GPIO基础知识)

目录 1、题目 2、解答 3、相关知识点 一、GPIO 基本结构与特性 1. GPIO 硬件结构 2. 主要特性 二、GPIO 工作模式 1. 输入模式 2. 输出模式 3. 复用功能模式 4. 特殊模式 三、GPIO 配置步骤&#xff08;以 STM32Cube HAL 库为例&#xff09; 1. 初始化 GPIO 时钟 …

小智服务器Java安装编译(xinnan-tech)版

github&#xff1a;https://github.com/xinnan-tech/xiaozhi-esp32-server 一、JDK 1、JDK21下载&#xff1a; https://www.oracle.com/cn/java/technologies/downloads/#jdk21-windows RPM安装&#xff1a; rpm -ivh jdk-21_linux-x64_bin.rpm 2、IDEA设置JDK File → P…

智能平台的感知进化:AI × 视频通感在群体终端协同中的应用探索

✳️ 引言&#xff1a;从单兵到集群&#xff0c;未来智能平台的协同演进 从传统的单兵执行任务到如今的“群体智能平台编组”&#xff0c;现代感知系统正经历一场由 AI、机器人与智能计算平台驱动的深度变革。过去&#xff0c;履带式无人平台在平坦地形中承担支援任务&#xf…

基于定制开发开源AI智能名片S2B2C商城小程序的B站私域流量引流策略研究

摘要&#xff1a;随着移动互联网进入存量竞争阶段&#xff0c;私域流量运营成为企业数字化转型的核心战略。B站作为中国最大的Z世代文化社区&#xff0c;其3.41亿月活跃用户中Z世代占比达58%&#xff0c;且25岁以上用户增速显著&#xff0c;用户日均使用时长超108分钟&#xff…

Spring+K8s+AI实战:3全栈开发指南

Spring、K8s、人工智能、Docker及Windows实例 以下是与Spring、K8s、人工智能、Docker及Windows实例相关的实用示例,涵盖开发、部署和集成场景: Spring Boot微服务开发 示例1:REST API构建 使用Spring Boot创建带Swagger文档的RESTful服务,集成JPA和Hibernate进行数据库…

C++ 生成动态库.dll 及 C++调用DLL,C++ 生成静态库.lib及 C++调用lib

文章目录1 C 动态库.dll生成 及 调用1.1 生成C 动态库dll1.1.1 创建项目MyDLL1.1.2 编写.h 和 .cpp文件1.1.3 设置 及 生成 DLL1.2 调用 C 动态库dll1.2.1 创建C 空项目DLLtest1.2.2 动态库配置 及代码调用测试2 C 静态库.lib 生成 及 调用3 C 生成静态库.lib及调用 &#xff0…

信创应用服务器TongWeb安装教程、前后端分离应用部署全流程

TongWeb 简介TongWeb 是东方通&#xff08;TongTech&#xff09;开发的国产Java应用服务器&#xff08;中间件&#xff09;&#xff0c;类似于国外的 WebLogic、WebSphere 和开源的 Tomcat、Jetty&#xff0c;主要用于企业级Java应用&#xff08;如J2EE&#xff09;的部署和运行…

Rust 同步方式访问 REST API 的完整指南

Rust 同步方式访问 REST API 的完整指南 在 Rust 中不使用异步机制访问 REST API 是完全可行的&#xff0c;特别适合简单应用、脚本或不需要高并发的场景。以下是完整的同步实现方案&#xff1a; &#x1f4e6; 依赖选择 推荐库&#xff1a; [dependencies] reqwest { version…

32.【.NET8 实战--孢子记账--从单体到微服务--转向微服务】--单体转微服务--财务服务--账本与预算

在我们的孢子记账应用中&#xff0c;账本是用于记录每一笔收支流水的核心模块。通过账本&#xff0c;我们可以清晰地追踪资金的流入与流出&#xff0c;进行数据统计和分析&#xff0c;为后续的报表生成和决策支持提供基础数据。预算模块则是用于设置和管理预算的功能&#xff0…

模型预估打分对运筹跟踪的影响

在uplift建模中&#xff0c;模型离线指标(QINI、AUUC)提升并不意味着在线A/B实验的收益&#xff0c;因为在线运筹还需要λ\lambdaλ约束。如果模型打分不满足单调增且roi边际递减&#xff0c;那么λ\lambdaλ运筹求解会非常不稳定&#xff0c;导致线上发券偏高&#xff0c;毛利…

音视频学习(四十六):声音的三要素

声音是人类感知世界的重要途径之一。在自然界中&#xff0c;声波本质上是介质中传播的机械振动&#xff0c;而人类对声音的主观感受主要通过三种属性来认知和描述&#xff0c;即音调&#xff08;音高&#xff09;、响度&#xff08;强弱&#xff09;、音色&#xff08;音质&…

spring batch处理数据模板(Reader-Processor-Writer模式)

步骤监听器 Component public class StepListener implements StepExecutionListener {private StepExecution stepExecution;public StepExecution getStepExecution() {return this.stepExecution;}Overridepublic void beforeStep(StepExecution stepExecution) {this.stepE…

【华为OD机试】从小桶里取球

题目描述 某部门开展Family Day开放日活动,其中有个从桶里取球的游戏,游戏规则如下: 有N个容量一样的小桶等距排开,且每个小桶都默认装了数不等的小球, 每个小桶装的小球数量记录在数组bucketBallNums中, 游戏开始时,要求所有桶的小球总数不能超过SUM, 如果小球总…

std::unordered_map 和 std::map的区别【C++】

std::unordered_map 和 std::map 是 C 标准库中两种不同的关联容器&#xff0c;它们都用于存储键值对&#xff0c;但在实现方式、性能特点和使用场景上存在显著区别。以下是它们的主要区别&#xff1a; 1. 数据结构 std::map&#xff1a; 基于 红黑树&#xff08;一种自平衡二叉…

云原生环境里的显示变革:Docker虚拟浏览器与cpolar穿透技术实战

文章目录前言【视频教程】1. 关于neko2. 本地部署neko3. neko简单使用4. 安装内网穿透5. 配置neko公网地址6. 配置固定公网地址前言 现代远程协作本该是无缝衔接的过程&#xff0c;却被这些障碍不断打断&#xff1a;多设备屏幕同步存在延迟、跨平台访问需要复杂配置、公网IP申…

LVGL + ESP-Brookesia 在Windows下的编译和运行

LVGL ESP-Brookesia 在Windows下的编译和运行 1. 项目介绍 本项目是基于 LVGL&#xff08;轻量级多功能图形库&#xff09;和 ESP-Brookesia 的嵌入式模拟桌面应用开发框架&#xff0c;专为嵌入式设备构建丰富的图形界面而设计。通过在Windows环境下模拟嵌入式设备的图形界面…

【ip】IP地址能否直接填写255?

IP地址数值限制​ 最近有朋友后台问我&#xff0c;IP地址里填255行不行&#xff1f;思索着有一阵子没有分享基础的知识&#xff0c;就在今天大致说一下&#xff0c;关于IP地址里填255行不行&#xff1f;答案当然是否定的。 IP地址由4个段组成&#xff0c;每个段的数值范围其实限…

力扣热题100----------141.环形链表

给你一个链表的头节点 head &#xff0c;判断链表中是否有环。 如果链表中有某个节点&#xff0c;可以通过连续跟踪 next 指针再次到达&#xff0c;则链表中存在环。 为了表示给定链表中的环&#xff0c;评测系统内部使用整数 pos 来表示链表尾连接到链表中的位置&#xff08;索…

【Java开发日记】我们来说说 LockSupport 的 park 和 unpark

目录 一、LockSupport 1.1、LockSupport函数列表 1.2、基本使用 先 park 再 unpark 先 unpark 再 park 1.3、特点 与 Object 的 wait & notify 相比 二、LockSupport park & unpark原理 2.1、情况一&#xff0c;先调用park&#xff0c;再调用unpark park 操作…

AGI|从“实验室”到“生产线”:企业级AI Agent 如何突围

在数字化转型的深水区&#xff0c;企业级 AI Agent 正从技术概念走向产业实践&#xff0c;成为驱动生产力变革的核心引擎。目录 一、风口已至&#xff1a;AI Agent 的崛起逻辑与市场刚需 二、企业级AI Agent&#xff1a;核心能力与独特价值定位 三、AI Agent 的未来目标 一、…