1 Yocto Project 板级支持包(BSP)手册

板级支持包(BSP)定义如何支持特定设备、设备集合或硬件平台,包括硬件功能、 必需的引导加载程序、内核和设备树配置,以及额外驱动。它还列出通用 Linux 软件栈之外,为平台必需或可选功能提供支持的软件组件。

本指南介绍 BSP 层、统一组件布局、配方定制、许可问题,以及如何用 bitbake-layers 创建层。

1 BSP 层

BSP 是基础目录中的一套文件结构,整体称为 BSP 层。虽非强制,通常采用:

meta-bsp_root_name

即在机器或平台名称 bsp_root_name 前加 meta-。

备注

建议遵循该惯例,虽然技术上无需此前缀,但多个脚本和工具会作此假定。

项目各发行版提供的 BSP 可在 Yocto Project 源码仓库 的 https://git.yoctoproject.org/ 界面查看,位于 Yocto Metadata Layers 分组。

备注

不再活跃支持的层放在 Yocto Metadata Layer Archive。

meta-raspberrypi、meta-intel 等各自是独立仓库,点击名称可看到两个克隆 URL。 例如克隆 Raspberry Pi 层:

$ git clone https://git.yoctoproject.org/meta-raspberrypi

此外,meta-yocto 中的 meta-yocto-bsp 维护参考 BSP, 包括 ARM Beaglebone 和通用 32 位、64 位 IA 机器。

开发流程见 开发板级支持包(BSP), 本地仓库准备见 手动设置 Poky 参考发行版。

层根目录 meta-bsp_root_name 应加入 BBLAYERS,位置为运行 oe-init-build-env 后建立的 Build Directory 中 build/conf/bblayers.conf。这样构建系统才能识别该层并生成 镜像。例如:

BBLAYERS ?= " \
   /usr/local/src/yocto/meta \
   /usr/local/src/yocto/meta-poky \
   /usr/local/src/yocto/meta-yocto-bsp \
   /usr/local/src/yocto/meta-mylayer \
   "

备注

BBLAYERS 顺序和 BBFILE_PRIORITY 都有影响。例如多个层定义机器 配置且优先级相近时,使用最后搜索到的层。搜索按列表从上到下进行。

如果 BSP 还依赖其他层,应在根层 README 的 Dependencies 中列出,并加入 相关构建说明。

有些层用于容纳其他层,称为 容器层。例如 meta-openembedded 包含多个 meta-*。此时要 加入实际需要的子层,例如:

BBLAYERS ?= " \
  /usr/local/src/yocto/meta \
  /usr/local/src/yocto/meta-poky \
  /usr/local/src/yocto/meta-yocto-bsp \
  /usr/local/src/yocto/meta-mylayer \
  .../meta-openembedded/meta-oe \
  .../meta-openembedded/meta-perl \
  .../meta-openembedded/meta-networking \
  "

其他子层同理。更多信息见 “理解和创建层”。

1 准备使用 BSP 层的构建主机

主机准备好后,可按 “使用 bitbake-layers 创建新 BSP 层” 创建层。

备注

BSP 结构见 文件系统布局示例。

  1. 设置构建环境: 确保 Shell 可用 BitBake,见 “准备构建主机”。

  2. 准备源码仓库:

    设置 Poky 有两种方式:

  3. 确定所需 BSP 层: BSP 可独立维护,也可多个放在一层, 层索引 可帮助查找。

  4. 按需克隆 meta-intel: 当前 Intel CPU 和设备通常可利用此层,详情见 README。

    1. 选择源码位置: 通常放在构建中的其他层旁边。

    2. 克隆:

      $ git clone https://git.yoctoproject.org/meta-intel.git
      Cloning into 'meta-intel'...
      remote: Counting objects: 15585, done.
      remote: Compressing objects: 100% (5056/5056), done.
      remote: Total 15585 (delta 9123), reused 15329 (delta 8867)
      Receiving objects: 100% (15585/15585), 4.51 MiB | 3.19 MiB/s, done.
      Resolving deltas: 100% (9123/9123), done.
      Checking connectivity... done.
      
    3. 检出匹配分支: 必须与项目发行分支一致,例如 blacksail:

      $ cd meta-intel
      $ git checkout -b blacksail remotes/origin/blacksail
      Branch blacksail set up to track remote branch
      blacksail from origin.
      Switched to a new branch 'blacksail'
      

      备注

      git branch -a 可列出可用分支。

  5. 按需选择其他 BSP: 如果硬件更接近其他已有 BSP,按同样方法克隆,仅 仓库名称不同。例如 Raspberry Pi:

    $ git clone https://git.yoctoproject.org/meta-raspberrypi
    Cloning into 'meta-raspberrypi'...
    remote: Counting objects: 4743, done.
    remote: Compressing objects: 100% (2185/2185), done.
    remote: Total 4743 (delta 2447), reused 4496 (delta 2258)
    Receiving objects: 100% (4743/4743), 1.18 MiB | 0 bytes/s, done.
    Resolving deltas: 100% (2447/2447), done.
    Checking connectivity... done.
    
  6. 初始化环境: 在源码目录运行 OE-Core 的 oe-init-build-env:

    $ source layers/openembedded-core/oe-init-build-env
    

    脚本创建 build 等内容,并切换当前工作目录到构建目录。

    备注

    也可加载 bitbake-setup 提供的 init-build-env。

1 文件系统布局示例

通用 BSP 目录结构便于用户熟悉,也促进硬件软件支持的标准化。

虽然以下形式包含 OpenEmbedded 专用元素,也希望其他构建系统能使用,且信息 易于提取和转换。通过标准 层机制, 构建系统可直接接受此格式。BSP 在一处按标准保存全部硬件细节,对使用任意 构建系统的平台用户都有价值。

BSP 规范仅涉及硬件组件,不包含构建系统或其他工具。最终产品可将它们组合 分发,但应始终明确三者是独立组件。

符合项目要求的 BSP 层还需满足 “发布要求”。

典型结构如下,实际 BSP 布局可以有所不同:

meta-bsp_root_name/
meta-bsp_root_name/bsp_license_file
meta-bsp_root_name/README
meta-bsp_root_name/README.sources
meta-bsp_root_name/binary/bootable_images
meta-bsp_root_name/conf/layer.conf
meta-bsp_root_name/conf/machine/*.conf
meta-bsp_root_name/recipes-bsp/*
meta-bsp_root_name/recipes-core/*
meta-bsp_root_name/recipes-graphics/*
meta-bsp_root_name/recipes-kernel/linux/linux-yocto_kernel_rev.bbappend

以下是 源码仓库 中 Raspberry Pi 层的实例:

meta-raspberrypi/COPYING.MIT
meta-raspberrypi/README.md
meta-raspberrypi/classes
meta-raspberrypi/classes/sdcard_image-rpi.bbclass
meta-raspberrypi/conf/
meta-raspberrypi/conf/layer.conf
meta-raspberrypi/conf/machine/
meta-raspberrypi/conf/machine/raspberrypi-cm.conf
meta-raspberrypi/conf/machine/raspberrypi-cm3.conf
meta-raspberrypi/conf/machine/raspberrypi.conf
meta-raspberrypi/conf/machine/raspberrypi0-wifi.conf
meta-raspberrypi/conf/machine/raspberrypi0.conf
meta-raspberrypi/conf/machine/raspberrypi2.conf
meta-raspberrypi/conf/machine/raspberrypi3-64.conf
meta-raspberrypi/conf/machine/raspberrypi3.conf
meta-raspberrypi/conf/machine/include
meta-raspberrypi/conf/machine/include/rpi-base.inc
meta-raspberrypi/conf/machine/include/rpi-default-providers.inc
meta-raspberrypi/conf/machine/include/rpi-default-settings.inc
meta-raspberrypi/conf/machine/include/rpi-default-versions.inc
meta-raspberrypi/conf/machine/include/tune-arm1176jzf-s.inc
meta-raspberrypi/docs
meta-raspberrypi/docs/Makefile
meta-raspberrypi/docs/conf.py
meta-raspberrypi/docs/contributing.md
meta-raspberrypi/docs/extra-apps.md
meta-raspberrypi/docs/extra-build-config.md
meta-raspberrypi/docs/index.rst
meta-raspberrypi/docs/layer-contents.md
meta-raspberrypi/docs/readme.md
meta-raspberrypi/files
meta-raspberrypi/files/custom-licenses
meta-raspberrypi/files/custom-licenses/Broadcom
meta-raspberrypi/recipes-bsp
meta-raspberrypi/recipes-bsp/bootfiles
meta-raspberrypi/recipes-bsp/bootfiles/bcm2835-bootfiles.bb
meta-raspberrypi/recipes-bsp/bootfiles/rpi-config_git.bb
meta-raspberrypi/recipes-bsp/common
meta-raspberrypi/recipes-bsp/common/firmware.inc
meta-raspberrypi/recipes-bsp/formfactor
meta-raspberrypi/recipes-bsp/formfactor/formfactor
meta-raspberrypi/recipes-bsp/formfactor/formfactor/raspberrypi
meta-raspberrypi/recipes-bsp/formfactor/formfactor/raspberrypi/machconfig
meta-raspberrypi/recipes-bsp/formfactor/formfactor_%.bbappend
meta-raspberrypi/recipes-bsp/rpi-u-boot-src
meta-raspberrypi/recipes-bsp/rpi-u-boot-src/files
meta-raspberrypi/recipes-bsp/rpi-u-boot-src/files/boot.cmd.in
meta-raspberrypi/recipes-bsp/rpi-u-boot-src/rpi-u-boot-scr.bb
meta-raspberrypi/recipes-bsp/u-boot
meta-raspberrypi/recipes-bsp/u-boot/u-boot
meta-raspberrypi/recipes-bsp/u-boot/u-boot/*.patch
meta-raspberrypi/recipes-bsp/u-boot/u-boot_%.bbappend
meta-raspberrypi/recipes-connectivity
meta-raspberrypi/recipes-connectivity/bluez5
meta-raspberrypi/recipes-connectivity/bluez5/bluez5
meta-raspberrypi/recipes-connectivity/bluez5/bluez5/*.patch
meta-raspberrypi/recipes-connectivity/bluez5/bluez5/BCM43430A1.hcd
meta-raspberrypi/recipes-connectivity/bluez5/bluez5brcm43438.service
meta-raspberrypi/recipes-connectivity/bluez5/bluez5_%.bbappend
meta-raspberrypi/recipes-core
meta-raspberrypi/recipes-core/images
meta-raspberrypi/recipes-core/images/rpi-basic-image.bb
meta-raspberrypi/recipes-core/images/rpi-hwup-image.bb
meta-raspberrypi/recipes-core/images/rpi-test-image.bb
meta-raspberrypi/recipes-core/packagegroups
meta-raspberrypi/recipes-core/packagegroups/packagegroup-rpi-test.bb
meta-raspberrypi/recipes-core/psplash
meta-raspberrypi/recipes-core/psplash/files
meta-raspberrypi/recipes-core/psplash/files/psplash-raspberrypi-img.h
meta-raspberrypi/recipes-core/psplash/psplash_git.bbappend
meta-raspberrypi/recipes-core/udev
meta-raspberrypi/recipes-core/udev/udev-rules-rpi
meta-raspberrypi/recipes-core/udev/udev-rules-rpi/99-com.rules
meta-raspberrypi/recipes-core/udev/udev-rules-rpi.bb
meta-raspberrypi/recipes-devtools
meta-raspberrypi/recipes-devtools/bcm2835
meta-raspberrypi/recipes-devtools/bcm2835/bcm2835_1.52.bb
meta-raspberrypi/recipes-devtools/pi-blaster
meta-raspberrypi/recipes-devtools/pi-blaster/files
meta-raspberrypi/recipes-devtools/pi-blaster/files/*.patch
meta-raspberrypi/recipes-devtools/pi-blaster/pi-blaster_git.bb
meta-raspberrypi/recipes-devtools/python
meta-raspberrypi/recipes-devtools/python/python-rtimu
meta-raspberrypi/recipes-devtools/python/python-rtimu/*.patch
meta-raspberrypi/recipes-devtools/python/python-rtimu_git.bb
meta-raspberrypi/recipes-devtools/python/python-sense-hat_2.2.0.bb
meta-raspberrypi/recipes-devtools/python/rpi-gpio
meta-raspberrypi/recipes-devtools/python/rpi-gpio/*.patch
meta-raspberrypi/recipes-devtools/python/rpi-gpio_0.6.3.bb
meta-raspberrypi/recipes-devtools/python/rpio
meta-raspberrypi/recipes-devtools/python/rpio/*.patch
meta-raspberrypi/recipes-devtools/python/rpio_0.10.0.bb
meta-raspberrypi/recipes-devtools/wiringPi
meta-raspberrypi/recipes-devtools/wiringPi/files
meta-raspberrypi/recipes-devtools/wiringPi/files/*.patch
meta-raspberrypi/recipes-devtools/wiringPi/wiringpi_git.bb
meta-raspberrypi/recipes-graphics
meta-raspberrypi/recipes-graphics/eglinfo
meta-raspberrypi/recipes-graphics/eglinfo/eglinfo-fb_%.bbappend
meta-raspberrypi/recipes-graphics/eglinfo/eglinfo-x11_%.bbappend
meta-raspberrypi/recipes-graphics/mesa
meta-raspberrypi/recipes-graphics/mesa/mesa-gl_%.bbappend
meta-raspberrypi/recipes-graphics/mesa/mesa_%.bbappend
meta-raspberrypi/recipes-graphics/userland
meta-raspberrypi/recipes-graphics/userland/userland
meta-raspberrypi/recipes-graphics/userland/userland/*.patch
meta-raspberrypi/recipes-graphics/userland/userland_git.bb
meta-raspberrypi/recipes-graphics/vc-graphics
meta-raspberrypi/recipes-graphics/vc-graphics/files
meta-raspberrypi/recipes-graphics/vc-graphics/files/egl.pc
meta-raspberrypi/recipes-graphics/vc-graphics/files/vchiq.sh
meta-raspberrypi/recipes-graphics/vc-graphics/vc-graphics-hardfp.bb
meta-raspberrypi/recipes-graphics/vc-graphics/vc-graphics.bb
meta-raspberrypi/recipes-graphics/vc-graphics/vc-graphics.inc
meta-raspberrypi/recipes-graphics/wayland
meta-raspberrypi/recipes-graphics/wayland/weston_%.bbappend
meta-raspberrypi/recipes-graphics/xorg-xserver
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi/xorg.conf
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi/xorg.conf.d
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi/xorg.conf.d/10-evdev.conf
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi/xorg.conf.d/98-pitft.conf
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config/rpi/xorg.conf.d/99-calibration.conf
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xf86-config_0.1.bbappend
meta-raspberrypi/recipes-graphics/xorg-xserver/xserver-xorg_%.bbappend
meta-raspberrypi/recipes-kernel
meta-raspberrypi/recipes-kernel/linux-firmware
meta-raspberrypi/recipes-kernel/linux-firmware/files
meta-raspberrypi/recipes-kernel/linux-firmware/files/brcmfmac43430-sdio.bin
meta-raspberrypi/recipes-kernel/linux-firmware/files/brcfmac43430-sdio.txt
meta-raspberrypi/recipes-kernel/linux-firmware/linux-firmware_%.bbappend
meta-raspberrypi/recipes-kernel/linux
meta-raspberrypi/recipes-kernel/linux/linux-raspberrypi-dev.bb
meta-raspberrypi/recipes-kernel/linux/linux-raspberrypi.inc
meta-raspberrypi/recipes-kernel/linux/linux-raspberrypi_4.14.bb
meta-raspberrypi/recipes-kernel/linux/linux-raspberrypi_4.9.bb
meta-raspberrypi/recipes-multimedia
meta-raspberrypi/recipes-multimedia/gstreamer
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-omx
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-omx/*.patch
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-omx_%.bbappend
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-plugins-bad_%.bbappend
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-omx-1.12
meta-raspberrypi/recipes-multimedia/gstreamer/gstreamer1.0-omx-1.12/*.patch
meta-raspberrypi/recipes-multimedia/omxplayer
meta-raspberrypi/recipes-multimedia/omxplayer/omxplayer
meta-raspberrypi/recipes-multimedia/omxplayer/omxplayer/*.patch
meta-raspberrypi/recipes-multimedia/omxplayer/omxplayer_git.bb
meta-raspberrypi/recipes-multimedia/x264
meta-raspberrypi/recipes-multimedia/x264/x264_git.bbappend
meta-raspberrypi/wic
meta-raspberrypi/wic/sdimage-raspberrypi.wks

下面逐项解释。

1 许可证文件

位置为:

meta-bsp_root_name/bsp_license_file

这些可选文件满足 BSP 许可要求,形式视具体许可而定。例如 Raspberry Pi 通过 COPYING.MIT 处理。

可以是 MIT、BSD、GPLv* 等,建议提供,但此处格式由开发者决定。合规方法见 “在产品生命周期中维护开源许可证合规”。

1 README 文件

位置为:

meta-bsp_root_name/README

说明如何启动 binary/ 中可选的 live 镜像,以及如何构建。

至少必须包含依赖列表,例如其他必需层,以及维护者姓名和联系方式。

1 README.sources 文件

位置为:

meta-bsp_root_name/README.sources

说明用于构建 meta-bsp_root_name/binary 中随 BSP 发布镜像的源码位置,也 帮助找到生成镜像的元数据。

备注

没有 binary 目录或其中没有镜像时,README.sources 没有意义,通常不存在。

1 预构建用户二进制文件

位置为:

meta-bsp_root_name/binary/bootable_images

此可选区域包含适合目标的预构建内核和用户空间文件系统镜像。网站发布的 BSP 归档通常包含图形镜像,例如 Sato,以及最小 live 镜像,便于快速启动开发。

具体二进制类型取决于硬件。层中应有 README 说明用法,以及 README.sources 指明源码和元数据。

1 层配置文件

位置为:

meta-bsp_root_name/conf/layer.conf

conf/layer.conf 将目录识别为层,说明内容和使用方式。通常标准模板即可, 将 bsp 替换为实际 bsp_root_name:

# We have a conf and classes directory, add to BBPATH
BBPATH .= ":${LAYERDIR}"

# We have a recipes directory containing .bb and .bbappend files, add to BBFILES
BBFILES += "${LAYERDIR}/recipes-*/*/*.bb \
            ${LAYERDIR}/recipes-*/*/*.bbappend"

BBFILE_COLLECTIONS += "bsp"
BBFILE_PATTERN_bsp = "^${LAYERDIR}/"
BBFILE_PRIORITY_bsp = "6"
LAYERDEPENDS_bsp = "intel"

Raspberry Pi 对应语句如下:

# We have a conf and classes directory, append to BBPATH
BBPATH .= ":${LAYERDIR}"

# We have a recipes directory containing .bb and .bbappend files, add to BBFILES
BBFILES += "${LAYERDIR}/recipes*/*/*.bb \
            ${LAYERDIR}/recipes*/*/*.bbappend"

BBFILE_COLLECTIONS += "raspberrypi"
BBFILE_PATTERN_raspberrypi := "^${LAYERDIR}/"
BBFILE_PRIORITY_raspberrypi = "9"

# Additional license directories.
LICENSE_PATH += "${LAYERDIR}/files/custom-licenses"
.
.
.

此文件告诉 BitBake 配方和配置目录,必须存在,系统才能识别 BSP。

1 硬件配置选项

位置为:

meta-bsp_root_name/conf/machine/*.conf

机器配置将 BSP 其他位置的信息组合为构建系统可理解的形式。至少需要一个, 支持多机器时可有多个,文件名对应 MACHINE 的值。

其中定义内核提供者,即 virtual/kernel 的 PREFERRED_PROVIDER、不同镜像所需驱动、特殊组件、引导加载程序及 镜像格式要求。

还可包含硬件调优文件,用于定义包架构和优化标志,以获得处理器最佳性能。 调优文件位于 OE-Core 的 meta/conf/machine/include,例如 tune-arm1136jf-s.inc、tune-1586-nlp.inc 等。

在机器配置中直接包含即可,例如 Raspberry Pi 的 raspberrypi3.conf:

include conf/machine/include/rpi-base.inc

1 其他 BSP 专用配方文件

位置为:

meta-bsp_root_name/recipes-bsp/*

此可选目录保存杂项 BSP 配方,典型是 formfactor。例如 Raspberry Pi 的 formfactor_%.bbappend 扩展主配方,机器设置由下级 machconfig 定义:

HAVE_TOUCHSCREEN=0
HAVE_KEYBOARD=1

DISPLAY_CAN_ROTATE=0
DISPLAY_ORIENTATION=0
DISPLAY_DPI=133

备注

未提供 formfactor 时,使用 OE-Core 主配方 meta/recipes-bsp/formfactor/formfactor_0.0.bb 安装的默认配置。

1 显示支持文件

位置为:

meta-bsp_root_name/recipes-graphics/*

此可选目录保存特殊图形支持配方,以及 BSP 支持显示所需全部文件。

1 Linux 内核配置

位置为:

meta-bsp_root_name/recipes-kernel/linux/linux*.bbappend
meta-bsp_root_name/recipes-kernel/linux/*.bb

追加文件修改现有内核配方,.bb 则为开发者提供的内核配方。两者可共存,但 实际通常二选一。

一般使用 OE-Core 的 meta/recipes-kernel/linux 中已有配方,再在 BSP 层 同类目录用同名追加文件加入机器定制。

假设使用 linux-yocto_6.12.bb,即在 bsp_root_name.conf 中设置:

PREFERRED_PROVIDER_virtual/kernel ?= "linux-yocto"
PREFERRED_VERSION_linux-yocto ?= "6.12%"

备注

默认已选定提供者时,机器配置可不出现 PREFERRED_PROVIDER。

通过 linux-yocto_6.12.bbappend 添加 BSP 设置,内容要求见 “创建追加文件”。

也可自行提供内核配方,例如 Raspberry Pi 层中有:

files/
linux-raspberrypi_6.12.bb
linux-raspberrypi_6.1.bb
linux-raspberrypi_6.6.bb
linux-raspberrypi-dev.bb
linux-raspberrypi.inc
linux-raspberrypi-v7_6.12.bb
linux-raspberrypi-v7_6.1.bb
linux-raspberrypi-v7_6.6.bb
linux-raspberrypi-v7.inc

1 开发板级支持包(BSP)

下面介绍总体流程。示例使用包含许多 BSP 的 meta-intel,但创建 BSP 并不 要求使用它。工具建层示例见 “使用 bitbake-layers 创建新 BSP 层”。

流程如下:

../_images/bsp-dev-flow.png
  1. 准备开发主机: 见 “准备构建主机”。

  2. 准备 meta-intel 本地仓库: 便于复用受支持 BSP,获取方法见 “准备使用 BSP 层的构建主机”。

  3. 使用 bitbake-layers 创建 BSP 层: 层用于隔离保存硬件配方和配置,BSP 本身就是特殊层。最简单的标准建层方法见 “使用 bitbake-layers 创建新 BSP 层”。

    应用也可有自己的层,存放编译和运行所需依赖配方。层的关键是将构建系统 知道的相关项隔离在独立区域。详见 “Yocto Project 层模型”、 “理解和创建层” 和 “BSP 层”。

    备注

    • meta-yocto-bsp 提供四个 硬件参考 BSP:

      • TI Beaglebone(beaglebone-yocto)

      • 两个通用 IA 平台(genericx86、genericx86-64)

      • 通用 ARM64 平台(genericarm64)

    新层应遵循 “文件系统布局示例” 的配方和 配置结构,也可参考 meta-intel 中任一 BSP。

  4. 修改配置: 文件在 conf 和各 recipes-* 目录中组织,配置说明新层位置 和使用的内核。bitbake-layers 可交互配置键盘、触摸屏等 BSP 项目。

  5. 修改配方: 调整 .bb,删除不用的配方,并添加支持硬件的新配方或追加文件。

  6. 准备构建: 加载 oe-init-build-env,正确设置 build/conf/local.conf 和 build/conf/bblayers.conf。告知系统新层的方法见 “启用层”。

  7. 构建镜像: 用 BitBake 生成所需类型,工具说明见 BitBake 用户手册,镜像类型见 “镜像”。

1 已发布 BSP 的要求与建议

本节介绍已发布 BSP 符合 Yocto Project 所需要求及建议。

1 发布要求

首先注意:

  • 假定 BSP 已是合法且结构良好的层,基础要求见 “BSP 层” 和 “理解和创建层”。

  • 不论如何打包,要求都适用。还应遵循具体发行流程的打包分发规则,例如 第三方 BSP 发布流程。

  • 开发者工作形式与正式交付形式独立。例如 Git 仓库内目录结构可以完全不同 于最终发布层。

  • 除一般兼容要求外,不强制特定包或修改,也不要求特定内核或版本。

发布 BSP 必须满足:

  • 层名称: 遵循项目标准,见 “BSP 层”。

  • 文件布局: 尽量采用 OE-Core meta 中 recipes.txt 指定的目录名。

    按功能将 .bb 和 .bbappend 放在 recipes-*。找不到适合类别时可自建。 每类内部布局与 OE-Core 一致,将相关文件放在与功能相符目录,或紧密 相关配方的共同子目录。配方遵循 “配方风格指南”。

  • 许可证: 根目录必须包含覆盖整个 BSP 元数据的许可文件,没有默认许可, 必须明确指定。示例见 Raspberry Pi 的 COPYING.MIT。

  • README: 根目录必须提供,示例见 README.md,至少包含:

    • 目标硬件简介。

    • 全部依赖,通常为必需层,也包括其他依赖。

    • 特殊许可信息,例如接受 EULA 所需变量,构建或分发二进制的相关说明。

    • 维护者姓名和联系方式,供发送补丁和问题。查找方法见 向组件贡献修改。

    • 用该层构建 BSP 的说明。

    • 启动构建结果的说明。

    • 如有 binary 镜像,其启动说明。

    • 构建或启动时应注意的已知问题。

  • README.sources: 如果 binary 中有镜像,根目录必须包含此文件,准确 指明生成二进制的源码位置。

  • 层配置: 根目录必须有 conf/layer.conf,让系统识别 BSP 层。

  • 机器配置: 必须有一个或多个 conf/machine/bsp_root_name.conf,定义 可构建目标。多个文件用于支持的机器变体,需在 README 充分说明。不要用 同一 BSP 的多个配置描述毫不相关硬件;差异很大的目标应分别建层。

    备注

    开发仓库可以混合无关 BSP,再通过脚本生成发布包,例如 meta-yocto-bsp, 但这种组织不在本文范围内。

1 发布建议

建议包括:

  • 可启动镜像: 可随 BSP 发布一个或多个镜像,便于用户在硬件试用。

    如果不便,可提供带镜像和不带镜像两个版本,避免不需要镜像的用户额外下载。 供评估启动的镜像、内核和文件系统产物应放在根目录 binary/。

    备注

    镜像若使用 GPL 或其他开源许可软件,发布者负责理解并满足全部要求, 可能包括提供源码。

  • 使用 Yocto Linux 内核: 以项目内核为基础可降低维护成本并提高扩展性, 见 源码仓库 的 Yocto Linux Kernel 分类。

1 为 BSP 定制配方

需要:

  • 为要修改的配方创建 .bbappend,见 “通过自己的层追加其他层元数据”。

  • 保证层目录结构能被构建系统搜索到,见下例。

  • 将追加文件放在适当 recipes-bsp、recipes-graphics、recipes-core 等 子目录下,与机器名称相符的目录中。

  • 将 BSP 专用文件放到适当位置。层支持多机器时,需有按机器隔离的目录层级; 单机器层则不需要额外层级。

例如,为支持多机器的层中 xyz 机器的 init-ifupdown_1.0.bb 添加专用 interfaces 配置:

  1. 编辑 init-ifupdown_1.0.bbappend:

    FILESEXTRAPATHS:prepend := "${THISDIR}/files:"
    

    文件放在 meta-xyz/recipes-core/init-ifupdown。

  2. 新 interfaces 文件放在:

    meta-xyz/recipes-core/init-ifupdown/files/xyz-machine-one/interfaces
    

    备注

    若层只支持一台机器,则放在:

    meta-xyz/recipes-core/init-ifupdown/files/interfaces
    

    FILESEXTRAPATHS 扩展搜索路径,因此 files 目录应与追加文件同级。

1 BSP 许可注意事项

某些 BSP 含单独授权的知识产权组件,需要显式接受商业或其他最终用户许可协议 (EULA)后才能构建并纳入镜像。预构建镜像也可能要求同意许可后才能下载。

有些核心组件没有不受限制或自由的替代品,缺少它们系统无法工作;有些可选 组件则有自由替代。即使是必需组件,也可能有能力较弱但仍可用的替代实现。

如果自由替代仍满足功能,网站 SOFTWARE 下 DOWNLOADS 提供去除受限功能的 BSP, 无需额外许可,名称也与受限版区分。若可用且满足需求,这是最简单、优先选择。

备注

若没有不受限制的版本,或其功能、质量不适用,也可使用受限版本。

构建系统提供两种方式满足许可要求,按推荐顺序为:

  1. 使用 LICENSE_FLAGS: 配方标明商业或特殊许可,在 local.conf 的 LICENSE_FLAGS_ACCEPTED 添加匹配字符串,表示接受许可,允许构建 并加入镜像。详见 “启用商业许可配方”。

    未设置时,构建停止并列出需要接受许可的配方。添加适当标志后重新启动, 从中断处继续,已满足要求后不再提示。

    配置好接受列表后,正常构建流程无需其他改变。

  2. 获取预构建 BSP: 从 项目网站 SOFTWARE 的 DOWNLOADS 下载,在下载流程中分别接受各受限组件的协议,即可立即获得镜像。若还要 根据归档中的配方自行构建,仍需设置匹配的 LICENSE_FLAGS_ACCEPTED。

备注

预构建镜像附带限时内核,运行 10 天后强制重启,以避免直接重新分发。 要移除此限制,最终仍需自行重建镜像。

1 使用 bitbake-layers 创建新 BSP 层

create-layer 自动创建基础层。BSP 层的核心特征是至少一个机器配置,通常还 包含内核配方或追加文件,但后者并非首要要求。

步骤如下:

  • 创建通用层: 使用 create-layer,见 “创建自己的层”。

  • 创建层配置: layer.conf 指定配方位置、优先级等。可参考 源码仓库 中其他层,例如 meta-ti 的 layer.conf。

  • 创建机器配置: 建立 conf/machine/bsp_root_name.conf。示例见 meta-yocto-bsp/conf/machine, 其他厂商更具体的机器和调优示例见 meta-ti 和 meta-freescale。

  • 创建内核配方: 在 recipes-kernel/linux 添加追加文件或新配方,例如 linux-yocto_6.12.bb。上述层也有不同示例,定制方法见 “修改已有配方”。

下面以 meta-yocto-bsp 中的 Beaglebone 参考 BSP 为例。

1 BSP 层配置示例

conf/layer.conf 内容如下:

# We have a conf and classes directory, add to BBPATH
BBPATH .= ":${LAYERDIR}"

# We have a recipes directory containing .bb and .bbappend files, add to BBFILES
BBFILES += "${LAYERDIR}/recipes-*/*/*.bb \
            ${LAYERDIR}/recipes-*/*/*.bbappend"

BBFILE_COLLECTIONS += "yoctobsp"
BBFILE_PATTERN_yoctobsp = "^${LAYERDIR}/"
BBFILE_PRIORITY_yoctobsp = "5"
LAYERVERSION_yoctobsp = "4"
LAYERSERIES_COMPAT_yoctobsp = "blacksail"

各变量定义层配置。阅读 源码仓库 中不同 BSP 是很好的学习方式。 此文件详细介绍见建层讨论的 “第三步”。

1 BSP 机器配置示例

至少一个机器配置,使 BSP 层区别于通用层或内核层。

例如,meta-yocto-bsp 的 conf 目录:

$ tree -F conf
conf/
├── layer.conf
└── machine/
    ├── beaglebone-yocto.conf
    ├── genericarm64.conf
    ├── genericx86-64.conf
    ├── genericx86.conf
    └── include/
        └── genericx86-common.inc

包含四个机器配置及一个下级调优配置。变量定义机器专用包、调优、内核类型及 U-Boot 等属性。

以下解释 BeagleBone 参考配置。实际还可定义更多内容,其他变量见 “变量表”。

  • PREFERRED_PROVIDER_virtual/xserver:多个提供者 中选择 xserver。本例为 OE-Core meta/recipes-graphics/xorg-xserver 中的 xserver-xorg。

  • MACHINE_EXTRA_RRECOMMENDS:非启动必需、但完整功能需要的机器包。 缺少时不导致构建失败。

    小技巧

    有许多 MACHINE* 变量可配置硬件。

  • EXTRA_IMAGEDEPENDS:镜像构建依赖但不向根文件系统安装包的配方。 本例需要 U-Boot;文件末尾也用它实现主机 runqemu 支持。

  • DEFAULTTUNE:调优优化机器、CPU 和应用性能,相关特性由 OE-Core 定义。本例默认采用 tune-cortexa8。

    备注

    引入 conf/machine/include/arm/tune-cortexa8.inc 可提供多种调优选择。

  • IMAGE_FSTYPES:生成根文件系统使用的格式,本例支持四种。

  • EXTRA_IMAGECMD:镜像创建命令额外选项,本例创建 JFFS2 时使用 "-lnp "。

  • WKS_FILE:创建分区镜像所用 Wic kickstart 文件位置。

  • do_image_wic[depends]:构建时生成的任务依赖,本例指定生成 Wic 镜像 系统根目录所需工具。

  • SERIAL_CONSOLES:定义通过 getty 启用的一个或多个串口控制台。

  • PREFERRED_PROVIDER_virtual/kernel:选择内核提供者, 本例是层 recipes-kernel/linux 中的 linux-yocto。

  • PREFERRED_VERSION_linux-yocto:内核配方版本, 本例为 "6.18%"。

  • KERNEL_IMAGETYPE:内核类型,本例为 zImage。

  • KERNEL_DEVICETREE:生成的 *.dtb 名称,包含各 BeagleBone 设备 的全部设备树。

  • KERNEL_EXTRA_ARGS:内核编译时传给 make 的额外参数,本例为 LOADADDR=${UBOOT_ENTRYPOINT}。

  • SPL_BINARY:次级程序加载器类型。本例为 MLO,即 Multimedia card LOader。BeagleBone 启动需要此类型,因此必须设为 MLO。

    备注

    SPL 变量用法见 u-boot.inc。

  • UBOOT_*:构建 U-Boot 的配置,本例需要其启动设备。

  • MACHINE_FEATURES:硬件支持功能,本例为 "usbgadget usbhost vfat alsa"。

  • IMAGE_BOOT_FILES:使用 Wic 的 bootimg_partition 或 bootimg_efi source 插件时,安装到启动分区的文件。

1 BSP 内核配方示例

BeagleBone 使用的内核配方由机器配置选定:

PREFERRED_PROVIDER_virtual/kernel ?= "linux-yocto"
PREFERRED_VERSION_linux-yocto ?= "6.18%"

层的 meta-yocto-bsp/recipes-kernel/linux 保存内核元数据。本例通过 linux-yocto_6.18.bbappend 覆盖已有 linux-yocto_6.18.bb,后者位于 https://git.openembedded.org/openembedded-core/tree/meta/recipes-kernel/linux。

追加文件内容:

COMPATIBLE_MACHINE:genericarm64 = "genericarm64"
COMPATIBLE_MACHINE:beaglebone-yocto = "beaglebone-yocto"
COMPATIBLE_MACHINE:genericx86 = "genericx86"
COMPATIBLE_MACHINE:genericx86-64 = "genericx86-64"

KMACHINE:beaglebone-yocto ?= "beaglebone"
KMACHINE:genericx86 ?= "common-pc"
KMACHINE:genericx86-64 ?= "common-pc-64"

KBRANCH:genericarm64 ?= "v6.18/standard/genericarm64"
SRCREV_machine:genericarm64 ?= "5cd75b0b5da06045acdd0c66e50656ab82cb880f"

此文件适用于该层所有机器,BeagleBone 相关语句带 beaglebone-yocto 覆盖,用于 覆盖原配方同类设置:

  • KBRANCH:构建时验证、修补和配置的内核分支。

  • KMACHINE:内核认识的机器名,可能与构建系统名称不同。

  • SRCREV:构建使用的源码修订。

  • COMPATIBLE_MACHINE:匹配一个或多个兼容目标的正则表达式。

  • LINUX_VERSION:构建内核镜像所用 kernel.org 版本。