使用 CodeQL 分析 AOSP
字数 1669 2025-08-29 08:32:01
使用 CodeQL 分析 AOSP 完整指南
1. CodeQL 简介
CodeQL 是一个开源的代码分析平台和漏洞扫描工具,其工作原理如下:
- 提取阶段:通过介入代码编译过程(编译型语言)或静态程序分析(解释型语言)获取代码语义信息
- 数据库生成:将提取的信息转换为 CodeQL 数据库
- 查询分析:使用专用 QL 语言编写查询语句来发现漏洞风险
CodeQL 的前身是 Semmle 的 LGTM 平台,2019 年被 GitHub 收购后开放了本地工具并开源了部分代码。
2. 准备工作
2.1 系统要求
- 操作系统:64 位 Ubuntu 18.04 或 16.04(不再支持 macOS)
- 硬件要求:
- 16GB+ 内存
- 500GB+ 磁盘空间
2.2 获取 AOSP 源码
推荐使用清华镜像源的每月初始化包:
wget -c mirrors.tuna.tsinghua.edu.cn/aosp-monthly/aosp-latest.tar
tar xf aosp-latest.tar
cd AOSP/.repo/repo
git pull origin master
cd repo/repo/repo sync
3. 编译 AOSP
- 安装依赖包(参考官方文档)
- 初始化编译环境:
source build/envsetup.sh
lunch aosp_x86_64-eng
m -j16 # 根据CPU核心数调整线程数
编译完成后会占用约 300GB 空间,在 out/target/product/generic_x86_64/ 目录下可找到镜像文件。
4. 生成 CodeQL 数据库
4.1 基本方法
以分析 frameworks/base 为例:
codeql database create ../codeql_frameworks \
--language=java \
--command="mmm frameworks/base" \
--source-root frameworks/base \
--overwrite
4.2 常见问题及解决方案
问题1:找不到 mmm 命令
原因:CodeQL 使用 preload_tracer 启动新进程,环境变量不继承
解决方案:
方法1:直接调用 soong 命令
codeql database create ../codeql-frameworks \
--language=java \
--command="`pwd`/build/soong/soong_ui.bash --make-mode -j1 framework-minus-apex" \
--source-root frameworks/base \
--overwrite
方法2:使用编译脚本
#!/bin/bash
cd $1
source ./build/envsetup.sh
lunch aosp_x86_64-eng
mmm $2
问题2:编译过程中没有发现代码
错误信息:No source code was seen and extracted
解决方案:
export ALLOW_NINJA_ENV=true
问题3:目录不存在错误
错误信息:directory /home/aosp/codeql-frameworks/log/ext does not exist
原因:AOSP 的 Soong 编译系统默认启用只读沙盒
解决方案:
- 将数据库路径设置为
./out/codeql-frameworks - 最终命令:
codeql database create out/codeql-frameworks \
--language=java \
--command="`pwd`/build/soong/soong_ui.bash --make-mode -j1 framework-minus-apex" \
--source-root frameworks/base \
--overwrite
4.3 内存问题处理
如果遇到 OOM 错误,需要修改 codeql-java-agent.jar 中的 JVM 参数:
- 使用反编译工具(如 Recaf)打开
codeql-java-agent.jar - 找到
com.semmle.extractor.java.Utils类中的invokeOdasaJavac方法 - 将 JVM 选项从
-Xmx1g修改为-Xmx4g
5. CodeQL 工作原理深入
5.1 编译过程拦截
CodeQL 通过以下机制介入编译过程:
- preload_tracer:使用
LD_PRELOAD/DYLD_INSERT_LIBRARIES注入 - libtrace:Lua 解释器,解释
tracing-config.lua脚本 - Java Agent:注入
codeql-java-agent.jar到 JVM 进程
5.2 文件系统限制
AOSP 的 Soong 编译系统限制:
- 默认只允许写入
./out/目录 - 可通过以下变量调整:
BUILD_BROKEN_SRC_DIR_RW_ALLOWLIST:指定白名单路径BUILD_BROKEN_SRC_DIR_IS_WRITABLE:完全禁用只读限制(不推荐)
6. 最佳实践
- 数据库路径:始终放在
./out/目录下 - 环境变量:确保设置
ALLOW_NINJA_ENV=true - 内存配置:根据项目规模调整 JVM 内存参数
- 清理缓存:生成新数据库前删除旧缓存:
rm -rf ./out/soong/.intermediates/frameworks/base/*
7. 总结
成功生成 CodeQL 数据库的关键步骤:
- 正确设置编译命令和环境变量
- 处理 AOSP 的文件系统限制
- 解决内存和路径问题
- 最终输出路径应为
out/codeql-frameworks
通过以上方法,可以成功为 AOSP 生成 CodeQL 数据库,为后续的代码分析和漏洞挖掘奠定基础。