news 2026/9/29 3:37:51

Zephyr BSP: 47-BSP Customer SDK

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Zephyr BSP: 47-BSP Customer SDK

BSP 是公司内部平台基础设施,Customer SDK 才是客户开发产品的入口。SDK 通过「稳定接口边界」把内部实现与客户代码解耦,客户只依赖受版本承诺保护的 Public API。一个完整 SDK 包含 Toolchain、Zephyr/BSP、Board Support、SDK API、Samples、Docs 与 Build/Flash/Debug 工具,并经过「开发 → CI → 打包 → SBOM → 发布 → 交付」的完整流程。版本演进遵循语义化版本号,配合 Deprecated 标记与迁移指南,让客户升级不被打断。

**BSP Customer SDK:把 BSP 变成"客户真正能用的产品"
**

BSP 做出来以后,公司客户到底拿什么东西来开发产品?

答案通常不是让客户直接面对几十万个 Zephyr 源文件,而是提供一层:

BSP Customer SDK

可以把整个体系理解成:

Company BSP │ ┌─────────────┴─────────────┐ │ │ BSP Internal Customer SDK │ │ HAL/Drivers/SoC Headers Devicetree/Board Libraries Build System Samples CI/Tests Toolchain Security/SBOM Flash/Debug │ │ └─────────────┬───────────────┘ │ Customer │ ┌──────────┼──────────┐ │ │ │ App1App2App3

核心思想是:
BSP 是公司的产品基础设施,Customer SDK 是客户使用 BSP 的产品开发接口。
下面这张图把 Customer SDK 的完整架构分层展开,标注每一层包含的内容、层与层之间的依赖关系,以及客户与 BSP 内部之间的稳定接口边界:

┌──────────────────────────────────────────────────────────────┐ │ Customer Application │ │(客户自己的 app/boards/prj.conf)│ └───────────────────────────┬──────────────────────────────────┘ │ ┌─────────────▼─────────────┐ │ Stable Interface │ ← 稳定接口边界 │(Zephyr API+SDK API)│ └─────────────┬─────────────┘ │ ┌───────────────────────────▼──────────────────────────────────┐ │ Customer SDK │ │ │ │ ┌──────────────┐ ┌──────────────┐ ┌──────────────────┐ │ │ │ Toolchain │ │ Zephyr/BSP │ │ Board Support │ │ │ │ GCC/CMake │──▶│ Zephyr OS │──▶│ Board Catalog │ │ │ │ Python/west │ │ Company BSP │ │ SoC/RAM/Flash │ │ │ └──────────────┘ └──────────────┘ │ UART/GPIO/SPI │ │ │ └──────────────────┘ │ │ ┌──────────────┐ ┌──────────────┐ ┌──────────────────┐ │ │ │ SDK API │ │ Samples │ │ Documentation │ │ │ │ Public API │──▶│ hello_world │ │ Getting Started │ │ │ │ Private API │ │ blinky/gpio │ │ Migration Guide │ │ │ └──────────────┘ └──────────────┘ └──────────────────┘ │ │ │ │ ┌──────────────┐ ┌──────────────┐ ┌──────────────────┐ │ │ │ Build Tools │ │ Flash Tools │ │ Debug Tools │ │ │ │ west build │ │ west flash │ │ GDB/OpenOCD │ │ │ └──────────────┘ └──────────────┘ └──────────────────┘ │ │ │ │ ┌────────────────────────────────────────────────────────┐ │ │ │ Release Metadata │ │ │ │ SDK version/Zephyr version/BSP version/SBOM │ │ │ └────────────────────────────────────────────────────────┘ │ └───────────────────────────┬──────────────────────────────────┘ │ ┌─────────────▼─────────────┐ │ Stable Interface │ ← 稳定接口边界 │(Zephyr API+SDK API)│ └─────────────┬─────────────┘ │ ┌───────────────────────────▼──────────────────────────────────┐ │ BSP Internal │ │ HAL/SoC/Drivers/Devicetree/Kconfig/Linker │ │ CI/Tests/Security/SBOM │ └──────────────────────────────────────────────────────────────┘

各层之间的依赖关系与边界说明:

  • Toolchain → Zephyr/BSP:工具链负责把应用与 BSP 源码编译成可执行镜像,SDK 必须锁定经过验证的 GCC/CMake/Python/west 版本组合;
  • Zephyr/BSP → Board Support:BSP 提供 SoC 与驱动实现,Board Support 在其之上定义客户可见的板卡目录(如company_devkit)与资源清单;
  • SDK API → Samples → Documentation:Samples 演示 SDK API 的用法,Documentation 解释 API 语义与迁移路径,三者共同构成客户的学习入口;
  • Build/Flash/Debug Tools:统一封装west build/west flash/company debug,屏蔽底层 OpenOCD、J-Link、ST-Link 等差异;
  • Release Metadata:把 SDK、Zephyr、BSP、HAL、Toolchain 的版本关系与 SBOM 固定下来,形成可交付的软件物料清单;
  • 上下两条「稳定接口边界」:客户只接触 Zephyr API 与 SDK Public API,BSP 内部实现细节被完全隔离在边界之下,公司可以自由演进内部实现而不破坏客户代码。

1. 为什么 BSP 和 Customer SDK 不是一回事?

很多公司最开始会直接把 BSP Git repository 给客户。

例如:

company-bsp/├── zephyr/├── modules/├── soc/├── boards/├── drivers/├── dts/├── samples/├── scripts/└── tools/

客户然后:

west build-b company_board app

看起来很好。
但很快就会出现问题。
客户开始依赖:

soc/drivers/dts/Kconfig CMakeLists.txt 内部 HAL 内部 scripts 内部 CI 内部测试代码

于是客户实际上不是在使用:
BSP API
而是在使用:
BSP 内部实现细节。
这会导致一个严重问题:

BSP v1.0│ ├── 客户 A 依赖内部文件 A ├── 客户 B 依赖内部 Kconfig ├── 客户 C patch driver └── 客户 D 修改 linker script │ ▼ BSP v2.0│ ┌─────┼─────┐ ▼ ▼ ▼ A崩 B崩 C崩

所以成熟的 BSP 必须建立:

下面从几个关键维度对比「直接给 BSP 仓库」与「提供 Customer SDK」两种交付方式的差异:|维度|直接给 BSP 仓库|提供 Customer SDK||---|---|---||**客户接触面**|客户直接面对 `soc/`、`drivers/`、`dts/`、`Kconfig`、内部 HAL 等实现细节|客户只接触 Zephyr API+SDK Public API,内部实现被「稳定接口边界」隔离||**依赖稳定性**|客户会逐渐依赖内部文件、内部 Kconfig、甚至 patch 驱动/修改 linker script|客户依赖的是稳定、受支持的 Public API,内部实现可自由演进||**升级影响**|BSP 升级时,依赖内部实现的客户 A/B/C 逐个崩溃,升级成本极高|只要 Public API 兼容,客户代码无需改动,升级平滑||**支持成本**|每个客户都 fork 一份 BSP,公司需要为每个分支单独维护,成本爆炸|所有客户共享同一份稳定 SDK,支持成本集中在 SDK 本身||**学习门槛**|客户需要理解 BSP 内部结构才能上手,10分钟跑不起来|通过 samples/docs/tools 让客户10分钟内跑起来||**可交付性**|只是源码包,缺少工具链、文档、烧录调试工具、版本锁定|是经过验证的完整开发环境(含 toolchain/samples/docs/manifest/SBOM)|**简要说明**:两种方式的本质区别在于「客户依赖什么」。直接给 BSP 仓库时,客户被迫依赖 BSP 的内部实现细节,这些细节不属于稳定接口,一旦 BSP 演进就会破坏客户代码,且每个客户各自 fork 导致维护成本失控。而 Customer SDK 通过「稳定接口边界」把内部实现与客户代码解耦,客户只依赖受版本承诺保护的 Public API,公司可以自由重构内部实现而不惊动客户,同时 SDK 作为完整交付物(工具链、示例、文档、版本锁定、SBOM)显著降低了客户的上手门槛与公司的支持成本。 Internal BSP │ │ Stable Interface ▼ Customer SDK │ ▼ Customer Application

2. Customer SDK 到底包含什么?

一个完整的 SDK 通常包括:

Customer SDK │ ├── Toolchain │ ├── Zephyr/BSP │ ├── Board Support │ ├── Device Drivers │ ├── SDK Headers │ ├── SDK Libraries │ ├── Samples │ ├── Documentation │ ├── Build Tools │ ├── Flash Tools │ ├── Debug Tools │ ├── Test Framework │ └── Release Metadata

但这里要注意:
不是所有 BSP 内部文件都应该暴露给客户。
下面是一个完整的 Customer SDK 顶层目录树示例。我们用注释标注每个目录的用途,并用[客户可见]/[内部保留]明确哪些目录客户可以直接使用、哪些仅供公司内部维护:

company-sdk/│ ├── toolchain/#[客户可见]经过验证的工具链(GCC/CMake/Python/west) │ ├── bin/# 编译器与工具可执行文件 │ ├── lib/# 运行时库 │ └── include/# 编译器内置头文件 │ ├── zephyr/#[客户可见]Zephyr 内核+Company BSP 源码 │ ├── kernel/# Zephyr 内核实现 │ ├── drivers/# 驱动框架与 Company 驱动 │ ├── dts/# Devicetree 源文件 │ ├── soc/# SoC 支持 │ └── boards/# 板级定义(见下方 boards/) │ ├── boards/#[客户可见]Board Catalog,客户用-b 指定 │ ├── company_devkit/# 开发板定义(dts、Kconfig、defconfig) │ ├── company_devkit_pro/│ ├── company_eval/│ └── company_reference/│ ├── include/#[客户可见]SDK Public API 头文件 │ └── company/│ ├── version.h # 版本信息 │ ├── power.h # 电源管理 API │ ├── security.h # 安全 API │ └── device_info.h # 设备信息 API │ ├── lib/#[客户可见]SDK 预编译库/源码库 │ └── company/# Company 提供的静态/动态库 │ ├── samples/#[客户可见]示例工程,客户学习入口 │ ├── hello_world/# 最小串口打印 │ ├── blinky/# GPIO 输出 │ ├── gpio/# GPIO 输入/中断 │ ├── uart/# UART 通信 │ ├── i2c/# I2C 外设 │ ├── spi/# SPI 外设 │ ├── adc/# ADC 采样 │ ├── pwm/# PWM 输出 │ ├── timer/# 定时器 │ ├── usb/# USB 设备 │ └── power_management/# 低功耗管理 │ ├── docs/#[客户可见]SDK 文档 │ ├── getting_started/# 快速上手 │ ├── installation/# 安装指南 │ ├── supported_boards/# 支持的板卡列表 │ ├── migration_guide/# 迁移指南(SDK1.x →2.x) │ └── release_notes/# 版本发布说明 │ ├── scripts/#[内部保留]构建/打包/发布脚本 │ ├── build/# 内部构建脚本 │ ├── package/# 打包脚本 │ └── release/# 发布流水线脚本 │ ├── tools/#[客户可见]客户使用的辅助工具 │ ├── flash/# west flash 封装/company flash │ ├── debug/# company debug(GDB+OpenOCD/J-Link) │ └── create/# company-sdk create 工程模板工具 │ ├── manifest/#[客户可见]west manifest,锁定版本组合 │ └── west.yml # Zephyr/HAL/BSP/三方模块版本 │ ├── modules/#[内部保留]内部模块(不直接暴露给客户) │ ├── hal_company/# Company HAL 源码 │ └── company_sdk/# SDK 内部实现 │ ├── tests/#[内部保留]内部测试与 CI │ ├── unit/# 单元测试 │ ├── regression/# 回归测试 │ └── hil/# 硬件在环测试 │ ├── licenses/#[客户可见]许可证文件 │ └── LICENSE-company.txt # Company 许可证 │ ├── sbom/#[客户可见]软件物料清单 │ └── company-sdk-2.1.0.spdx # SPDX 格式 SBOM │ ├── VERSION #[客户可见]SDK 版本号 └── README.md #[客户可见]SDK 总览与快速开始

目录可见性小结

目录客户可见用途
toolchain/✅经过验证的工具链组合
zephyr/✅Zephyr 内核 + Company BSP
boards/✅板卡目录,-b company_devkit指定
include/✅SDK Public API 头文件
lib/✅SDK 库
samples/✅示例工程,学习入口
docs/✅文档与迁移指南
tools/✅flash / debug / create 工具
manifest/✅west manifest,锁定版本
licenses/✅许可证
sbom/✅软件物料清单
scripts/❌内部构建/发布脚本
modules/❌内部 HAL 与 SDK 实现
tests/❌内部测试与 CI

2.1 Customer SDK 的发布与交付流程

上一节从目录层面看清了 SDK 的组成。这一节我们把视角切换到「时间轴」:一个 SDK 版本从 BSP 内部开发到客户真正拿到手,中间要经过哪些环节,每个环节又设置了怎样的质量门禁。

下面是完整的发布与交付流程:

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/29 3:37:34

医学图像跨模态转换:配准伪配对与扩散模型训练流程

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/29 3:36:57

汽车电子从ECU到诊断:嵌入式开发、Simulink与故障注入全解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/29 3:36:40

基于SpringBoot的勤工俭学系统:毕业设计实战与答辩全攻略

每年到三月,我这边就会密集收到一类私信:学长,计算机毕业设计到底选什么题?SpringBoot的题目是不是烂大街了?然后聊到最后,总会有人补一句,"有没有那种功能看着不low、工作量适中、答辩还不…

作者头像 李华
网站建设 2026/9/29 3:36:00

别再用 JSON.parse 深拷贝了,聊聊 StructuredClone 与 TaoToken 配置骨架

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华