环境搭建与编译构建
本文档介绍 AC792N AIoT SDK(杰理 AC792N 系列 WiFi 802.11b/g/n + 双模蓝牙 V5.4 音视频多媒体 SoC 的通用固件 SDK)从零搭建开发环境、安装编译工具链,以及通过 Code::Blocks IDE 或 Makefile 命令行完成固件编译构建的完整流程,包含顶层构建系统调度机制、make target 速查与常见编译错误处理。
Purpose and Scope
本页覆盖「环境搭建与编译构建」这一子系统能力的端到端内容:
- 支持的主机平台(Windows / Linux / macOS)与工具选型;
- 杰理编译工具链的获取、安装与验证(
/opt/jieli、clang); - 烧录与量产工具简介;
- SDK 工程结构(
sdk/apps/*/board/wl83/板级工程、.cbp工程、project.jlproj杰理工程文件); - 顶层
sdk/Makefile的调度机制与全部 make target; - 编译产物与常见编译错误的排查。
下列主题属于本目录的兄弟页面,本文仅作交叉指引、不展开:烧录与升级(USB 升级工具、生产烧写工具的具体操作)、配置说明(板级/功能/蓝牙/网络/音频 JSON 配置项详解)、应用与示例指南(各方案与 demo 的功能开发)。固件升级细节见 README「九、烧录与升级」,配置入口见 project.jlproj 的 tabform 列表。
Overview
AC792N 是杰理科技推出的低成本、高集成度 WiFi + 蓝牙 AIoT 多媒体 SoC:双核浮点 DSP @ 320MHz、384KB SRAM、8/16MB DDR1、集成音频(ADC/DAC)、视频(DVP/MIPI + ISP)、显示(MIPI/RGB + LVGL/AWTK + GPU2.5D)与丰富外设。SDK 代码以 C 语言为主,依赖 lwIP、mbedTLS、LVGL、AWTK 等开源项目,并与预编译静态库(*.a)配合链接生成固件。
SDK 的构建体系为「双入口、统一产物」:
- Code::Blocks IDE 入口(Windows 推荐)——直接打开板级目录下的
AC792N_*.cbp工程文件,IDE 内一键 Build(Ctrl+F9); - Makefile 命令行入口(Linux 推荐)——在
sdk/目录执行make <target>,由顶层 Makefile 逐级派发到各应用的板级 Makefile。
两条路径共用同一套杰理交叉编译工具链(基于 clang),最终产出可烧录的固件镜像(bin / uboot 等)。构建过程高度依赖外部预编译库与头文件,因此「工具链安装正确 + 库文件完整」是编译成功的前提——这也是本页把环境搭建放在编译构建之前的原因。
Architecture
下图展示构建环境的整体架构:主机侧入口(IDE / 命令行)→ 杰理工具链 → SDK 源码与预编译库 → 固件产物。
flowchart TD
subgraph sg_Host["主机环境"]
CB["Code::Blocks IDE (.cbp)"]
MK["Makefile 命令行"]
BAT["make_prompt.bat (Windows)"]
end
subgraph sg_Toolchain["杰理编译工具链 (/opt/jieli)"]
CLANG["clang 交叉编译器"]
LD["链接器 / 库工具"]
end
subgraph sg_SDK["SDK 源码树"]
TOPMK["sdk/Makefile 顶层入口"]
BOARDMK["apps/*/board/wl83/Makefile"]
CBP["AC792N_*.cbp 工程"]
CFG["板级/功能/蓝牙等 JSON 配置"]
end
subgraph sg_Libs["预编译资源"]
LIBA["cpu/wl83/liba/*.a"]
LIB["lib/*.a"]
INCLUDE["include_lib/ 头文件"]
end
subgraph sg_Out["构建产物"]
FW["固件 bin / uboot 镜像"]
end
CB --> CBP
BAT --> MK
MK --> TOPMK
TOPMK --> BOARDMK
CBP --> CLANG
BOARDMK --> CLANG
CLANG --> LIBA
CLANG --> LIB
CLANG --> INCLUDE
CFG --> BOARDMK
BOARDMK --> FW
CBP --> FW
各组件职责说明:
| 组件 | 职责 | 来源依据 |
|---|---|---|
project.jlproj | 杰理 IDE 工程描述文件,声明 type(如音箱)、sdk(如 wifi_soundbox)、chip(AC792N)及 tabform 配置页(板级配置/功能配置/蓝牙配置/LE_AUDIO/网络/音频/提示音/音频流程 x6flow) | project.jlproj |
sdk/Makefile | 顶层统一编译入口,仅做目标派发:$(MAKE) -C apps/<app>/board/wl83 -f Makefile | sdk/Makefile |
apps/*/board/wl83/ | 板级工程目录:板级 Makefile、AC792N_*.cbp、board_develop_AC79xx.h 引脚/外设配置、board_develop.c 与 sdk_config.h 全局配置 | README.md |
| 杰理工具链 | 基于 clang 的交叉编译器与链接工具,Linux 下安装于 /opt/jieli,关键路径 /opt/jieli/common/bin/clang | README.md |
| 预编译库 | sdk/cpu/wl83/liba/ 与 sdk/lib/ 下的 *.a 静态库,配合 include_lib/ 头文件使用 | README.md |
设计意图:顶层 Makefile 刻意保持「薄」,只做目标到子目录的映射,实际编译逻辑全部下沉到各应用的板级 Makefile。这样新增一个应用只需在顶层登记一个 target,而应用内部如何组织源文件、宏定义、链接脚本完全自治,避免多应用共享构建脚本时的耦合。
环境搭建
主机平台支持矩阵
| 系统 | 支持情况 | 推荐编译方式 |
|---|---|---|
| Windows | ✅ 官方推荐 | Code::Blocks IDE(打开 .cbp 工程,Build / Ctrl+F9) |
| Linux | ✅ 官方支持 | Makefile 命令行(make <target>) |
| macOS | ⚠️ 需自行配置交叉编译工具链 | 不提供开箱即用路径 |
安装杰理编译工具链
工具链是编译的前提,Linux 下安装步骤与校验命令如下:
- 从开发环境文档获取安装指引;
- Linux 用户从 pkgman.jieliapp.com 下载工具链,解压到
/opt/jieli目录; - 确认目录层次正确:
/opt/jieli/common/bin/clang必须存在; - 验证安装:
# 验证工具链是否安装成功
clang --version
设计意图:将工具链固定安装到 /opt/jieli 这一约定路径,是为了让仓库内所有 Makefile 和 .cbp 工程无需携带绝对路径即可按统一前缀定位编译器;工具链不在仓库内分发,而是独立发布,保证 SDK 体积可控且工具链可独立升级。
安装烧录与测试工具
| 工具 | 用途 | 获取方式 |
|---|---|---|
| USB 升级工具 | 将编译生成的固件烧录到目标板(开发调试) | 使用文档 |
| 生产烧写工具 | 量产 / 裸片烧写 | 使用文档 |
烧录操作(按住烧录按键→复位/上电→选择固件→升级)属于「烧录与升级」兄弟页面主题,本文不展开。
工程结构
仓库布局(构建相关视角)
ac792(仓库根)/
├── sdk/ # SDK 主体
│ ├── apps/ # 应用层代码
│ │ ├── common/ # 公共模块(asr/audio_music/camera/lvgl/dma2d_gpu/…)
│ │ ├── wifi_camera/ # WiFi 摄像头方案
│ │ ├── wifi_soundbox/ # WiFi 智能音箱方案
│ │ ├── wifi_bbm/ # 婴儿监护器方案
│ │ └── demo/ # 7 个功能 demo(ble/wifi/wifi_ext/edr/ui/hello/audio)
│ ├── cpu/wl83/ # CPU 平台代码 + 预编译库(liba) + 烧录工具(tools)
│ ├── include_lib/ # 头文件(btctrler/btstack/driver/media/net/system/update…)
│ ├── lib/ # 预编译库
│ ├── audio/ # 音频中间件
│ ├── tools/ # 编译工具
│ ├── Makefile # SDK 顶层统一编译入口
│ └── make_prompt.bat # Windows 编译命令行入口
├── src/ # 项目配置(板级/功能/蓝牙/网络/音频 JSON 配置)
├── ui_prj/ # 杰理 UI 工程资源
├── doc/ # 数据手册、硬件资料
├── docs/ # 在线文档源
├── sdk_tools/ # SDK 工具
└── project.jlproj # 杰理工程文件
板级工程目录(编译单元)
每个应用目录下都有 board/wl83/ 子目录,它同时是 Makefile 派发的目标目录 和 Code::Blocks 工程的载体:
| 文件 | 作用 |
|---|---|
Makefile | 该应用的编译脚本(顶层 Makefile 通过 -C 进入此处执行) |
AC792N_*.cbp | Code::Blocks 工程文件(如 AC792N_WIFI_CAMERA.cbp) |
board_develop_AC79xx.h | 板级配置(引脚、外设等,按芯片型号区分,如 board_develop_AC7926A.h) |
board_develop.c / sdk_config.h | 板级初始化与全局配置 |
杰理工程文件 project.jlproj
仓库根目录的 project.jlproj 是杰理 IDE 的工程描述文件,声明了当前工程类型、SDK 选择与配置页映射:
{
"type": "音箱",
"sdk": "wifi_soundbox",
"singleSeries": false,
"chip": "AC792N",
"version": "V1.0.0",
"pack": "AC792N-demo",
"projectType": "OfflineProject",
"tabform": [
{ "type": 1, "fileName": "src\\板级配置.json", "binName": "boardcfg.bin", "showName": "板级配置" },
{ "type": 1, "fileName": "src\\功能配置.json", "binName": "modecfg.bin", "showName": "功能配置" },
{ "type": 1, "fileName": "src\\蓝牙配置.json", "binName": "btcfg.bin", "showName": "蓝牙配置" }
]
}
设计意图:tabform 把 src/ 下的 JSON 配置(板级配置 → boardcfg.bin、功能配置 → modecfg.bin、蓝牙配置 → btcfg.bin 等)与 IDE 可视化配置页一一绑定,开发者在 IDE 中修改配置后即可编译生成对应 *.bin,随固件一并烧录;projectType: OfflineProject 表示该工程为离线工程,不依赖云端托管。
编译构建机制
顶层 Makefile 调度逻辑
sdk/Makefile 是整棵 SDK 树唯一的统一编译入口,其设计原则是「薄派发」:文件头部注释声明 Linux 编译前提(工具链解压到 /opt/jieli、ulimit -n 建议大于 8096),随后为每个应用定义 目标名 与 clean_目标名 两个 phony target,统一通过 $(MAKE) -C <板级目录> -f Makefile 递归调用子工程:
# 总的 Makefile,用于调用目录下各个子工程对应的 Makefile
# 注意: Linux 下编译方式:
# 1. 从 http://pkgman.jieliapp.com/doc/all 处找到下载链接
# 2. 下载后,解压到 /opt/jieli 目录下,保证
# /opt/jieli/common/bin/clang 存在(注意目录层次)
# 3. 确认 ulimit -n 的结果足够大(建议大于8096),否则链接可能会因为打开文件太多而失败
all: ac792n_wifi_camera ac792n_wifi_soundbox ac792n_wifi_bbm ac792n_demo_demo_ble ac792n_demo_demo_wifi_ext ac792n_demo_demo_ui ac792n_demo_demo_hello ac792n_demo_demo_wifi
@echo +ALL DONE
clean: clean_ac792n_wifi_camera clean_ac792n_wifi_soundbox clean_ac792n_wifi_bbm clean_ac792n_demo_demo_ble clean_ac792n_demo_demo_wifi_ext clean_ac792n_demo_demo_ui clean_ac792n_demo_demo_hello clean_ac792n_demo_demo_wifi
@echo +CLEAN DONE
ac792n_wifi_camera:
$(MAKE) -C apps/wifi_camera/board/wl83 -f Makefile
clean_ac792n_wifi_camera:
$(MAKE) -C apps/wifi_camera/board/wl83 -f Makefile clean
依据:sdk/Makefile
要点解读:
- 递归 make:
$(MAKE) -C切换到板级目录执行该应用的 Makefile,因此各应用的源文件组织、编译选项、宏定义互不影响; all聚合:一键构建全部 8 个已登记 target,构建完成后打印+ALL DONE便于脚本识别;clean聚合:一键清理全部子工程产物,打印+CLEAN DONE;- 命名约定:
<应用名>与clean_<应用名>成对出现,应用名即 README 中「make target」列的值。
注:README「编译命令速查表」中还列出了
ac792n_demo_demo_edr与ac792n_demo_demo_audio两个目标,但当前sdk/Makefile的.PHONY声明与all集合仅登记了上述 8 个 target。若需要这两个 demo,可参照既有模式在顶层 Makefile 中补充登记,或直接进入对应board/wl83/目录执行其 Makefile。
make target 速查表
以下命令在 sdk/ 目录下执行:
| 目标 | 应用 | 命令 |
|---|---|---|
| WiFi 摄像头 | wifi_camera | make ac792n_wifi_camera |
| WiFi 智能音箱 | wifi_soundbox | make ac792n_wifi_soundbox |
| 婴儿监护器 | wifi_bbm | make ac792n_wifi_bbm |
| BLE Demo | demo_ble | make ac792n_demo_demo_ble |
| 扩展 WiFi Demo | demo_wifi_ext | make ac792n_demo_demo_wifi_ext |
| UI Demo | demo_ui | make ac792n_demo_demo_ui |
| Hello Demo | demo_hello | make ac792n_demo_demo_hello |
| WiFi Demo | demo_wifi | make ac792n_demo_demo_wifi |
| 全部 | 全部 | make all |
| 清理全部 | 全部 | make clean |
| 清理单个工程 | wifi_camera | make clean_ac792n_wifi_camera |
| 清理单个工程 | demo_ble | make clean_ac792n_demo_demo_ble |
编译控制流
flowchart TD
Start([开发者执行 make 或 IDE Build]) --> Entry{"构建入口?"}
Entry -->|"make <target>"| TopMK["sdk/Makefile 解析 target"]
Entry -->|"Code::Blocks Ctrl+F9"| CBP["打开 AC792N_*.cbp"]
TopMK --> Dispatch["$(MAKE) -C apps/<app>/board/wl83 -f Makefile"]
CBP --> BoardMK["读取板级工程配置"]
Dispatch --> BoardMK
BoardMK --> Compile["clang 交叉编译 .c 源文件"]
Compile --> Libs{"链接预编译库?"}
Libs -->|"cpu/wl83/liba/*.a"| Link["链接 .a + include_lib 头文件"]
Libs -->|"lib/*.a"| Link
Link --> Check{"编译成功?"}
Check -->|"是"| FW["生成固件 bin / uboot 镜像"]
Check -->|"否"| Err["报错:clang not found / Too many open files / -lxxx missing / undefined reference"]
FW --> Flash["USB 升级工具 / 生产烧写工具 烧录"]
Err --> Fix["按错误表排查(见失败模式章节)"]
Flash --> End([完成])
Fix --> End
两种构建方式的等价性
- Code::Blocks 方式:进入
sdk/apps/<app>/board/wl83/,双击AC792N_*.cbp,点击 Build(Ctrl+F9)。IDE 内部调用与 Makefile 相同的工具链完成编译链接,适合 Windows 上依赖 IDE 断点调试与配置页可视化的场景; - Makefile 方式:Windows 用户双击
sdk/make_prompt.bat打开预置环境变量的命令行;Linux 用户在sdk/目录直接make <target>。适合 CI、脚本化构建与 Linux 开发机。
Linux 编译注意事项
链接阶段需要同时打开大量目标文件与库文件,Linux 默认文件描述符上限可能不足,须先调大:
# 1. 确保文件描述符限制足够大(链接阶段需要打开大量文件)
ulimit -n 8096
# 2. 进入 sdk 目录并行编译
make ac792n_wifi_camera -j`nproc`
设计意图:-j 并行度直接取 nproc(物理核数),因为各应用编译彼此独立、子工程内部也以文件为粒度并行,可以最大化利用多核;而 ulimit -n 8096 是对链接器「打开大量文件」行为的显式适配,属于嵌入式大工程链接阶段的常见坑。
使用示例
示例 1:克隆仓库并选择工程
git clone git@gitlab.zh-jieli.com:video/ac792.git
cd ac792
# SDK 实际工程位于 sdk/ 目录,根据产品需求选择应用工程
# sdk/apps/wifi_camera/ # WiFi 摄像头方案
# sdk/apps/wifi_soundbox/ # WiFi 智能音箱方案
# sdk/apps/wifi_bbm/ # 婴儿监护器 / 带屏视频监护方案
# sdk/apps/demo/ # 7 个功能 demo(ble/wifi/wifi_ext/edr/ui/hello/audio)
示例 2:工具链验证与单应用编译(Linux)
# 验证工具链(关键路径 /opt/jieli/common/bin/clang)
clang --version
# 调大文件描述符限制后并行编译 WiFi 摄像头固件
ulimit -n 8096
cd sdk
make ac792n_wifi_camera -j`nproc`
示例 3:清理单个工程
make clean_ac792n_wifi_camera # 清理 wifi_camera 编译产物
make clean_ac792n_demo_demo_ble # 清理 demo_ble 编译产物
示例 4:在顶层 Makefile 中登记新应用(扩展模式)
参照既有模式,为新增应用注册「构建 / 清理」两个目标,并加入 all / clean 聚合列表:
ac792n_demo_demo_audio:
$(MAKE) -C apps/demo/demo_audio/board/wl83 -f Makefile
clean_ac792n_demo_demo_audio:
$(MAKE) -C apps/demo/demo_audio/board/wl83 -f Makefile clean
依据:sdk/Makefile(demo_ble 同型目标)
配置选项
构建环境配置
| 配置项 | 类型 | 默认值 / 约定 | 说明 |
|---|---|---|---|
| 工具链安装路径 | 路径 | /opt/jieli(Linux) | 工具链解压目录,需保证 /opt/jieli/common/bin/clang 存在 |
| 文件描述符上限 | ulimit | 建议 > 8096 | 链接阶段需打开大量文件,ulimit -n 8096 规避 Too many open files |
| 并行度 | make -j | nproc | 按 CPU 核数并行编译,缩短构建时间 |
| Windows 命令行环境 | bat | sdk/make_prompt.bat | 双击打开预置工具链环境变量的命令行 |
| 工程类型 | jlproj | OfflineProject | 离线工程,不依赖云端托管(见 project.jlproj) |
构建产物与目标映射
| 配置项 | 说明 |
|---|---|
make all | 构建全部 8 个已登记 target,完成打印 +ALL DONE |
make clean | 清理全部子工程产物,完成打印 +CLEAN DONE |
make clean_<target> | 清理单个应用产物 |
| 固件产物 | bin / uboot 镜像,供 USB 升级工具或生产烧写工具烧录 |
失败模式、边界情况与并发
常见编译错误对照
| 错误提示 | 根因 | 解决方法 |
|---|---|---|
clang: command not found | 未安装杰理编译工具链,或环境变量未配置 | 安装工具链;Linux 解压到 /opt/jieli 并确认 common/bin/clang 存在 |
Too many open files | Linux 文件描述符上限不足(链接阶段打开大量文件) | ulimit -n 8096 调大限制 |
cannot find -lxxx | 缺少对应的 .a 库文件 | 检查 sdk/cpu/wl83/liba/ 与 sdk/lib/ 目录,确认预编译库完整 |
undefined reference to ... | 功能裁剪配置未包含对应模块 | 检查 sdk/apps/common/config/ 下的库配置(蓝牙 Profile、用户配置、授权码、日志等) |
边界情况与并发要点
- 并行构建的依赖顺序:顶层
all串行派发各 target(make 默认串行执行无依赖目标),各应用构建互不干扰;并行仅发生在-j指定的单应用内部编译/链接阶段,因此不会产生跨应用的产物竞争; - macOS 边界:SDK 官方未提供 macOS 开箱即用路径,需自行配置交叉编译工具链,属于不保证场景;
- 库缺失即失败:本仓库为 SDK 代码与示例工程,必须配合对应平台的
*.a库文件才能编译;若 clone 的子模块/库不完整,链接阶段会立即报cannot find -lxxx,属预期失败而非编译配置错误; - 工具链版本敏感性:Makefile 头部注释强调目录层次(
/opt/jieli/common/bin/clang),目录层级错误会导致 clang 无法定位,报错表现为clang: command not found。
性能与运维建议
- 编译属 CPU 密集 + 磁盘 IO 密集任务,建议
make <target> -j$(nproc)并行构建;CI 场景可在顶层执行make all后检查+ALL DONE输出判定整体成功; - 链接阶段对文件描述符敏感,所有 Linux 构建脚本应在顶部执行
ulimit -n 8096(README 与 Makefile 注释均已强调); - 预编译库(
*.a)与头文件(include_lib/)由杰理随 SDK 版本发布,升级 SDK 分支时应同步更新库与头文件,避免 ABI 不匹配导致undefined reference; - 调试期建议优先
make clean_<target>清理单个应用再重编,避免陈旧产物干扰;make clean全量清理适合发布前验证。
扩展点
- 新增应用 target:在
sdk/Makefile中按ac792n_<app>/clean_ac792n_<app>模式注册,并加入.PHONY、all、clean列表; - 新增板级型号:在
apps/<app>/board/wl83/下新增board_develop_AC79xx.h(按芯片型号如 AC7926A 区分引脚/外设配置),板级初始化由board_develop.c/sdk_config.h承载; - 功能裁剪:通过
sdk/apps/common/config/下的库配置(蓝牙 Profile、授权码、日志等)决定链接哪些模块——错误的裁剪会以undefined reference形式暴露; - IDE 配置页扩展:在
project.jlproj的tabform中登记新的配置 JSON 与对应binName(如boardcfg.bin、modecfg.bin、btcfg.bin),即可在杰理 IDE 中可视化编辑并随固件生成配置 bin。
测试
仓库未包含针对构建系统的自动化测试套件;构建系统的正确性验证依赖「编译成功 + 固件可烧录 + 目标板运行」的端到端链路。README 提供的 clang --version 校验与 +ALL DONE 输出可作为构建环境自检的最小冒烟测试。sh.exe.stackdump(仓库根目录)为 Windows 下 sh 异常时的崩溃转储文件,可忽略,不影响构建。
Related Links
- README.md 环境搭建与编译指南(源文档)
- sdk/Makefile(顶层构建入口)
- project.jlproj(杰理工程文件)
- 兄弟页面:烧录与升级(USB 升级工具 / 生产烧写工具操作)、配置说明(JSON 配置项详解)、应用与示例指南(方案与 demo 开发)
- 外部资源:杰理开发环境文档、工具链下载 pkgman、AC792 在线文档中心